summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--CHANGES.md6
-rwxr-xr-xcmd2.py8
-rwxr-xr-xexamples/case_sensitive.py25
-rw-r--r--tests/test_cmd2.py2
-rw-r--r--tests/test_parsing.py40
5 files changed, 76 insertions, 5 deletions
diff --git a/CHANGES.md b/CHANGES.md
index 403669ae..919142b0 100644
--- a/CHANGES.md
+++ b/CHANGES.md
@@ -7,9 +7,11 @@ News
*Release date: TBD*
* Bug Fixes
- * Fixed some timing bugs when running unit tests in parallel by using monkeypatch
+ * Case-sensitive command parsing was completely broken and has been fixed
+ * <Ctrl>+D now properly quits when case-sensitive command parsing is enabled
* Fixed some pyperclip clipboard interaction bugs on Linux
-
+ * Fixed some timing bugs when running unit tests in parallel by using monkeypatch
+
0.7.5
-----
diff --git a/cmd2.py b/cmd2.py
index 4810dc26..f76072fe 100755
--- a/cmd2.py
+++ b/cmd2.py
@@ -891,13 +891,13 @@ class Cmd(cmd.Cmd):
try:
line = sm.input(safe_prompt)
except EOFError:
- line = 'EOF'
+ line = 'eof'
else:
self.stdout.write(safe_prompt)
self.stdout.flush()
line = self.stdin.readline()
if not len(line):
- line = 'EOF'
+ line = 'eof'
else:
line = line.rstrip('\r\n')
@@ -1846,6 +1846,10 @@ class ParserManager:
if case_insensitive:
multilineCommand.setParseAction(lambda x: x[0].lower())
oneline_command.setParseAction(lambda x: x[0].lower())
+ else:
+ multilineCommand.setParseAction(lambda x: x[0])
+ oneline_command.setParseAction(lambda x: x[0])
+
if blankLinesAllowed:
blankLineTerminationParser = pyparsing.NoMatch
else:
diff --git a/examples/case_sensitive.py b/examples/case_sensitive.py
new file mode 100755
index 00000000..828ebc06
--- /dev/null
+++ b/examples/case_sensitive.py
@@ -0,0 +1,25 @@
+#!/usr/bin/env python
+# coding=utf-8
+"""A sample application demonstrating when commands are set to be case sensitive.
+
+By default cmd2 parses commands in a case-insensitive manner. But this behavior can be changed.
+"""
+
+import cmd2
+
+
+class CaseSensitiveApp(cmd2.Cmd):
+ """ Example cmd2 application where commands are case-sensitive."""
+
+ def __init__(self):
+ # Set this before calling the super class __init__()
+ self.case_insensitive = False
+
+ cmd2.Cmd.__init__(self)
+
+ self.debug = True
+
+
+if __name__ == '__main__':
+ app = CaseSensitiveApp()
+ app.cmdloop()
diff --git a/tests/test_cmd2.py b/tests/test_cmd2.py
index 29958ed5..e2e54bae 100644
--- a/tests/test_cmd2.py
+++ b/tests/test_cmd2.py
@@ -1335,4 +1335,4 @@ def test_empty_stdin_input():
app.stdin.readline = m
line = app.pseudo_raw_input('(cmd2)')
- assert line == 'EOF'
+ assert line == 'eof'
diff --git a/tests/test_parsing.py b/tests/test_parsing.py
index bcb19f10..da8f6692 100644
--- a/tests/test_parsing.py
+++ b/tests/test_parsing.py
@@ -20,6 +20,7 @@ def hist():
h = cmd2.History([HistoryItem('first'), HistoryItem('second'), HistoryItem('third'), HistoryItem('fourth')])
return h
+# Case-insensitive parser
@pytest.fixture
def parser():
c = cmd2.Cmd()
@@ -32,6 +33,33 @@ def parser():
preparse=c.preparse, postparse=c.postparse, shortcuts=c.shortcuts)
return c.parser_manager.main_parser
+# Case-insensitive ParserManager
+@pytest.fixture
+def ci_pm():
+ c = cmd2.Cmd()
+ c.multilineCommands = ['multiline']
+ c.case_insensitive = True
+ c.parser_manager = cmd2.ParserManager(redirector=c.redirector, terminators=c.terminators, multilineCommands=c.multilineCommands,
+ legalChars=c.legalChars, commentGrammars=c.commentGrammars,
+ commentInProgress=c.commentInProgress, case_insensitive=c.case_insensitive,
+ blankLinesAllowed=c.blankLinesAllowed, prefixParser=c.prefixParser,
+ preparse=c.preparse, postparse=c.postparse, shortcuts=c.shortcuts)
+ return c.parser_manager
+
+# Case-sensitive ParserManager
+@pytest.fixture
+def cs_pm():
+ c = cmd2.Cmd()
+ c.multilineCommands = ['multiline']
+ c.case_insensitive = False
+ c.parser_manager = cmd2.ParserManager(redirector=c.redirector, terminators=c.terminators, multilineCommands=c.multilineCommands,
+ legalChars=c.legalChars, commentGrammars=c.commentGrammars,
+ commentInProgress=c.commentInProgress, case_insensitive=c.case_insensitive,
+ blankLinesAllowed=c.blankLinesAllowed, prefixParser=c.prefixParser,
+ preparse=c.preparse, postparse=c.postparse, shortcuts=c.shortcuts)
+ return c.parser_manager
+
+
@pytest.fixture
def input_parser():
c = cmd2.Cmd()
@@ -190,6 +218,18 @@ def test_parse_output_redirect_with_dash_in_path(parser):
assert results.output == '>'
assert results.outputTo == 'python-cmd2/afile.txt'
+
+def test_case_insensitive_parsed_single_word(ci_pm):
+ line = 'HeLp'
+ statement = ci_pm.parsed(line)
+ assert statement.parsed.command == line.lower()
+
+def test_case_sensitive_parsed_single_word(cs_pm):
+ line = 'HeLp'
+ statement = cs_pm.parsed(line)
+ assert statement.parsed.command == line
+
+
def test_parse_input_redirect(input_parser):
line = '< afile.txt'
results = input_parser.parseString(line)