# HG changeset patch # User catherine.devlin@gmail.com # Date 1313908783 14400 # Node ID 742fd308f0c976c402903886716fe1e7832df040 # Parent 5a814cb007ae3c7327a94f116ef796011f41b273 better SkipTo around quoted strings diff -r 5a814cb007ae -r 742fd308f0c9 cmd2.py --- a/cmd2.py Sun Aug 21 02:22:13 2011 -0400 +++ b/cmd2.py Sun Aug 21 02:39:43 2011 -0400 @@ -628,7 +628,7 @@ - terminator: ; - terminator: ; >>> print (c.parser.parseString('multiline command /* with comment in progress;').dump()) - ['multiline', ' command'] + ['multiline', ' command /* with comment in progress;'] - multilineCommand: multiline >>> print (c.parser.parseString('multiline command /* with comment complete */ is done;').dump()) ['multiline', 'command /* with comment complete */ is done', ';', ''] @@ -649,42 +649,34 @@ - terminator: ['\n', '\n'] - terminator: ['\n', '\n'] >>> print (c.parser.parseString('multiline command "with term; ends" now\n\n').dump()) - ['multiline', 'command ends', '\n', '\n'] + ['multiline', 'command "with term; ends" now', '\n', '\n'] - args: command "with term; ends" now - multilineCommand: multiline - - statement: ['multiline', '"with term; ends" now', '\n', '\n'] + - statement: ['multiline', 'command "with term; ends" now', '\n', '\n'] - args: command "with term; ends" now - multilineCommand: multiline - terminator: ['\n', '\n'] - terminator: ['\n', '\n'] - >>> print (c.parser.parseString('what if "ending is in quotes" but').dump()) - ['what', 'if "ending is in quotes" but'] - - args: if "ending is in quotes" but + >>> print (c.parser.parseString('what if "quoted strings /* seem to " start comments?').dump()) + ['what', 'if "quoted strings /* seem to " start comments?'] + - args: if "quoted strings /* seem to " start comments? - command: what - - statement: ['what', 'if "ending is in quotes" but'] - - args: if "ending is in quotes" but - - command: what - >>> print (c.parser.parseString('what if "ending is in quotes"').dump()) - ['what', 'if "ending is in quotes"'] - - args: if "ending is in quotes" - - command: what - - statement: ['what', 'if "ending is in quotes"'] - - args: if "ending is in quotes" + - statement: ['what', 'if "quoted strings /* seem to " start comments?'] + - args: if "quoted strings /* seem to " start comments? - command: what ''' outputParser = (pyparsing.Literal('>>') | (pyparsing.WordStart() + '>') | pyparsing.Regex('[^=]>'))('output') terminatorParser = pyparsing.Or([(hasattr(t, 'parseString') and t) or pyparsing.Literal(t) for t in self.terminators])('terminator') - terminatorParser.ignore(pyparsing.quotedString) #fail stringEnd = pyparsing.stringEnd ^ '\nEOF' self.multilineCommand = pyparsing.Or([pyparsing.Keyword(c, caseless=self.case_insensitive) for c in self.multilineCommands])('multilineCommand') oneLineCommand = (~self.multilineCommand + pyparsing.Word(self.legalChars))('command') pipe = pyparsing.Keyword('|', identChars='|') self.commentGrammars.ignore(pyparsing.quotedString).setParseAction(lambda x: '') - doNotParse = self.commentGrammars | commentInProgress + doNotParse = self.commentGrammars | self.commentInProgress | pyparsing.quotedString afterElements = \ - pyparsing.Optional(pipe + pyparsing.SkipTo(outputParser ^ stringEnd)('pipeTo')) + \ - pyparsing.Optional(outputParser + pyparsing.SkipTo(stringEnd).setParseAction(lambda x: x[0].strip())('outputTo')) + pyparsing.Optional(pipe + pyparsing.SkipTo(outputParser ^ stringEnd, ignore=doNotParse)('pipeTo')) + \ + pyparsing.Optional(outputParser + pyparsing.SkipTo(stringEnd, ignore=doNotParse).setParseAction(lambda x: x[0].strip())('outputTo')) if self.case_insensitive: self.multilineCommand.setParseAction(lambda x: x[0].lower()) oneLineCommand.setParseAction(lambda x: x[0].lower()) @@ -693,11 +685,11 @@ else: self.blankLineTerminator = (pyparsing.lineEnd + pyparsing.lineEnd)('terminator') self.blankLineTerminator.setResultsName('terminator') - self.blankLineTerminationParser = ((self.multilineCommand ^ oneLineCommand) + pyparsing.SkipTo(self.blankLineTerminator).setParseAction(lambda x: x[0].strip())('args') + self.blankLineTerminator)('statement') - self.multilineParser = (((self.multilineCommand ^ oneLineCommand) + pyparsing.SkipTo(terminatorParser, ignore=self.commentInProgress).setParseAction(lambda x: x[0].strip())('args') + terminatorParser)('statement') + - pyparsing.SkipTo(outputParser ^ pipe ^ stringEnd).setParseAction(lambda x: x[0].strip())('suffix') + afterElements) + self.blankLineTerminationParser = ((self.multilineCommand ^ oneLineCommand) + pyparsing.SkipTo(self.blankLineTerminator, ignore=doNotParse).setParseAction(lambda x: x[0].strip())('args') + self.blankLineTerminator)('statement') + self.multilineParser = (((self.multilineCommand ^ oneLineCommand) + pyparsing.SkipTo(terminatorParser, ignore=doNotParse).setParseAction(lambda x: x[0].strip())('args') + terminatorParser)('statement') + + pyparsing.SkipTo(outputParser ^ pipe ^ stringEnd, ignore=doNotParse).setParseAction(lambda x: x[0].strip())('suffix') + afterElements) self.multilineParser.ignore(self.commentInProgress) - self.singleLineParser = ((oneLineCommand + pyparsing.SkipTo(terminatorParser ^ stringEnd ^ pipe ^ outputParser).setParseAction(lambda x:x[0].strip())('args'))('statement') + + self.singleLineParser = ((oneLineCommand + pyparsing.SkipTo(terminatorParser ^ stringEnd ^ pipe ^ outputParser, ignore=doNotParse).setParseAction(lambda x:x[0].strip())('args'))('statement') + pyparsing.Optional(terminatorParser) + afterElements) #self.multilineParser = self.multilineParser.setResultsName('multilineParser') #self.singleLineParser = self.singleLineParser.setResultsName('singleLineParser') @@ -707,9 +699,8 @@ self.multilineParser | self.singleLineParser | self.blankLineTerminationParser | - self.multilineCommand + pyparsing.SkipTo(stringEnd) + self.multilineCommand + pyparsing.SkipTo(stringEnd, ignore=doNotParse) ) - #self.parser.ignore(pyparsing.quotedString).ignore(self.commentGrammars) self.parser.ignore(self.commentGrammars) inputMark = pyparsing.Literal('<') @@ -721,8 +712,7 @@ # as in "lesser than" self.inputParser = inputMark + pyparsing.Optional(inputFrom) + pyparsing.Optional('>') + \ pyparsing.Optional(fileName) + (pyparsing.stringEnd | '|') - #self.inputParser.ignore(pyparsing.quotedString).ignore(self.commentGrammars).ignore(self.commentInProgress) - self.inputParser.ignore(self.commentGrammars).ignore(self.commentInProgress) + self.inputParser.ignore(self.commentInProgress) def preparse(self, raw, **kwargs): return raw