summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorKevin Van Brunt <kmvanbrunt@gmail.com>2020-02-17 11:24:28 -0500
committerKevin Van Brunt <kmvanbrunt@gmail.com>2020-02-17 11:24:28 -0500
commit555db5d98fc122dc21d3bb239c079d68272cc0c3 (patch)
tree25f9041650716c5be91926da39af0b0ebaca853f
parentdb9c3a6d455e2bb19be7ae295c73a28751a7b481 (diff)
downloadcmd2-git-555db5d98fc122dc21d3bb239c079d68272cc0c3.tar.gz
Updated documentation and tests
-rw-r--r--CHANGELOG.md2
-rw-r--r--cmd2/cmd2.py4
-rwxr-xr-xtests/test_cmd2.py9
3 files changed, 13 insertions, 2 deletions
diff --git a/CHANGELOG.md b/CHANGELOG.md
index 18ac2348..4d662cf3 100644
--- a/CHANGELOG.md
+++ b/CHANGELOG.md
@@ -12,6 +12,8 @@
* Setting the following pyscript variables:
* `__name__`: __main__
* `__file__`: script path (as typed, ~ will be expanded)
+* Other
+ * Removed undocumented `py run` command since it was replaced by `run_pyscript` a while ago
## 0.10.0 (February 7, 2020)
* Enhancements
diff --git a/cmd2/cmd2.py b/cmd2/cmd2.py
index c7a0fa6d..3b1fbb6f 100644
--- a/cmd2/cmd2.py
+++ b/cmd2/cmd2.py
@@ -3120,7 +3120,9 @@ class Cmd(cmd.Cmd):
self._in_py = True
py_code_to_run = ''
- # Locals for the Python environment we are creating
+ # Use self.py_locals as the locals() dictionary in the Python environment we are creating, but make
+ # a copy to prevent pyscripts from editing it. (e.g. locals().clear()). Only make a shallow copy since
+ # it's OK for py_locals to contain objects which are editable in a pyscript.
localvars = dict(self.py_locals)
localvars[self.py_bridge_name] = py_bridge
localvars['quit'] = py_quit
diff --git a/tests/test_cmd2.py b/tests/test_cmd2.py
index 41528612..dc9a3fa1 100755
--- a/tests/test_cmd2.py
+++ b/tests/test_cmd2.py
@@ -206,7 +206,7 @@ def test_base_shell(base_app, monkeypatch):
def test_base_py(base_app):
# Make sure py can't edit Cmd.py_locals. It used to be that cmd2 was passing its py_locals
- # dictionary to the py environment instead of a copy.
+ # dictionary to the py environment instead of a shallow copy.
base_app.py_locals['test_var'] = 5
out, err = run_cmd(base_app, 'py del[locals()["test_var"]]')
assert not out and not err
@@ -215,6 +215,13 @@ def test_base_py(base_app):
out, err = run_cmd(base_app, 'py print(test_var)')
assert out[0].rstrip() == '5'
+ # Place an editable object in py_locals. Since we make a shallow copy of py_locals,
+ # this object should be editable from the py environment.
+ base_app.py_locals['my_list'] = []
+ out, err = run_cmd(base_app, 'py my_list.append(2)')
+ assert not out and not err
+ assert base_app.py_locals['my_list'][0] == 2
+
# Try a print statement
out, err = run_cmd(base_app, 'py print("spaces" + " in this " + "command")')
assert out[0].rstrip() == 'spaces in this command'