Skip to content

Commit

Permalink
Don't call frame.f_locals multiple times when assigning locals after …
Browse files Browse the repository at this point in the history
…evaluation. Fixes #915
  • Loading branch information
fabioz committed Apr 22, 2022
1 parent 7be5993 commit 6174f4c
Show file tree
Hide file tree
Showing 2 changed files with 22 additions and 4 deletions.
12 changes: 8 additions & 4 deletions src/debugpy/_vendored/pydevd/_pydevd_bundle/pydevd_vars.py
Original file line number Diff line number Diff line change
Expand Up @@ -377,13 +377,17 @@ def _update_globals_and_locals(updated_globals, initial_globals, frame):
# Still, the approach to have a single namespace was chosen because it was the only
# one that enabled creating and using variables during the same evaluation.
assert updated_globals is not None
changed = False
f_locals = None
for key, val in updated_globals.items():
if initial_globals.get(key) is not val:
changed = True
frame.f_locals[key] = val
if f_locals is None:
# Note: we call f_locals only once because each time
# we call it the values may be reset.
f_locals = frame.f_locals

if changed:
f_locals[key] = val

if f_locals is not None:
pydevd_save_locals.save_locals(frame)


Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -9,6 +9,8 @@


def obtain_frame():
A = 1
B = 2
yield sys._getframe()


Expand Down Expand Up @@ -116,3 +118,15 @@ def check(frame):
assert 'email' in sys._getframe().f_globals
del sys._getframe().f_globals['email']
assert 'email' not in sys._getframe().f_globals


def test_evaluate_expression_5(disable_critical_log):
from _pydevd_bundle.pydevd_vars import evaluate_expression

def check(frame):
eval_txt = 'A, B = 5, 6'
evaluate_expression(None, frame, eval_txt, is_exec=True)
assert frame.f_locals['A'] == 5
assert frame.f_locals['B'] == 6

check(next(iter(obtain_frame())))

0 comments on commit 6174f4c

Please sign in to comment.