fix(checkpoint): revive lc=2 JSON blobs for safe types without allowlist#7582
Merged
Sydney Runkle (sydney-runkle) merged 1 commit intoApr 27, 2026
Merged
Conversation
…without allowlist Old checkpoints written before the msgpack migration (pre-v1.0.1) stored LangChain messages and other safe types as lc=2 JSON constructor dicts. PR #6269 added an _allowed_json_modules security gate that defaults to None, causing _reviver to skip reconstruction and return raw dicts. Those raw dicts then reach add_messages → convert_to_messages → MESSAGE_COERCION_FAILURE. Fix: let _reviver reconstruct lc=2 blobs whose class is already in SAFE_MSGPACK_TYPES — the same curated safe-type list used by the msgpack path. This restores backwards-compat for pre-v1.0.1 threads without reopening the broader security gate for arbitrary classes. Fixes #7498 Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
William FH (hinthornw)
approved these changes
Apr 23, 2026
This was referenced Apr 27, 2026
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Summary
Fixes #7498 —
MESSAGE_COERCION_FAILUREwhen resuming threads checkpointed before v1.0.1.Root cause: PR #6269 (v1.0.1) added an
_allowed_json_modulessecurity gate toJsonPlusSerializer._reviver. The gate defaults toNone, so old"json"-format checkpoint blobs containinglc=2constructor dicts (the pre-msgpack serialization format for pydantic objects likeHumanMessage) are now returned as raw dicts instead of being reconstructed. Those raw dicts reachadd_messages → convert_to_messages, which seestype="constructor"and raisesMESSAGE_COERCION_FAILURE. Fresh first-turn messages are unaffected because currentdumps_typedonly writes"msgpack"blobs.Fix:
_revivernow reconstructslc=2blobs whose target class is already inSAFE_MSGPACK_TYPES— the same curated allowlist already used by the msgpack deserialization path (includes all standard LangChain message types). Unknown classes are still blocked, preserving the security intent of #6269.Changes
libs/checkpoint/langgraph/checkpoint/serde/jsonplus.py— add_is_safe_json_type()helper; update_reviverand_check_allowed_json_modulesto allow safe types without an explicit allowlistlibs/checkpoint/tests/test_jsonplus.py— two new regression tests: safe-typelc=2blobs revive correctly; unknown-typelc=2blobs stay blockedTest plan
test_lc2_json_safe_type_revives_without_allowlist—HumanMessage/AIMessagelc=2 JSON blobs round-trip to properBaseMessageobjects with no allowlist configuredtest_lc2_json_unknown_type_stays_blocked_without_allowlist—pprint.pprintlc=2 blob still returns raw dict (not reconstructed)test_deserde_invalid_module— existing behaviour unchangedtest_jsonplus.pysuite: 93/93 passing