Skip to content

Instantly share code, notes, and snippets.

@stasm
Forked from zbraniecki/fuzz
Last active August 29, 2015 14:23
Show Gist options
  • Save stasm/01ef409bb72756b8ce26 to your computer and use it in GitHub Desktop.
Save stasm/01ef409bb72756b8ce26 to your computer and use it in GitHub Desktop.
#!/usr/bin/env python
import argparse
import random
import hglib
import json
import subprocess
PY_COMPARE = 'compare-dirs'
JS_COMPARE = '/home/stas/moz/compare-locales.js/bin/compare-dirs.js'
def compare_details(det1, det2):
if type(det1) != type(det2):
raise Exception('Type mismatch between "%s" and "%s"' % (det1, det2))
if type(det1) == int:
if det1 != det2:
raise Exception('Different value between "%s" and "%s"' % (det1, det2))
if type(det1) == str or type(det1) == unicode:
if det1 != det2:
# python reports if the bad byte is a start or a continuation
# No way to get that in node.
if "codec can't decode" in det1 and "codec can't decode" in det2:
pass
# c-l returns slightly different string for unknown escape sequence
elif "unknown escape sequence" in det1 and "unknown escape sequence" in det2:
pass
else:
raise Exception('Different value between "%s" and "%s"' % (det1, det2))
if type(det1) == list:
if len(det1) != len(det2):
raise Exception('Different length between "%s" and "%s"' % (det1, det2))
for i in range(0, len(det1)):
compare_details(det1[i], det2[i])
if type(det1) == dict:
if det1.keys() != det2.keys():
if u'missingFile' in det1.keys():
# compare-locales does not include strings key for unknown
# formats. c-l.js includes strings: 0 in that case
det1[u'strings'] = 0
if det1.keys() != det2.keys():
raise Exception('Different keys between "%s" and "%s"' % (det1, det2))
for key in det1:
compare_details(det1[key], det2[key])
def check(ref, loc):
py = subprocess.check_output([PY_COMPARE, '--data=json', ref, loc])
js = subprocess.check_output([JS_COMPARE, '--data=json', ref, loc])
py_data = json.loads(py)
js_data = json.loads(js)
# compare details in depth
try:
compare_details(py_data['details'], js_data['details'])
except Exception as e:
print('bad details')
print(e)
return True
# compare summaries excluding keys, which are python only
py_sum = py_data['summary']['null']
js_sum = js_data['summary']['null']
for key in ('missing', 'missingInFiles', 'obsolete'):
if py_sum.get(key, 0) != js_sum.get(key, 0):
print 'bad', key
return True
if py_sum.get('changed', 0) + py_sum.get('unchanged', 0) + py_sum.get('keys', 0) != \
js_sum.get('changed', 0) + js_sum.get('unchanged', 0):
print 'bad changed+unchanged+keys'
return True
return False
def fuzz(max_comps, dir1, dir2):
client1 = hglib.open(args.dir1);
client2 = hglib.open(args.dir2);
tries_so_far = 0
orig1 = client1.tip().rev
orig2 = client2.tip().rev
compared = []
random.seed()
log1 = client1.log();
log2 = client2.log();
while len(log1) and len(log2):
tries_so_far += 1
print(tries_so_far)
if tries_so_far == args.max_comps:
break
cset1 = log1.pop(random.randrange(len(log1)))
cset2 = log2.pop(random.randrange(len(log2)))
client1.update(cset1.rev)
client2.update(cset2.rev)
if check(args.dir1, args.dir2):
print
print("{}: {}".format(args.dir1, cset1.node))
print("{}: {}".format(args.dir2, cset2.node))
break
client1.update(orig1)
client2.update(orig2)
if __name__=='__main__':
parser = argparse.ArgumentParser()
parser.add_argument("dir1", type=str, help="first dir")
parser.add_argument("dir2", type=str, help="second dir")
parser.add_argument("max_comps", type=int, help="max number of tries")
args = parser.parse_args()
fuzz(**vars(args))
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment