diff --git a/bin/gws b/bin/gws index d4b1d7d..831df1f 100755 --- a/bin/gws +++ b/bin/gws @@ -7,21 +7,30 @@ could load shortcuts from environment import os from sys import argv, exit -from typing import Tuple, List, Generator, Iterable, Sequence, Callable +from typing import Tuple, List, Generator, Iterable, Iterator, Sequence, Callable +from itertools import chain Args = Sequence[str] +StrIter = Iterable[str] + +DEBUG = False shortcuts = { + 'c': ['clean'], + 'b': ['build'], + 't': ['test'], 'bt': ['compileTestKotlin'], 'ct': ['componentTest'], + 'ctest': ['componentTest'], 'cb': ['clean', 'build'], 'cbx': ['clean', 'build', '-x', 'test'], - 'cbt': ['clean', 'build', 'compileTestKotlin'], + 'cbt': ['clean', 'build', 'compileTestKotlin', '-x', 'test'], '-nc': ['--no-build-cache'], - '-rr': ['--rerun-tasks'] + '-rr': ['--rerun-tasks'], + '-wl': ['--write-locks'] } -optionsWithArgument = set(['-x', '-b', '-c', '-g', '-p', '-D', '-I', '-P']) +optionsWithArgument = {'-x', '-b', '-c', '-g', '-p', '-D', '-I', '-P'} help_text = """\ Support functionality for gw application @@ -50,63 +59,102 @@ def show_shortcuts(): print(f" {key} ... {' '.join(value)}") -def flat_map(f: Callable, xs: Sequence) -> Iterable: - return (y for ys in xs for y in f(ys)) +def log(name, obj): + if DEBUG: + print(name + str(obj)) -def try_remove(lst: List, value) -> Tuple[bool, List]: +def flat_map(func, seq): + for item in seq: + for transformed in func(item): + yield transformed + + +def flatten(lst): + return list(chain(*lst)) + + +def partition(predicate: Callable, seq: Iterable) -> Tuple[List, List]: + true_list: List = [] + false_list: List = [] + for item in seq: + (true_list if predicate(item) else false_list).append(item) + return true_list, false_list + + +def try_remove(lst: Sequence, value) -> Tuple[bool, Sequence]: filtered = list(filter(lambda x: x != value, lst)) return len(lst) != len(filtered), filtered -def split_options(args: Args) -> Generator[List[str], None, None]: +def list_sub(lhs: Sequence, rhs: Sequence) -> Sequence: + return [item for item in lhs if item not in rhs] + + +def get_next(iterator: Iterator): + try: + item = next(iterator) + return True, item + except StopIteration: + return False, None + + +def pair_option_with_argument(args: StrIter) -> Generator[List[str], None, None]: iterator = iter(args) while True: - try: - arg = next(iterator) - if arg in optionsWithArgument: - yield [arg, next(iterator)] + has_next, option = get_next(iterator) + if has_next: + if option in optionsWithArgument: + has_next, value = get_next(iterator) + if has_next: + yield [option, value] + else: + yield [option] + return else: - yield [arg] - except StopIteration: - break - - -def mix_task_modules(modules: Sequence, tasks: Sequence) -> Generator[str, None, None]: - return (module + ':' + task for module in modules for task in tasks) - - -def remake(args: Args, modules: List[str]) -> List[str]: - tasks = [] - options = [] - for item in split_options(args): - if item[0].startswith('-'): - options.extend(item) + yield [option] else: - tasks.extend(item) + return + + +def mix_task_modules(modules: Sequence, tasks: Sequence) -> List[str]: + return [module + ':' + task for module in modules for task in tasks] + + +def remake(args: StrIter, modules: List[str]) -> List[str]: + options, tasks = partition(lambda item: item[0].startswith('-'), args) + log('options', options) + log('tasks', tasks) if modules and tasks: - return list(mix_task_modules(modules, tasks)) + options + return mix_task_modules(modules, flatten(tasks)) + flatten(options) else: - return tasks + modules + options + return flatten(tasks + modules + options) def prepare_args(args: Args) -> List[str]: modules = list(filter(lambda value: value.startswith(':'), args)) - args = (arg for arg in args if arg not in modules) - args = flat_map(lambda arg: shortcuts.get(arg, [arg]), args) - args = list(args) - args = remake(args, modules) - return list(args) + log('modules', modules) + _args = list_sub(args, modules) + log('stage 1', _args) + _args = list(flat_map(lambda arg: shortcuts.get(arg, [arg]), _args)) + log('stage 2', _args) + _args = list(pair_option_with_argument(_args)) + log('stage 3', _args) + _args = remake(_args, modules) + log('stage 4', _args) + return list(_args) def prepare_command(args: Args) -> str: - args = prepare_args(args) - return 'gw ' + ' '.join(args) + _args = prepare_args(args) + return 'gw ' + ' '.join(_args) def main(args: List[str]): if not args: show_help() + global DEBUG + DEBUG, args = try_remove(args, '--debug') just_show, args = try_remove(args, '--show') cmd = prepare_command(args) print(cmd)