TINKERPOP-3279 Restrict GraphSON 1.0 embedded-type deserialization - #3586
Draft
GumpacG wants to merge 2 commits into
Draft
TINKERPOP-3279 Restrict GraphSON 1.0 embedded-type deserialization#3586GumpacG wants to merge 2 commits into
GumpacG wants to merge 2 commits into
Conversation
Assisted-by: Kiro: Claude Opus 4.8
Codecov Report❌ Patch coverage is
Additional details and impacted files@@ Coverage Diff @@
## 3.7-dev #3586 +/- ##
=============================================
+ Coverage 75.49% 75.54% +0.04%
- Complexity 13161 13209 +48
=============================================
Files 1092 1093 +1
Lines 67208 67355 +147
Branches 7391 7419 +28
=============================================
+ Hits 50742 50884 +142
- Misses 13837 13850 +13
+ Partials 2629 2621 -8 ☔ View full report in Codecov by Harness. 🚀 New features to boost your workflow:
|
GumpacG
marked this pull request as draft
August 5, 2026 22:43
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
GraphSON 1.0 with embedded types (
TypeInfo.PARTIAL_TYPES) configured Jackson default typing withJsonTypeInfo.Id.CLASSand noPolymorphicTypeValidator. Reading a document reconstructed whatever class was named in its@classproperty, so a crafted document could name and construct (or merely load, running its staticinitializer) any class on the classpath. It is reachable pre-auth via the typed GraphSON 1.0 wire serializer
GraphSONMessageSerializerV1(application/vnd.gremlin-v1.0+json), and throughio()reads and GraphSON 1.0persistence. GraphSON 2.0/3.0 are unaffected: they resolve types through a fixed registry, not by arbitrary class name.
This change constrains that default typing while leaving legitimate value types working.
What changed
New API
GraphSONMapper.Builder.addAllowedTypeIdPrefix(String...)trusts additional class-name prefixes for GraphSON 1.0 embedded-type deserialization, in addition to the safe defaults. Intended for provider/application types read from trusted input.Hardened (GraphSON 1.0
PARTIAL_TYPESonly)PolymorphicTypeValidatordecides a simple type id from its name, so a disallowed class is refused invalidateSubClassNamebefore it is loaded (its static initializer never runs). Array descriptors are unwrapped and allowed only when the component type is allowed; primitive arrays are allowed.java.lang,java.util,java.math,java.time,java.sql,org.apache.tinkerpop, minus the network packagesjava.net/java.nio.java.net.InetAddressandjava.net.URI(string-backed, no DNS, unlikejava.net.URL).java.lang.Classis exact-denied even thoughjava.langis allowed, so ajava.lang.Classvalue cannot name and load an arbitrary class (Jackson would otherwise resolve it withinitialize=true).GraphSON1dScreeningIdResolverrefuses a parameterized type id (one containing<) before Jackson resolves it. This closes a bypass where a disallowed class hidden as a generic type argument was loaded before validation, and where enum type arguments were not validated at all (Jackson skips them). GraphSON 1.0 never emits a parameterized@class, so nothing legitimate is affected.Behavior change
A GraphSON 1.0 typed document whose
@classnames a type outside the allowed set now fails on read:Breaking changes and capability impact
Breaking: reading a GraphSON 1.0 typed document now fails, instead of deserializing, when its
@class:IoRegistry, an application POJO, mostjava.net.*/java.nio.*types),java.lang.Classused as a value, orA document written by an older version that embeds such a type may no longer be readable.
Restore a specific type for trusted input by trusting its package:
or migrate to GraphSON 3.0 / GraphBinary. Standard scalar, collection and array values,
java.math/java.time/java.sqlvalues,java.net.InetAddress/java.net.URI, and TinkerPop graph types are unaffected. The restrictiongates reads; the write path still emits
@classfor any type, so a writer and reader should be configured consistently. (java.nio.ByteBufferis written by V1 as a concrete subtype Jackson cannot reconstruct, so it was never round-trippable in V1 and remains refused on read.)Testing
GraphSONMapperPartialEmbeddedTypeTestcovers, on the default V1 mapper:@classis refused, and is not class-loaded (a static-init canary never fires);argument is refused (regression for the parameterized-id / enum bypass);
java.lang.Classvalue is refused and not loaded;java.net.URL) is refused, whilejava.net.InetAddressandjava.net.URIround-trip;java.sql/java.utilvalue types round-trip;addAllowedTypeIdPrefix(...)re-enables an otherwise-denied package.GraphSON 2.0/3.0 embedded-type and wire-serializer suites continue to pass unchanged.
Assisted-by: Kiro:claude-opus-4.8