diff options
author | Kevin Van Brunt <kmvanbrunt@gmail.com> | 2018-09-27 13:08:14 -0400 |
---|---|---|
committer | Kevin Van Brunt <kmvanbrunt@gmail.com> | 2018-09-27 13:08:14 -0400 |
commit | 0f2f798586d4b680baa20c24086709b9faec9c24 (patch) | |
tree | 1b11a12dc3a773108c47bf898f5a3c03bcd866d7 /cmd2 | |
parent | 19cdd5ff086a7bc8714e011084a1aaecacbf1900 (diff) | |
parent | 86f27ac241c2366022c55e891e449a2ed08b308a (diff) | |
download | cmd2-git-0f2f798586d4b680baa20c24086709b9faec9c24.tar.gz |
Merge branch 'macro' into argparse_conversion
Diffstat (limited to 'cmd2')
-rw-r--r-- | cmd2/cmd2.py | 28 | ||||
-rw-r--r-- | cmd2/parsing.py | 42 |
2 files changed, 37 insertions, 33 deletions
diff --git a/cmd2/cmd2.py b/cmd2/cmd2.py index fcad6880..2c58d550 100644 --- a/cmd2/cmd2.py +++ b/cmd2/cmd2.py @@ -48,8 +48,7 @@ from . import utils from . import plugin from .argparse_completer import AutoCompleter, ACArgumentParser, ACTION_ARG_CHOICES from .clipboard import can_clip, get_paste_buffer, write_to_paste_buffer -from .parsing import StatementParser, Statement, Macro, MacroArg, \ - macro_normal_arg_pattern, macro_escaped_arg_pattern, digit_pattern +from .parsing import StatementParser, Statement, Macro, MacroArg # Set up readline from .rl_utils import rl_type, RlType, rl_get_point, rl_set_prompt, vt100_support, rl_make_safe_prompt @@ -2041,11 +2040,11 @@ class Cmd(cmd.Cmd): for arg in reverse_arg_list: if arg.is_escaped: - to_replace = '{{' + str(arg.number) + '}}' - replacement = '{' + str(arg.number) + '}' + to_replace = '{{' + arg.number_str + '}}' + replacement = '{' + arg.number_str + '}' else: - to_replace = '{' + str(arg.number) + '}' - replacement = statement.argv[arg.number] + to_replace = '{' + arg.number_str + '}' + replacement = statement.argv[int(arg.number_str)] parts = resolved.rsplit(to_replace, maxsplit=1) resolved = parts[0] + replacement + parts[1] @@ -2374,7 +2373,7 @@ class Cmd(cmd.Cmd): # Find all normal arguments arg_list = [] - normal_matches = re.finditer(macro_normal_arg_pattern, value) + normal_matches = re.finditer(MacroArg.macro_normal_arg_pattern, value) max_arg_num = 0 num_set = set() @@ -2382,8 +2381,9 @@ class Cmd(cmd.Cmd): try: cur_match = normal_matches.__next__() - # Get the number between the braces - cur_num = int(re.findall(digit_pattern, cur_match.group())[0]) + # Get the number string between the braces + cur_num_str = (re.findall(MacroArg.digit_pattern, cur_match.group())[0]) + cur_num = int(cur_num_str) if cur_num < 1: self.perror("Argument numbers must be greater than 0", traceback_war=False) return @@ -2392,7 +2392,7 @@ class Cmd(cmd.Cmd): if cur_num > max_arg_num: max_arg_num = cur_num - arg_list.append(MacroArg(start_index=cur_match.start(), number=cur_num, is_escaped=False)) + arg_list.append(MacroArg(start_index=cur_match.start(), number_str=cur_num_str, is_escaped=False)) except StopIteration: break @@ -2404,16 +2404,16 @@ class Cmd(cmd.Cmd): return # Find all escaped arguments - escaped_matches = re.finditer(macro_escaped_arg_pattern, value) + escaped_matches = re.finditer(MacroArg.macro_escaped_arg_pattern, value) while True: try: cur_match = escaped_matches.__next__() - # Get the number between the braces - cur_num = int(re.findall(digit_pattern, cur_match.group())[0]) + # Get the number string between the braces + cur_num_str = re.findall(MacroArg.digit_pattern, cur_match.group())[0] - arg_list.append(MacroArg(start_index=cur_match.start(), number=cur_num, is_escaped=True)) + arg_list.append(MacroArg(start_index=cur_match.start(), number_str=cur_num_str, is_escaped=True)) except StopIteration: break diff --git a/cmd2/parsing.py b/cmd2/parsing.py index 498834cf..949be42e 100644 --- a/cmd2/parsing.py +++ b/cmd2/parsing.py @@ -12,17 +12,6 @@ import attr from . import constants from . import utils -# Pattern used to find normal argument -# Match strings like: {5}, {{{{{4}, {2}}}}} -macro_normal_arg_pattern = re.compile(r'(?<!\{)\{\d+\}|\{\d+\}(?!\})') - -# Pattern used to find escaped arguments (2 or more braces on each side of digit) -# Match strings like: {{5}}, {{{{{4}}, {{2}}}}}, {{{4}}} -macro_escaped_arg_pattern = re.compile(r'\{{2}\d+\}{2}') - -# Finds a string of digits -digit_pattern = re.compile(r'\d+') - @attr.s(frozen=True) class MacroArg: @@ -32,13 +21,28 @@ class MacroArg: Escaped argument syntax: {{5}} """ # The starting index of this argument in the macro value - start_index = attr.ib(validator=attr.validators.instance_of(int), type=int) + start_index = attr.ib(validator=attr.validators.instance_of(int)) - # The number that appears between the braces - number = attr.ib(validator=attr.validators.instance_of(int), type=int) + # The number string that appears between the braces + # This is a string instead of an int because we support unicode digits and must be able + # to reproduce this string later + number_str = attr.ib(validator=attr.validators.instance_of(str)) # Tells if this argument is escaped and therefore needs to be unescaped - is_escaped = attr.ib(validator=attr.validators.instance_of(bool), type=bool) + is_escaped = attr.ib(validator=attr.validators.instance_of(bool)) + + # Pattern used to find normal argument + # Digits surrounded by exactly 1 brace on a side and 1 or more braces on the opposite side + # Match strings like: {5}, {{{{{4}, {2}}}}} + macro_normal_arg_pattern = re.compile(r'(?<!\{)\{\d+\}|\{\d+\}(?!\})') + + # Pattern used to find escaped arguments + # Digits surrounded by 2 or more braces on both sides + # Match strings like: {{5}}, {{{{{4}}, {{2}}}}} + macro_escaped_arg_pattern = re.compile(r'\{{2}\d+\}{2}') + + # Finds a string of digits + digit_pattern = re.compile(r'\d+') @attr.s(frozen=True) @@ -46,16 +50,16 @@ class Macro: """Defines a cmd2 macro""" # Name of the macro - name = attr.ib(validator=attr.validators.instance_of(str), type=str) + name = attr.ib(validator=attr.validators.instance_of(str)) # The string the macro resolves to - value = attr.ib(validator=attr.validators.instance_of(str), type=str) + value = attr.ib(validator=attr.validators.instance_of(str)) # The required number of args the user has to pass to this macro - required_arg_count = attr.ib(validator=attr.validators.instance_of(int), type=int) + required_arg_count = attr.ib(validator=attr.validators.instance_of(int)) # Used to fill in argument placeholders in the macro - arg_list = attr.ib(factory=list, validator=attr.validators.instance_of(list), type=List[MacroArg]) + arg_list = attr.ib(factory=list, validator=attr.validators.instance_of(list)) @attr.s(frozen=True) |