Mercurial > python-cmd2
comparison cmd2.py @ 434:742fd308f0c9
better SkipTo around quoted strings
author | catherine.devlin@gmail.com |
---|---|
date | Sun, 21 Aug 2011 02:39:43 -0400 |
parents | 5a814cb007ae |
children | bfbe4241bd6b |
comparison
equal
deleted
inserted
replaced
433:5a814cb007ae | 434:742fd308f0c9 |
---|---|
626 - args: has > inside | 626 - args: has > inside |
627 - multilineCommand: multiline | 627 - multilineCommand: multiline |
628 - terminator: ; | 628 - terminator: ; |
629 - terminator: ; | 629 - terminator: ; |
630 >>> print (c.parser.parseString('multiline command /* with comment in progress;').dump()) | 630 >>> print (c.parser.parseString('multiline command /* with comment in progress;').dump()) |
631 ['multiline', ' command'] | 631 ['multiline', ' command /* with comment in progress;'] |
632 - multilineCommand: multiline | 632 - multilineCommand: multiline |
633 >>> print (c.parser.parseString('multiline command /* with comment complete */ is done;').dump()) | 633 >>> print (c.parser.parseString('multiline command /* with comment complete */ is done;').dump()) |
634 ['multiline', 'command /* with comment complete */ is done', ';', ''] | 634 ['multiline', 'command /* with comment complete */ is done', ';', ''] |
635 - args: command /* with comment complete */ is done | 635 - args: command /* with comment complete */ is done |
636 - multilineCommand: multiline | 636 - multilineCommand: multiline |
647 - args: command ends | 647 - args: command ends |
648 - multilineCommand: multiline | 648 - multilineCommand: multiline |
649 - terminator: ['\n', '\n'] | 649 - terminator: ['\n', '\n'] |
650 - terminator: ['\n', '\n'] | 650 - terminator: ['\n', '\n'] |
651 >>> print (c.parser.parseString('multiline command "with term; ends" now\n\n').dump()) | 651 >>> print (c.parser.parseString('multiline command "with term; ends" now\n\n').dump()) |
652 ['multiline', 'command ends', '\n', '\n'] | 652 ['multiline', 'command "with term; ends" now', '\n', '\n'] |
653 - args: command "with term; ends" now | 653 - args: command "with term; ends" now |
654 - multilineCommand: multiline | 654 - multilineCommand: multiline |
655 - statement: ['multiline', '"with term; ends" now', '\n', '\n'] | 655 - statement: ['multiline', 'command "with term; ends" now', '\n', '\n'] |
656 - args: command "with term; ends" now | 656 - args: command "with term; ends" now |
657 - multilineCommand: multiline | 657 - multilineCommand: multiline |
658 - terminator: ['\n', '\n'] | 658 - terminator: ['\n', '\n'] |
659 - terminator: ['\n', '\n'] | 659 - terminator: ['\n', '\n'] |
660 >>> print (c.parser.parseString('what if "ending is in quotes" but').dump()) | 660 >>> print (c.parser.parseString('what if "quoted strings /* seem to " start comments?').dump()) |
661 ['what', 'if "ending is in quotes" but'] | 661 ['what', 'if "quoted strings /* seem to " start comments?'] |
662 - args: if "ending is in quotes" but | 662 - args: if "quoted strings /* seem to " start comments? |
663 - command: what | 663 - command: what |
664 - statement: ['what', 'if "ending is in quotes" but'] | 664 - statement: ['what', 'if "quoted strings /* seem to " start comments?'] |
665 - args: if "ending is in quotes" but | 665 - args: if "quoted strings /* seem to " start comments? |
666 - command: what | |
667 >>> print (c.parser.parseString('what if "ending is in quotes"').dump()) | |
668 ['what', 'if "ending is in quotes"'] | |
669 - args: if "ending is in quotes" | |
670 - command: what | |
671 - statement: ['what', 'if "ending is in quotes"'] | |
672 - args: if "ending is in quotes" | |
673 - command: what | 666 - command: what |
674 ''' | 667 ''' |
675 outputParser = (pyparsing.Literal('>>') | (pyparsing.WordStart() + '>') | pyparsing.Regex('[^=]>'))('output') | 668 outputParser = (pyparsing.Literal('>>') | (pyparsing.WordStart() + '>') | pyparsing.Regex('[^=]>'))('output') |
676 | 669 |
677 terminatorParser = pyparsing.Or([(hasattr(t, 'parseString') and t) or pyparsing.Literal(t) for t in self.terminators])('terminator') | 670 terminatorParser = pyparsing.Or([(hasattr(t, 'parseString') and t) or pyparsing.Literal(t) for t in self.terminators])('terminator') |
678 terminatorParser.ignore(pyparsing.quotedString) #fail | |
679 stringEnd = pyparsing.stringEnd ^ '\nEOF' | 671 stringEnd = pyparsing.stringEnd ^ '\nEOF' |
680 self.multilineCommand = pyparsing.Or([pyparsing.Keyword(c, caseless=self.case_insensitive) for c in self.multilineCommands])('multilineCommand') | 672 self.multilineCommand = pyparsing.Or([pyparsing.Keyword(c, caseless=self.case_insensitive) for c in self.multilineCommands])('multilineCommand') |
681 oneLineCommand = (~self.multilineCommand + pyparsing.Word(self.legalChars))('command') | 673 oneLineCommand = (~self.multilineCommand + pyparsing.Word(self.legalChars))('command') |
682 pipe = pyparsing.Keyword('|', identChars='|') | 674 pipe = pyparsing.Keyword('|', identChars='|') |
683 self.commentGrammars.ignore(pyparsing.quotedString).setParseAction(lambda x: '') | 675 self.commentGrammars.ignore(pyparsing.quotedString).setParseAction(lambda x: '') |
684 doNotParse = self.commentGrammars | commentInProgress | 676 doNotParse = self.commentGrammars | self.commentInProgress | pyparsing.quotedString |
685 afterElements = \ | 677 afterElements = \ |
686 pyparsing.Optional(pipe + pyparsing.SkipTo(outputParser ^ stringEnd)('pipeTo')) + \ | 678 pyparsing.Optional(pipe + pyparsing.SkipTo(outputParser ^ stringEnd, ignore=doNotParse)('pipeTo')) + \ |
687 pyparsing.Optional(outputParser + pyparsing.SkipTo(stringEnd).setParseAction(lambda x: x[0].strip())('outputTo')) | 679 pyparsing.Optional(outputParser + pyparsing.SkipTo(stringEnd, ignore=doNotParse).setParseAction(lambda x: x[0].strip())('outputTo')) |
688 if self.case_insensitive: | 680 if self.case_insensitive: |
689 self.multilineCommand.setParseAction(lambda x: x[0].lower()) | 681 self.multilineCommand.setParseAction(lambda x: x[0].lower()) |
690 oneLineCommand.setParseAction(lambda x: x[0].lower()) | 682 oneLineCommand.setParseAction(lambda x: x[0].lower()) |
691 if self.blankLinesAllowed: | 683 if self.blankLinesAllowed: |
692 self.blankLineTerminationParser = pyparsing.NoMatch | 684 self.blankLineTerminationParser = pyparsing.NoMatch |
693 else: | 685 else: |
694 self.blankLineTerminator = (pyparsing.lineEnd + pyparsing.lineEnd)('terminator') | 686 self.blankLineTerminator = (pyparsing.lineEnd + pyparsing.lineEnd)('terminator') |
695 self.blankLineTerminator.setResultsName('terminator') | 687 self.blankLineTerminator.setResultsName('terminator') |
696 self.blankLineTerminationParser = ((self.multilineCommand ^ oneLineCommand) + pyparsing.SkipTo(self.blankLineTerminator).setParseAction(lambda x: x[0].strip())('args') + self.blankLineTerminator)('statement') | 688 self.blankLineTerminationParser = ((self.multilineCommand ^ oneLineCommand) + pyparsing.SkipTo(self.blankLineTerminator, ignore=doNotParse).setParseAction(lambda x: x[0].strip())('args') + self.blankLineTerminator)('statement') |
697 self.multilineParser = (((self.multilineCommand ^ oneLineCommand) + pyparsing.SkipTo(terminatorParser, ignore=self.commentInProgress).setParseAction(lambda x: x[0].strip())('args') + terminatorParser)('statement') + | 689 self.multilineParser = (((self.multilineCommand ^ oneLineCommand) + pyparsing.SkipTo(terminatorParser, ignore=doNotParse).setParseAction(lambda x: x[0].strip())('args') + terminatorParser)('statement') + |
698 pyparsing.SkipTo(outputParser ^ pipe ^ stringEnd).setParseAction(lambda x: x[0].strip())('suffix') + afterElements) | 690 pyparsing.SkipTo(outputParser ^ pipe ^ stringEnd, ignore=doNotParse).setParseAction(lambda x: x[0].strip())('suffix') + afterElements) |
699 self.multilineParser.ignore(self.commentInProgress) | 691 self.multilineParser.ignore(self.commentInProgress) |
700 self.singleLineParser = ((oneLineCommand + pyparsing.SkipTo(terminatorParser ^ stringEnd ^ pipe ^ outputParser).setParseAction(lambda x:x[0].strip())('args'))('statement') + | 692 self.singleLineParser = ((oneLineCommand + pyparsing.SkipTo(terminatorParser ^ stringEnd ^ pipe ^ outputParser, ignore=doNotParse).setParseAction(lambda x:x[0].strip())('args'))('statement') + |
701 pyparsing.Optional(terminatorParser) + afterElements) | 693 pyparsing.Optional(terminatorParser) + afterElements) |
702 #self.multilineParser = self.multilineParser.setResultsName('multilineParser') | 694 #self.multilineParser = self.multilineParser.setResultsName('multilineParser') |
703 #self.singleLineParser = self.singleLineParser.setResultsName('singleLineParser') | 695 #self.singleLineParser = self.singleLineParser.setResultsName('singleLineParser') |
704 self.blankLineTerminationParser = self.blankLineTerminationParser.setResultsName('statement') | 696 self.blankLineTerminationParser = self.blankLineTerminationParser.setResultsName('statement') |
705 self.parser = self.prefixParser + ( | 697 self.parser = self.prefixParser + ( |
706 stringEnd | | 698 stringEnd | |
707 self.multilineParser | | 699 self.multilineParser | |
708 self.singleLineParser | | 700 self.singleLineParser | |
709 self.blankLineTerminationParser | | 701 self.blankLineTerminationParser | |
710 self.multilineCommand + pyparsing.SkipTo(stringEnd) | 702 self.multilineCommand + pyparsing.SkipTo(stringEnd, ignore=doNotParse) |
711 ) | 703 ) |
712 #self.parser.ignore(pyparsing.quotedString).ignore(self.commentGrammars) | |
713 self.parser.ignore(self.commentGrammars) | 704 self.parser.ignore(self.commentGrammars) |
714 | 705 |
715 inputMark = pyparsing.Literal('<') | 706 inputMark = pyparsing.Literal('<') |
716 inputMark.setParseAction(lambda x: '') | 707 inputMark.setParseAction(lambda x: '') |
717 fileName = pyparsing.Word(self.legalChars + '/\\') | 708 fileName = pyparsing.Word(self.legalChars + '/\\') |
719 inputFrom.setParseAction(replace_with_file_contents) | 710 inputFrom.setParseAction(replace_with_file_contents) |
720 # a not-entirely-satisfactory way of distinguishing < as in "import from" from < | 711 # a not-entirely-satisfactory way of distinguishing < as in "import from" from < |
721 # as in "lesser than" | 712 # as in "lesser than" |
722 self.inputParser = inputMark + pyparsing.Optional(inputFrom) + pyparsing.Optional('>') + \ | 713 self.inputParser = inputMark + pyparsing.Optional(inputFrom) + pyparsing.Optional('>') + \ |
723 pyparsing.Optional(fileName) + (pyparsing.stringEnd | '|') | 714 pyparsing.Optional(fileName) + (pyparsing.stringEnd | '|') |
724 #self.inputParser.ignore(pyparsing.quotedString).ignore(self.commentGrammars).ignore(self.commentInProgress) | 715 self.inputParser.ignore(self.commentInProgress) |
725 self.inputParser.ignore(self.commentGrammars).ignore(self.commentInProgress) | |
726 | 716 |
727 def preparse(self, raw, **kwargs): | 717 def preparse(self, raw, **kwargs): |
728 return raw | 718 return raw |
729 def postparse(self, parseResult): | 719 def postparse(self, parseResult): |
730 return parseResult | 720 return parseResult |