Skip to content

Fix Variable Explorer PicklingError for deeply nested objects#25706

Open
d-kavinraja wants to merge 2 commits intospyder-ide:masterfrom
d-kavinraja:fix/variable-explorer-pickling-error-25699
Open

Fix Variable Explorer PicklingError for deeply nested objects#25706
d-kavinraja wants to merge 2 commits intospyder-ide:masterfrom
d-kavinraja:fix/variable-explorer-pickling-error-25699

Conversation

@d-kavinraja
Copy link
Copy Markdown

Description

Fixes #25699 — Variable Explorer throws "An unknown error occurred, sorry" when clicking on lists, dictionaries, or Pandas DataFrames that require deep recursion to pickle.

Root Cause

A 3-layer failure in the error handling chain:

  1. Kernel side (kernel.py): cloudpickle.dumps(value) raises pickle.PicklingError for deeply nested structures with no fallback.
  2. Comm layer (commbase.py): from_json() reconstructs the error type using getattr(builtins, "PicklingError", ...). Since PicklingError is NOT in builtins, a dynamically-created class inheriting from Exception (not pickle.PicklingError) is created.
  3. Frontend (namespacebrowser.py): except (PicklingError, ...) catches pickle.PicklingError, but the dynamically-created class doesn't match, so the error falls through to the generic except Exception handler showing the unhelpful message.

Changes

1. commbase.py — Fix exception type reconstruction

from_json() now resolves exception types from well-known modules (pickle, _pickle) before falling back to builtins/dynamic creation. This ensures pickle.PicklingError raised in the kernel is properly reconstructed on the Spyder side.

2. kernel.py — Add recursion limit fallback

get_value() now catches PicklingError/RecursionError on the first pickle attempt and retries with a temporarily increased recursion limit (10x), allowing most normal objects (lists, dicts, DataFrames) that happen to be moderately deep to succeed.

3. namespacebrowser.py — Safety net in generic handler

The final except Exception block now checks the exception's class name. If it's PicklingError or UnpicklingError (even from a dynamically-created class), it shows the proper "not picklable" message instead of "unknown error."

@d-kavinraja d-kavinraja force-pushed the fix/variable-explorer-pickling-error-25699 branch from c0e68c3 to fa14491 Compare February 12, 2026 15:28
…-ide#25699)

Root cause: When cloudpickle.dumps() raises pickle.PicklingError in the
kernel for deeply nested lists/dicts/DataFrames, the comm layer
reconstructs the error as a dynamic Exception subclass (not
pickle.PicklingError), so the frontend's except handler misses it and
shows an unhelpful 'unknown error' message.

Changes:
- commbase.py: Resolve exception types from well-known modules (pickle,
  _pickle) in from_json() before falling back to builtins, so
  PicklingError is properly reconstructed as pickle.PicklingError.
- kernel.py: Catch PicklingError/RecursionError in get_value() and retry
  with a temporarily increased recursion limit (10x) before giving up.
- namespacebrowser.py: Add safety net in the generic except handler to
  detect PicklingError by class name and show a proper error message.

Fixes spyder-ide#25699
The test_goto_uri[params15] test case hardcoded
'spyder-ide#123' as the expected URL for
the 'spyder-idegh-123' shorthand. However, go_to_uri_from_cursor() computes this URL
dynamically from the repo's git remotes (preferring 'upstream' over
'origin'). When running on a fork, origin points to the fork, causing a
mismatch.

Fix: compute the expected URL at module level using the same
get_git_remotes + remote_to_url logic so the test works on any fork.
@ccordoba12
Copy link
Copy Markdown
Member

Hey @d-kavinraja, thanks for your contribution. Could you clarify if you used AI to create this pull request?

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

Variable Explorer Error For Certain Types on Arch Linux

2 participants