PK!*Ilfastest/__init__.pyname = "fastest" PK!fastest/bodies/__init__.pyname = "bodies_pkg"PK!Roe fastest/bodies/f.pyimport uuid from fastest.type import type_inference def case_generator(): return str(uuid.uuid4()).upper().replace("-", "")[0:10] def create_var_type_test_case(function_obj, variable_name, statements): function_name = function_obj['name'] args = ', '.join(function_obj['args']) expected_types = type_inference.infer(variable_name, statements) if len(expected_types) == 1: expected_type = expected_types[0] type_message = 'Automatically detected type of {variable} to be an {type}'\ .format(variable=variable_name, type=expected_type) return """ def test__{function}__for_typeof__arg__{variable}(self): # You must always check type of arguments # to prevent unexpected crashes # # Feel free to remove this test if you're confident that this is not required # {message} self.assert({function}({args}), {type}) """.format(function=function_name, args=args, variable=variable_name, message=type_message, type=expected_type) else: expected_type = '' return """ def test__{function}__for_typeof__arg__{variable}(self): # You must always check type of arguments # to prevent unexpected crashes # # Feel free to remove this test if you're confident that this is not required self.assert({function}({args}), {type}) """.format(function=function_name, args=args, variable=variable_name, type=expected_type) def create_return_type_test_case(function_obj, return_values, statements): function_name = function_obj['name'] args = ', '.join(function_obj['args']) for return_value in return_values: expected_types = type_inference.infer(return_value, statements) multi_type_return = len(list(set(expected_types))) > 1 if multi_type_return: type_message = 'Seems like the return value {} is one of {}. ' \ 'Be very careful with such functions, ' \ 'a better approach would be to have different ' \ 'functions to perform the different kind of tasks'.format(return_value, expected_types) expected_type = '' return """ def test__{function}__for_typeof_return__{variable}(self): # You must always have checkpoints for return values # # Feel free to remove this test if you're confident that this is not required # {message} self.assertIs({function}({args}), {type}) """.format(function=function_name, args=args, variable=return_value, message=type_message, type=expected_type) else: expected_type = expected_types[0] return """ def test__{function}__for_typeof_return__{variable}(self): # You must always have checkpoints for return values # # # Feel free to remove this test if you're confident that this is not required self.assertIs({function}({args}), {type}) """.format(function=function_name, args=args, variable=return_value, type=expected_type) def create_naive_test_case(function_object, test): return """ def test__{function_name}__{case_id}(self): self.assertEqual({function}, {value}) """.format( function_name=function_object['name'], case_id=case_generator(), function=test['from'], value=test['expect'] ) PK!"fastest/case_labyrinth/__init__.pyname = "case_labyrinth_pkg"PK!U4fastest/case_labyrinth/type_check_detect/__init__.pyname = "type_check_detect_pkg" PK!d6fastest/case_labyrinth/type_check_detect/type_check.pydef detect_type_check(statements, argument): for statement in statements: # TODO: Does not scale need patterns for string if 'if type({argument})'.format(argument=argument) in statement: return True return False PK!fastest/cli.pyimport argparse import os import time import subprocess from fastest.io.read_file import read_file from fastest.code_assets.function import get_functions from fastest.compiler import compile from watchdog.observers import Observer from watchdog.events import PatternMatchingEventHandler parser = argparse.ArgumentParser(description='Create test cases automatically') parser.add_argument('--path', help='Project root, use $(pwd) to be sure') args = parser.parse_args() test_files = [ test_file.replace('.py', '') for test_file in os.listdir('./test') if '__' not in test_file[:2] ] report_path = os.path.abspath(os.path.join(args.path, 'htmlcov/index.html')) class PyFileHandler(PatternMatchingEventHandler): patterns = ["*.py"] def process(self, event): """ event.event_type 'modified' | 'created' | 'moved' | 'deleted' event.is_directory True | False event.src_path path/to/observed/file """ print(event.src_path, event.event_type) if '__test.py' not in event.src_path and \ os.path.isfile(event.src_path) and \ 'core' not in event.src_path: page = read_file(args.path, event.src_path) functions = get_functions(page) compile.build(functions, event.src_path, args.path) command = ['test.{}'.format(test_file) for test_file in test_files] subprocess.call(['coverage', 'run', '--source', 'mocks', '-m', 'unittest'] + command) subprocess.call(['coverage', 'report']) subprocess.call(['coverage', 'html']) print(report_path) def on_modified(self, event): self.process(event) def on_created(self, event): self.process(event) observer = Observer() observer.schedule(PyFileHandler(), args.path, recursive=True) observer.start() try: while True: time.sleep(1) except KeyboardInterrupt: observer.stop() observer.join() PK!XE}fastest/code_assets/__init__.pyname = "code_assets_pkg" PK!vB+ fastest/code_assets/arguments.pydef get_args(args_str): args_str = args_str.strip() args_str = args_str.replace('(', '') args_str = args_str.replace(')', '') args = args_str.split(',') args = [arg.strip() for arg in args] return argsPK!nX355#fastest/code_assets/conditionals.pyimport re def get_conditionals(statement): passPK!ɡC==fastest/code_assets/function.pyimport re from fastest.code_assets.arguments import get_args from fastest.code_assets.variables import get_variables from fastest.code_assets.return_value import get_return_values from fastest.code_assets.naive_case_detector import get_naive_case def get_functions(page): statements = re.split(r'\n', page) function_map = [] function_finder = None function_running = False function_object = {} function_body_start = 0 for statement_number in range(len(statements)): if function_running is False: function_finder = re.match(r'def ((\w[A-Za-z_]*[^\(])(\(.*[^:]\)))', statements[statement_number]) function_body_start = statement_number if function_finder is not None: function_running = True function_object['name'] = function_finder.group(2) function_object['args'] = get_args(function_finder.group(3)) function_finder = None if function_body_start != statement_number and re.match(r'^\s+', statements[statement_number]) is None: function_object['str'] = '\n'.join(statements[function_body_start: statement_number]) function_object['returns'] = get_return_values(function_object['str']) function_object['vars'] = get_variables(function_object['str'], function_object['args']) function_object['tests'] = get_naive_case(function_object['str']) function_map.append(function_object) function_object = {} function_running = False function_finder = None return function_map PK!}77fastest/code_assets/keywords.pyFALSE = 'False' CLASS = 'class' FINALLY = 'finally' IS = 'is' RETURN = 'return' NONE = 'None' CONTINUE = 'continue' FOR = 'for' LAMBDA = 'lambda' TRY = 'try' TRUE = 'True' DEF = 'def' FROM = 'from' NONLOCAL = 'nonlocal' WHILE = 'while' AND = 'and' DEL = 'del' GLOBAL = 'global' NOT = 'not' WITH = 'with' AS = 'as' ELIF = 'elif' IF = 'if' OR = 'or' YIELD = 'yield' ASSERT = 'assert' ELSE = 'else' IMPORT = 'import' PASS = 'pass' BREAK = 'break' EXCEPT = 'except' IN = 'in' RAISE = 'raise' RESERVED = [ FALSE, CLASS, FINALLY, IS, RETURN, NONE, CONTINUE, FOR, LAMBDA, TRY, TRUE, DEF, FROM, NONLOCAL, WHILE, AND, DEL, GLOBAL, NOT, WITH, AS, ELIF, IF, OR, YIELD, ASSERT, ELSE, IMPORT, PASS, BREAK, EXCEPT, IN, RAISE, "+", "-", "/", "*", "+=", "-=", "/=", "*=", "**", "%", "!", "@", "^", "&", "(", ")", "=", "'", "\"", "|", ">", ">=", "<", "<=", ",", "!=", "==", ":", '.' ]PK! ڳ*fastest/code_assets/naive_case_detector.pyimport re FUNCTION_CALL = 0 OUTPUT = 1 def get_naive_case(statements): function_call_pattern = r'example: [\s\S]+?(?=->)' total_pattern = r'example: [\s\S]+?(?=#)' function_call_matches = re.findall(function_call_pattern, statements, re.M) total_matches = re.findall(total_pattern, statements, re.M) test_cases = [] for func_match, total_match in zip(function_call_matches, total_matches): func_match = func_match.replace('example:', '').strip() expectation = total_match\ .replace(func_match, '')\ .replace('example:', '')\ .replace('->', '')\ .strip() test_cases.append({ 'from': func_match, 'expect': expectation }) return test_casesPK!+ #fastest/code_assets/return_value.pyimport re def get_return_values(statements): return_values = re.findall(r'return (.*)', statements) if len(return_values) > 0: return return_values else: return [None] PK!!^ fastest/code_assets/variables.pyimport re from fastest.code_assets import keywords def get_variables(statements, arguments): statements = statements.split('\n') statements = statements[1:] statements = ' '.join(statements) statements = re.sub(r'\s+', ' ', statements).replace(':', '') words = statements.split(' ') exclude_options = keywords.RESERVED + arguments return list(set([word for word in words if word not in exclude_options and word.isalpha()])) PK!Wfastest/compiler/__init__.pyname = "compiler_pkg" PK!ωCCfastest/compiler/compile.pyimport os from fastest.bodies import f def build(function_objects, src_file_path, base_path): test_file_name = src_file_path.split('/')[-1].replace('.py', '__test.py') deps_import = src_file_path.replace(base_path + '/', '').replace('/', '.').replace('.py', '') root_module_name = deps_import.split('.')[-1] test_file_path = os.path.join(base_path, 'test', test_file_name) with open(test_file_path, 'w+') as fp: fp.write('import unittest\n\n') for function_object in function_objects: fp.write('from {} import {}\n'.format(deps_import, function_object['name'])) for function_object in function_objects: fp.write( """\n class Test_{}_{}(unittest.TestCase): """.format(root_module_name, function_object['name']) ) for test in function_object['tests']: fp.write(f.create_naive_test_case(function_object, test))PK![nfastest/io/__init__.pyname = "io_pkg" PK!ً9fastest/io/read_file.pyimport os def get_current_directory(): return os.path.dirname(os.path.realpath(__file__)) def read_file(dir_path, file_path): goal_dir = os.path.join(dir_path, file_path) with open(os.path.abspath(goal_dir), 'r') as fp: contents = fp.read() return contents PK!_RSfastest/type/__init__.pyname = "type_pkg" PK!&]  fastest/type/type_inference.pyfrom fastest.type import type_usage_patterns INT = 0 STR = 1 LIST = 2 TUPLE = 3 DICT = 4 type_map = ['int', 'str', 'list', 'tuple', 'dict'] def infer(variable, statements): statements = statements.split('\n') statements = statements[1:] type_chances = [0] * 5 for statement in statements: type_chances[INT] += type_usage_patterns.used_as_int(statement, variable) type_chances[STR] += type_usage_patterns.used_as_str(statement, variable) type_chances[LIST] += type_usage_patterns.used_as_list(statement, variable) type_chances[TUPLE] += type_usage_patterns.used_as_tuple(statement, variable) type_chances[DICT] += type_usage_patterns.used_as_dict(statement, variable) max_prob_type = max(type_chances) if type_chances.count(max_prob_type) > 1: return [type_map[i] for i, type_chance in enumerate(type_chances) if type_chance == max_prob_type] else: return [type_map[type_chances.index(max_prob_type)]] PK![y y #fastest/type/type_usage_patterns.pyimport re from fastest.utils import count_truthy def used_as_int(statement, variable): statement = statement.strip() assignment = re.search(r'{variable}\s*=\s*\d+'.format(variable=variable), statement) addition = re.search(r'{variable}\s*\+\s*'.format(variable=variable), statement) addition_inc = re.search(r'{variable}\s*\+=\s*\d+'.format(variable=variable), statement) multiplication = re.search(r'{variable}\s*\*\s*'.format(variable=variable), statement) subtraction = re.search(r'{variable}\s*-\s*'.format(variable=variable), statement) division = re.search(r'{variable}\s*/\s*'.format(variable=variable), statement) return count_truthy([assignment, addition, subtraction,multiplication, division, addition_inc]) def used_as_str(statement, variable): statement = statement.strip() assignment = re.match('{variable}\s*=\s*"|\'\w*"|\''.format(variable=variable), statement) addition = re.match(r'{variable}\s*\+\s*'.format(variable=variable), statement) multiplication = re.match(r'{variable}\s*\*\s*'.format(variable=variable), statement) return count_truthy([assignment, addition, multiplication]) def used_as_iterable(statement, variable): statement = statement.strip() loop = re.match(r'for \w+ in {variable}'.format(variable=variable), statement) map_fn = re.search(r'map\(.*[^,)],\s*{variable}'.format(variable=variable), statement) filter_fn = re.search(r'filter\(.*[^,)],\s*{variable}'.format(variable=variable), statement) reduce_fn = re.search(r'reduce\(.*[^,)],\s*{variable}'.format(variable=variable), statement) item_index = re.match(r'{variable}\[\d+\]'.format(variable=variable), statement) return count_truthy([loop, map_fn, filter_fn, reduce_fn, item_index]) def used_as_list(statement, variable): statement = statement.strip() assignment = re.match(r'{variable}\s*=\s*\['.format(variable=variable), statement) assignment_as_instance = re.match(r'{variable}\s*=\s*list\('.format(variable=variable), statement) append = re.search(r'{variable}.append\('.format(variable=variable), statement) return count_truthy([assignment_as_instance, assignment, append]) + used_as_iterable(statement, variable) def used_as_tuple(statement, variable): statement = statement.strip() assignment = re.match(r'{variable}\s*=\s*\('.format(variable=variable), statement) assignment_as_instance = re.match(r'{variable}\s*=\s*tuple\('.format(variable=variable), statement) insert = re.match(r'{variable}.insert\('.format(variable=variable), statement) return count_truthy([assignment_as_instance, assignment, insert]) + used_as_iterable(statement, variable) def used_as_dict(statement, variable): statement = statement.strip() assignment = re.search(r'{variable}\s*=\s*\{{'.format(variable=variable), statement) key_ref_str = re.search(r'{variable}\[\"|\'\w+\"|\'\]'.format(variable=variable), statement) key_ref_var = re.search(r'{variable}\[\w+\]'.format(variable=variable), statement) get_access = re.search(r'{variable}.get\('.format(variable=variable), statement) return count_truthy([assignment, key_ref_str, key_ref_var, get_access]) PK!No'@fastest/utils.pydef count_truthy(items): counter = 0 for item in items: if item is not None: counter += 1 return counter PK!HڽTUfastest-0.0.3.dist-info/WHEEL A н#Z;/"d&F[xzw@Zpy3Fv]\fi4WZ^EgM_-]#0(q7PK!Hh fastest-0.0.3.dist-info/METADATAON0 )4*bMzY:)IZioO^Q#{8F^0D QQ,e%3c$ȪAh]7V@;O1=ꔸg-!Z|st>űpܓ;1Nr:q,k0-6Hw>=Vrvp+Ka`([A)Xo0{Fj,G,!Myln^|PK!H efastest-0.0.3.dist-info/RECORDɲH}? bE/ !Ad.]VD2X|䉟i8`Ac|wdCp6ѵdѕQZn AhdN!;^EU^\kil8<ɺiP0@T@p`"9KoK:n˲aU4?XXn6jSDi*}ь&|Y;)>i:va[µu eO!{ 8q$`/U9h]mj@QzՉВ.BK1le>e`䖉/;3@o:N)Թ`>Y*^bx9tL:%GK;q}J