You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@tinkerpop.apache.org by co...@apache.org on 2023/07/17 22:25:15 UTC

[tinkerpop] branch master updated (30df50200f -> 4cdddebc30)

This is an automated email from the ASF dual-hosted git repository.

colegreer pushed a change to branch master
in repository https://gitbox.apache.org/repos/asf/tinkerpop.git


    from 30df50200f Merge branch '3.6-dev'
     add 08559317c7 TINKERPOP-2948 bump jackson databind to 2.15.0 (#2139)
     add 1f99a0a7de Merge branch '3.5-dev' into 3.6-dev
     new 4cdddebc30 Merge branch '3.6-dev'

The 1 revisions listed above as "new" are entirely new to this
repository and will be described in separate emails.  The revisions
listed as "add" were already present in the repository and have only
been added to this reference.


Summary of changes:
 CHANGELOG.asciidoc                                 |  2 +
 docs/src/upgrade/release-3.5.x.asciidoc            | 14 ++++
 .../structure/io/graphson/GraphSONMapper.java      | 25 +++++-
 .../io/graphson/GraphSONStreamConstraintsTest.java | 93 ++++++++++++++++++++++
 .../gremlin/driver/ClusterConfigTest.java          | 72 +++++++++++++++++
 gremlin-shaded/pom.xml                             |  2 +-
 .../ser/AbstractGraphSONMessageSerializerV1.java   | 16 ++++
 .../ser/AbstractGraphSONMessageSerializerV2.java   | 16 ++++
 .../AbstractGraphSONMessageSerializerV1Test.java   | 53 ++++++++++++
 .../AbstractGraphSONMessageSerializerV2Test.java   | 53 ++++++++++++
 pom.xml                                            |  5 +-
 11 files changed, 348 insertions(+), 3 deletions(-)
 create mode 100644 gremlin-core/src/test/java/org/apache/tinkerpop/gremlin/structure/io/graphson/GraphSONStreamConstraintsTest.java
 create mode 100644 gremlin-driver/src/test/java/org/apache/tinkerpop/gremlin/driver/ClusterConfigTest.java
 create mode 100644 gremlin-util/src/test/java/org/apache/tinkerpop/gremlin/util/ser/AbstractGraphSONMessageSerializerV1Test.java
 create mode 100644 gremlin-util/src/test/java/org/apache/tinkerpop/gremlin/util/ser/AbstractGraphSONMessageSerializerV2Test.java


[tinkerpop] 01/01: Merge branch '3.6-dev'

Posted by co...@apache.org.
This is an automated email from the ASF dual-hosted git repository.

colegreer pushed a commit to branch master
in repository https://gitbox.apache.org/repos/asf/tinkerpop.git

commit 4cdddebc304cf6d0471a5b724b54ede8a2297611
Merge: 30df50200f 1f99a0a7de
Author: Cole-Greer <Co...@improving.com>
AuthorDate: Mon Jul 17 15:25:02 2023 -0700

    Merge branch '3.6-dev'

 CHANGELOG.asciidoc                                 |  2 +
 docs/src/upgrade/release-3.5.x.asciidoc            | 14 ++++
 .../structure/io/graphson/GraphSONMapper.java      | 25 +++++-
 .../io/graphson/GraphSONStreamConstraintsTest.java | 93 ++++++++++++++++++++++
 .../gremlin/driver/ClusterConfigTest.java          | 72 +++++++++++++++++
 gremlin-shaded/pom.xml                             |  2 +-
 .../ser/AbstractGraphSONMessageSerializerV1.java   | 16 ++++
 .../ser/AbstractGraphSONMessageSerializerV2.java   | 16 ++++
 .../AbstractGraphSONMessageSerializerV1Test.java   | 53 ++++++++++++
 .../AbstractGraphSONMessageSerializerV2Test.java   | 53 ++++++++++++
 pom.xml                                            |  5 +-
 11 files changed, 348 insertions(+), 3 deletions(-)

diff --cc gremlin-driver/src/test/java/org/apache/tinkerpop/gremlin/driver/ClusterConfigTest.java
index 0000000000,4e47684dd7..03b8fce75c
mode 000000,100644..100644
--- a/gremlin-driver/src/test/java/org/apache/tinkerpop/gremlin/driver/ClusterConfigTest.java
+++ b/gremlin-driver/src/test/java/org/apache/tinkerpop/gremlin/driver/ClusterConfigTest.java
@@@ -1,0 -1,72 +1,72 @@@
+ /*
+  * Licensed to the Apache Software Foundation (ASF) under one
+  * or more contributor license agreements.  See the NOTICE file
+  * distributed with this work for additional information
+  * regarding copyright ownership.  The ASF licenses this file
+  * to you under the Apache License, Version 2.0 (the
+  * "License"); you may not use this file except in compliance
+  * with the License.  You may obtain a copy of the License at
+  *
+  * http://www.apache.org/licenses/LICENSE-2.0
+  *
+  * Unless required by applicable law or agreed to in writing,
+  * software distributed under the License is distributed on an
+  * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+  * KIND, either express or implied.  See the License for the
+  * specific language governing permissions and limitations
+  * under the License.
+  */
+ package org.apache.tinkerpop.gremlin.driver;
+ 
+ import org.apache.commons.configuration2.BaseConfiguration;
+ import org.apache.commons.configuration2.Configuration;
 -import org.apache.tinkerpop.gremlin.driver.ser.GraphSONMessageSerializerV2d0;
 -import org.apache.tinkerpop.gremlin.driver.ser.GraphSONMessageSerializerV3d0;
++import org.apache.tinkerpop.gremlin.util.ser.GraphSONMessageSerializerV2;
++import org.apache.tinkerpop.gremlin.util.ser.GraphSONMessageSerializerV3;
+ import org.apache.tinkerpop.shaded.jackson.core.StreamReadConstraints;
+ import org.junit.Test;
+ 
+ import java.util.Arrays;
+ 
+ import static org.junit.Assert.assertEquals;
+ import static org.junit.Assert.assertTrue;
+ 
+ public class ClusterConfigTest {
+ 
+     @Test
+     public void shouldPropagateSerializerConstraintsForGraphSON3() {
+         final Configuration config = new BaseConfiguration();
+         config.setProperty("serializer.config.maxNumberLength", 999);
+         config.setProperty("serializer.config.maxStringLength", 123456);
+         config.setProperty("serializer.config.maxNestingDepth", 55);
+         config.setProperty("hosts", Arrays.asList("localhost"));
+ 
 -        config.setProperty("serializer.className", GraphSONMessageSerializerV3d0.class.getCanonicalName());
++        config.setProperty("serializer.className", GraphSONMessageSerializerV3.class.getCanonicalName());
+         final Cluster cluster = Cluster.open(config);
 -        assertTrue(cluster.getSerializer() instanceof GraphSONMessageSerializerV3d0);
 -        final GraphSONMessageSerializerV3d0 serV3 = (GraphSONMessageSerializerV3d0) cluster.getSerializer();
++        assertTrue(cluster.getSerializer() instanceof GraphSONMessageSerializerV3);
++        final GraphSONMessageSerializerV3 serV3 = (GraphSONMessageSerializerV3) cluster.getSerializer();
+         final StreamReadConstraints constraints = serV3.getMapper().getFactory().streamReadConstraints();
+ 
+         assertEquals(999, constraints.getMaxNumberLength());
+         assertEquals(123456, constraints.getMaxStringLength());
+         assertEquals(55, constraints.getMaxNestingDepth());
+     }
+ 
+     @Test
+     public void shouldPropagateSerializerConstraintsForGraphSON2() {
+         final Configuration config = new BaseConfiguration();
+         config.setProperty("serializer.config.maxNumberLength", 999);
+         config.setProperty("serializer.config.maxStringLength", 123456);
+         config.setProperty("serializer.config.maxNestingDepth", 55);
+         config.setProperty("hosts", Arrays.asList("localhost"));
+ 
 -        config.setProperty("serializer.className", GraphSONMessageSerializerV2d0.class.getCanonicalName());
++        config.setProperty("serializer.className", GraphSONMessageSerializerV2.class.getCanonicalName());
+         final Cluster cluster = Cluster.open(config);
 -        assertTrue(cluster.getSerializer() instanceof GraphSONMessageSerializerV2d0);
 -        final GraphSONMessageSerializerV2d0 serV2 = (GraphSONMessageSerializerV2d0) cluster.getSerializer();
++        assertTrue(cluster.getSerializer() instanceof GraphSONMessageSerializerV2);
++        final GraphSONMessageSerializerV2 serV2 = (GraphSONMessageSerializerV2) cluster.getSerializer();
+         final StreamReadConstraints constraints = serV2.getMapper().getFactory().streamReadConstraints();
+ 
+         assertEquals(999, constraints.getMaxNumberLength());
+         assertEquals(123456, constraints.getMaxStringLength());
+         assertEquals(55, constraints.getMaxNestingDepth());
+     }
+ }
diff --cc gremlin-util/src/main/java/org/apache/tinkerpop/gremlin/util/ser/AbstractGraphSONMessageSerializerV1.java
index 0252d4da99,0000000000..66fe869b98
mode 100644,000000..100644
--- a/gremlin-util/src/main/java/org/apache/tinkerpop/gremlin/util/ser/AbstractGraphSONMessageSerializerV1.java
+++ b/gremlin-util/src/main/java/org/apache/tinkerpop/gremlin/util/ser/AbstractGraphSONMessageSerializerV1.java
@@@ -1,213 -1,0 +1,229 @@@
 +/*
 + * Licensed to the Apache Software Foundation (ASF) under one
 + * or more contributor license agreements.  See the NOTICE file
 + * distributed with this work for additional information
 + * regarding copyright ownership.  The ASF licenses this file
 + * to you under the Apache License, Version 2.0 (the
 + * "License"); you may not use this file except in compliance
 + * with the License.  You may obtain a copy of the License at
 + *
 + * http://www.apache.org/licenses/LICENSE-2.0
 + *
 + * Unless required by applicable law or agreed to in writing,
 + * software distributed under the License is distributed on an
 + * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
 + * KIND, either express or implied.  See the License for the
 + * specific language governing permissions and limitations
 + * under the License.
 + */
 +package org.apache.tinkerpop.gremlin.util.ser;
 +
 +import org.apache.tinkerpop.gremlin.util.message.RequestMessage;
 +import org.apache.tinkerpop.gremlin.util.message.ResponseMessage;
 +import org.apache.tinkerpop.gremlin.util.message.ResponseStatusCode;
 +import org.apache.tinkerpop.gremlin.structure.Graph;
 +import org.apache.tinkerpop.gremlin.structure.io.graphson.GraphSONMapper;
 +import io.netty.buffer.ByteBuf;
 +import io.netty.buffer.ByteBufAllocator;
 +import io.netty.util.ReferenceCountUtil;
 +import org.apache.tinkerpop.gremlin.structure.io.graphson.GraphSONTokens;
 +import org.apache.tinkerpop.gremlin.structure.io.graphson.GraphSONUtil;
 +import org.apache.tinkerpop.gremlin.structure.io.graphson.GraphSONVersion;
 +import org.apache.tinkerpop.shaded.jackson.core.JsonGenerationException;
 +import org.apache.tinkerpop.shaded.jackson.core.JsonGenerator;
 +import org.apache.tinkerpop.shaded.jackson.core.JsonProcessingException;
 +import org.apache.tinkerpop.shaded.jackson.core.type.TypeReference;
 +import org.apache.tinkerpop.shaded.jackson.databind.ObjectMapper;
 +import org.apache.tinkerpop.shaded.jackson.databind.SerializerProvider;
 +import org.apache.tinkerpop.shaded.jackson.databind.jsontype.TypeSerializer;
 +import org.apache.tinkerpop.shaded.jackson.databind.module.SimpleModule;
 +import org.apache.tinkerpop.shaded.jackson.databind.ser.std.StdSerializer;
 +import org.slf4j.Logger;
 +import org.slf4j.LoggerFactory;
 +
 +import java.io.IOException;
 +import java.util.HashMap;
 +import java.util.Map;
 +import java.util.UUID;
 +
 +/**
 + * @author Stephen Mallette (http://stephen.genoprime.com)
 + */
 +public abstract class AbstractGraphSONMessageSerializerV1 extends AbstractMessageSerializer<ObjectMapper> {
 +    private static final Logger logger = LoggerFactory.getLogger(AbstractGraphSONMessageSerializerV1.class);
 +
 +    protected ObjectMapper mapper;
 +
 +    protected final TypeReference<Map<String, Object>> mapTypeReference = new TypeReference<Map<String, Object>>() {
 +    };
 +
 +    public AbstractGraphSONMessageSerializerV1() {
 +        final GraphSONMapper.Builder builder = configureBuilder(initBuilder(null));
 +        mapper = builder.create().createMapper();
 +    }
 +
 +    public AbstractGraphSONMessageSerializerV1(final GraphSONMapper mapper) {
 +        this.mapper = mapper.createMapper();
 +    }
 +
 +    abstract byte[] obtainHeader();
 +
 +    abstract GraphSONMapper.Builder configureBuilder(final GraphSONMapper.Builder builder);
 +
 +    @Override
 +    public void configure(final Map<String, Object> config, final Map<String, Graph> graphs) {
 +        final GraphSONMapper.Builder initialBuilder = initBuilder(null);
 +        addIoRegistries(config, initialBuilder);
++        applyMaxTokenLimits(initialBuilder, config);
 +        mapper = configureBuilder(initialBuilder).create().createMapper();
 +    }
 +
 +    @Override
 +    public ByteBuf serializeResponseAsBinary(final ResponseMessage responseMessage, final ByteBufAllocator allocator) throws SerializationException {
 +        ByteBuf encodedMessage = null;
 +        try {
 +            final byte[] payload = mapper.writeValueAsBytes(responseMessage);
 +            encodedMessage = allocator.buffer(payload.length);
 +            encodedMessage.writeBytes(payload);
 +
 +            return encodedMessage;
 +        } catch (Exception ex) {
 +            if (encodedMessage != null) ReferenceCountUtil.release(encodedMessage);
 +
 +            logger.warn("Response [{}] could not be serialized by {}.", responseMessage.toString(), AbstractGraphSONMessageSerializerV1.class.getName());
 +            throw new SerializationException(ex);
 +        }
 +    }
 +
 +    @Override
 +    public ByteBuf serializeRequestAsBinary(final RequestMessage requestMessage, final ByteBufAllocator allocator) throws SerializationException {
 +        ByteBuf encodedMessage = null;
 +        try {
 +            final byte[] header = obtainHeader();
 +            final byte[] payload = mapper.writeValueAsBytes(requestMessage);
 +
 +            encodedMessage = allocator.buffer(header.length + payload.length);
 +            encodedMessage.writeBytes(header);
 +            encodedMessage.writeBytes(payload);
 +
 +            return encodedMessage;
 +        } catch (Exception ex) {
 +            if (encodedMessage != null) ReferenceCountUtil.release(encodedMessage);
 +
 +            logger.warn("Request [{}] could not be serialized by {}.", requestMessage.toString(), AbstractGraphSONMessageSerializerV1.class.getName());
 +            throw new SerializationException(ex);
 +        }
 +    }
 +
 +    @Override
 +    public RequestMessage deserializeRequest(final ByteBuf msg) throws SerializationException {
 +        try {
 +            final byte[] payload = new byte[msg.readableBytes()];
 +            msg.readBytes(payload);
 +            return mapper.readValue(payload, RequestMessage.class);
 +        } catch (Exception ex) {
 +            logger.warn("Request [{}] could not be deserialized by {}.", msg, AbstractGraphSONMessageSerializerV1.class.getName());
 +            throw new SerializationException(ex);
 +        }
 +    }
 +
 +    @Override
 +    public ResponseMessage deserializeResponse(final ByteBuf msg) throws SerializationException {
 +        try {
 +            final byte[] payload = new byte[msg.readableBytes()];
 +            msg.readBytes(payload);
 +            final Map<String, Object> responseData = mapper.readValue(payload, mapTypeReference);
 +            final Map<String, Object> status = (Map<String, Object>) responseData.get(SerTokens.TOKEN_STATUS);
 +            final Map<String, Object> result = (Map<String, Object>) responseData.get(SerTokens.TOKEN_RESULT);
 +            return ResponseMessage.build(UUID.fromString(responseData.get(SerTokens.TOKEN_REQUEST).toString()))
 +                    .code(ResponseStatusCode.getFromValue((Integer) status.get(SerTokens.TOKEN_CODE)))
 +                    .statusMessage(String.valueOf(status.get(SerTokens.TOKEN_MESSAGE)))
 +                    .statusAttributes((Map<String, Object>) status.get(SerTokens.TOKEN_ATTRIBUTES))
 +                    .result(result.get(SerTokens.TOKEN_DATA))
 +                    .responseMetaData((Map<String, Object>) result.get(SerTokens.TOKEN_META))
 +                    .create();
 +        } catch (Exception ex) {
 +            logger.warn("Response [{}] could not be deserialized by {}.", msg, AbstractGraphSONMessageSerializerV1.class.getName());
 +            throw new SerializationException(ex);
 +        }
 +    }
 +
 +    private GraphSONMapper.Builder initBuilder(final GraphSONMapper.Builder builder) {
 +        final GraphSONMapper.Builder b = null == builder ? GraphSONMapper.build() : builder;
 +        return b.addCustomModule(new AbstractGraphSONMessageSerializerV1.GremlinServerModule())
 +                .version(GraphSONVersion.V1_0);
 +    }
 +
++    private GraphSONMapper.Builder applyMaxTokenLimits(final GraphSONMapper.Builder builder, final Map<String, Object> config) {
++        if(config != null) {
++            if(config.containsKey("maxNumberLength")) {
++                builder.maxNumberLength((int)config.get("maxNumberLength"));
++            }
++            if(config.containsKey("maxStringLength")) {
++                builder.maxStringLength((int)config.get("maxStringLength"));
++            }
++            if(config.containsKey("maxNestingDepth")) {
++                builder.maxNestingDepth((int)config.get("maxNestingDepth"));
++            }
++        }
++        return builder;
++    }
++
 +    @Override
 +    public ObjectMapper getMapper() {
 +        return this.mapper;
 +    }
 +
 +    public final static class GremlinServerModule extends SimpleModule {
 +        public GremlinServerModule() {
 +            super("graphson-gremlin-server");
 +            addSerializer(ResponseMessage.class, new ResponseMessageSerializer());
 +        }
 +    }
 +
 +    public final static class ResponseMessageSerializer extends StdSerializer<ResponseMessage> {
 +        public ResponseMessageSerializer() {
 +            super(ResponseMessage.class);
 +        }
 +
 +        @Override
 +        public void serialize(final ResponseMessage responseMessage, final JsonGenerator jsonGenerator,
 +                              final SerializerProvider serializerProvider) throws IOException, JsonGenerationException {
 +            ser(responseMessage, jsonGenerator, serializerProvider, null);
 +        }
 +
 +        @Override
 +        public void serializeWithType(final ResponseMessage responseMessage, final JsonGenerator jsonGenerator,
 +                                      final SerializerProvider serializerProvider,
 +                                      final TypeSerializer typeSerializer) throws IOException, JsonProcessingException {
 +            ser(responseMessage, jsonGenerator, serializerProvider, typeSerializer);
 +        }
 +
 +        public void ser(final ResponseMessage responseMessage, final JsonGenerator jsonGenerator,
 +                        final SerializerProvider serializerProvider,
 +                        final TypeSerializer typeSerializer) throws IOException, JsonProcessingException {
 +            jsonGenerator.writeStartObject();
 +            if (typeSerializer != null) jsonGenerator.writeStringField(GraphSONTokens.CLASS, HashMap.class.getName());
 +
 +            jsonGenerator.writeStringField(SerTokens.TOKEN_REQUEST, responseMessage.getRequestId() != null ? responseMessage.getRequestId().toString() : null);
 +            jsonGenerator.writeObjectFieldStart(SerTokens.TOKEN_STATUS);
 +
 +            if (typeSerializer != null) jsonGenerator.writeStringField(GraphSONTokens.CLASS, HashMap.class.getName());
 +            jsonGenerator.writeStringField(SerTokens.TOKEN_MESSAGE, responseMessage.getStatus().getMessage());
 +            jsonGenerator.writeNumberField(SerTokens.TOKEN_CODE, responseMessage.getStatus().getCode().getValue());
 +            jsonGenerator.writeObjectField(SerTokens.TOKEN_ATTRIBUTES, responseMessage.getStatus().getAttributes());
 +            jsonGenerator.writeEndObject();
 +
 +            jsonGenerator.writeObjectFieldStart(SerTokens.TOKEN_RESULT);
 +            if (typeSerializer != null) jsonGenerator.writeStringField(GraphSONTokens.CLASS, HashMap.class.getName());
 +            if (null == responseMessage.getResult().getData())
 +                jsonGenerator.writeNullField(SerTokens.TOKEN_DATA);
 +            else
 +                GraphSONUtil.writeWithType(SerTokens.TOKEN_DATA, responseMessage.getResult().getData(), jsonGenerator, serializerProvider, typeSerializer);
 +            jsonGenerator.writeObjectField(SerTokens.TOKEN_META, responseMessage.getResult().getMeta());
 +            jsonGenerator.writeEndObject();
 +
 +            jsonGenerator.writeEndObject();
 +        }
 +    }
 +}
diff --cc gremlin-util/src/main/java/org/apache/tinkerpop/gremlin/util/ser/AbstractGraphSONMessageSerializerV2.java
index 5049c902c2,0000000000..521a4260f0
mode 100644,000000..100644
--- a/gremlin-util/src/main/java/org/apache/tinkerpop/gremlin/util/ser/AbstractGraphSONMessageSerializerV2.java
+++ b/gremlin-util/src/main/java/org/apache/tinkerpop/gremlin/util/ser/AbstractGraphSONMessageSerializerV2.java
@@@ -1,290 -1,0 +1,306 @@@
 +/*
 + * Licensed to the Apache Software Foundation (ASF) under one
 + * or more contributor license agreements.  See the NOTICE file
 + * distributed with this work for additional information
 + * regarding copyright ownership.  The ASF licenses this file
 + * to you under the Apache License, Version 2.0 (the
 + * "License"); you may not use this file except in compliance
 + * with the License.  You may obtain a copy of the License at
 + *
 + * http://www.apache.org/licenses/LICENSE-2.0
 + *
 + * Unless required by applicable law or agreed to in writing,
 + * software distributed under the License is distributed on an
 + * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
 + * KIND, either express or implied.  See the License for the
 + * specific language governing permissions and limitations
 + * under the License.
 + */
 +package org.apache.tinkerpop.gremlin.util.ser;
 +
 +import io.netty.buffer.ByteBuf;
 +import io.netty.buffer.ByteBufAllocator;
 +import io.netty.util.ReferenceCountUtil;
 +import org.apache.tinkerpop.gremlin.util.message.RequestMessage;
 +import org.apache.tinkerpop.gremlin.util.message.ResponseMessage;
 +import org.apache.tinkerpop.gremlin.util.message.ResponseStatusCode;
 +import org.apache.tinkerpop.gremlin.structure.Graph;
 +import org.apache.tinkerpop.gremlin.structure.io.graphson.AbstractObjectDeserializer;
 +import org.apache.tinkerpop.gremlin.structure.io.graphson.GraphSONMapper;
 +import org.apache.tinkerpop.gremlin.structure.io.graphson.GraphSONUtil;
 +import org.apache.tinkerpop.gremlin.structure.io.graphson.GraphSONVersion;
 +import org.apache.tinkerpop.gremlin.structure.io.graphson.GraphSONXModuleV2;
 +import org.apache.tinkerpop.shaded.jackson.core.JsonGenerator;
 +import org.apache.tinkerpop.shaded.jackson.databind.ObjectMapper;
 +import org.apache.tinkerpop.shaded.jackson.databind.SerializerProvider;
 +import org.apache.tinkerpop.shaded.jackson.databind.jsontype.TypeSerializer;
 +import org.apache.tinkerpop.shaded.jackson.databind.module.SimpleModule;
 +import org.apache.tinkerpop.shaded.jackson.databind.ser.std.StdSerializer;
 +import org.slf4j.Logger;
 +import org.slf4j.LoggerFactory;
 +
 +import java.io.IOException;
 +import java.util.Map;
 +import java.util.UUID;
 +
 +/**
 + * @author Stephen Mallette (http://stephen.genoprime.com)
 + */
 +public abstract class AbstractGraphSONMessageSerializerV2 extends AbstractMessageSerializer<ObjectMapper> {
 +    private static final Logger logger = LoggerFactory.getLogger(AbstractGraphSONMessageSerializerV2.class);
 +
 +    protected ObjectMapper mapper;
 +
 +    public AbstractGraphSONMessageSerializerV2() {
 +        final GraphSONMapper.Builder builder = configureBuilder(initBuilder(null));
 +        mapper = builder.create().createMapper();
 +    }
 +
 +    @Deprecated
 +    public AbstractGraphSONMessageSerializerV2(final GraphSONMapper mapper) {
 +        this.mapper = mapper.createMapper();
 +    }
 +
 +    public AbstractGraphSONMessageSerializerV2(final GraphSONMapper.Builder mapperBuilder) {
 +        this.mapper = configureBuilder(mapperBuilder).create().createMapper();
 +    }
 +
 +    abstract byte[] obtainHeader();
 +
 +    abstract GraphSONMapper.Builder configureBuilder(final GraphSONMapper.Builder builder);
 +
 +    @Override
 +    public void configure(final Map<String, Object> config, final Map<String, Graph> graphs) {
 +        final GraphSONMapper.Builder initialBuilder = initBuilder(null);
 +        addIoRegistries(config, initialBuilder);
++        applyMaxTokenLimits(initialBuilder, config);
 +        mapper = configureBuilder(initialBuilder).create().createMapper();
 +    }
 +
 +    @Override
 +    public ByteBuf serializeResponseAsBinary(final ResponseMessage responseMessage, final ByteBufAllocator allocator) throws SerializationException {
 +        ByteBuf encodedMessage = null;
 +        try {
 +            final byte[] payload = mapper.writeValueAsBytes(responseMessage);
 +            encodedMessage = allocator.buffer(payload.length);
 +            encodedMessage.writeBytes(payload);
 +
 +            return encodedMessage;
 +        } catch (Exception ex) {
 +            if (encodedMessage != null) ReferenceCountUtil.release(encodedMessage);
 +
 +            logger.warn(String.format("Response [%s] could not be serialized by %s.", responseMessage, AbstractGraphSONMessageSerializerV2.class.getName()), ex);
 +            throw new SerializationException(ex);
 +        }
 +    }
 +
 +    @Override
 +    public ByteBuf serializeRequestAsBinary(final RequestMessage requestMessage, final ByteBufAllocator allocator) throws SerializationException {
 +        ByteBuf encodedMessage = null;
 +        try {
 +            final byte[] header = obtainHeader();
 +            final byte[] payload = mapper.writeValueAsBytes(requestMessage);
 +
 +            encodedMessage = allocator.buffer(header.length + payload.length);
 +            encodedMessage.writeBytes(header);
 +            encodedMessage.writeBytes(payload);
 +
 +            return encodedMessage;
 +        } catch (Exception ex) {
 +            if (encodedMessage != null) ReferenceCountUtil.release(encodedMessage);
 +
 +            logger.warn(String.format("Request [%s] could not be serialized by %s.", requestMessage, AbstractGraphSONMessageSerializerV2.class.getName()), ex);
 +            throw new SerializationException(ex);
 +        }
 +    }
 +
 +    @Override
 +    public RequestMessage deserializeRequest(final ByteBuf msg) throws SerializationException {
 +        try {
 +            final byte[] payload = new byte[msg.readableBytes()];
 +            msg.readBytes(payload);
 +            return mapper.readValue(payload, RequestMessage.class);
 +        } catch (Exception ex) {
 +            logger.warn(String.format("Request [%s] could not be deserialized by %s.", msg, AbstractGraphSONMessageSerializerV2.class.getName()), ex);
 +            throw new SerializationException(ex);
 +        }
 +    }
 +
 +    @Override
 +    public ResponseMessage deserializeResponse(final ByteBuf msg) throws SerializationException {
 +        try {
 +            final byte[] payload = new byte[msg.readableBytes()];
 +            msg.readBytes(payload);
 +            return mapper.readValue(payload, ResponseMessage.class);
 +        } catch (Exception ex) {
 +            logger.warn(String.format("Response [%s] could not be deserialized by %s.", msg, AbstractGraphSONMessageSerializerV2.class.getName()), ex);
 +            throw new SerializationException(ex);
 +        }
 +    }
 +
 +    private GraphSONMapper.Builder initBuilder(final GraphSONMapper.Builder builder) {
 +        final GraphSONMapper.Builder b = null == builder ? GraphSONMapper.build() : builder;
 +        return b.addCustomModule(GraphSONXModuleV2.build().create(false))
 +                .version(GraphSONVersion.V2_0);
 +    }
 +
++    private GraphSONMapper.Builder applyMaxTokenLimits(final GraphSONMapper.Builder builder, final Map<String, Object> config) {
++        if(config != null) {
++            if(config.containsKey("maxNumberLength")) {
++                builder.maxNumberLength((int)config.get("maxNumberLength"));
++            }
++            if(config.containsKey("maxStringLength")) {
++                builder.maxStringLength((int)config.get("maxStringLength"));
++            }
++            if(config.containsKey("maxNestingDepth")) {
++                builder.maxNestingDepth((int)config.get("maxNestingDepth"));
++            }
++        }
++        return builder;
++    }
++
 +    @Override
 +    public ObjectMapper getMapper() {
 +        return this.mapper;
 +    }
 +
 +    public final static class GremlinServerModule extends SimpleModule {
 +        public GremlinServerModule() {
 +            super("graphson-gremlin-server");
 +
 +            // SERIALIZERS
 +            addSerializer(ResponseMessage.class, new ResponseMessageSerializer());
 +            addSerializer(RequestMessage.class, new RequestMessageSerializer());
 +
 +            //DESERIALIZERS
 +            addDeserializer(ResponseMessage.class, new ResponseMessageDeserializer());
 +            addDeserializer(RequestMessage.class, new RequestMessageDeserializer());
 +        }
 +    }
 +
 +    public final static class RequestMessageSerializer extends StdSerializer<RequestMessage> {
 +        public RequestMessageSerializer() {
 +            super(RequestMessage.class);
 +        }
 +
 +        @Override
 +        public void serialize(final RequestMessage requestMessage, final JsonGenerator jsonGenerator,
 +                              final SerializerProvider serializerProvider) throws IOException {
 +            ser(requestMessage, jsonGenerator, serializerProvider, null);
 +        }
 +
 +        @Override
 +        public void serializeWithType(final RequestMessage requestMessage, final JsonGenerator jsonGenerator,
 +                                      final SerializerProvider serializerProvider,
 +                                      final TypeSerializer typeSerializer) throws IOException {
 +            ser(requestMessage, jsonGenerator, serializerProvider, typeSerializer);
 +        }
 +
 +        public void ser(final RequestMessage requestMessage, final JsonGenerator jsonGenerator,
 +                        final SerializerProvider serializerProvider,
 +                        final TypeSerializer typeSerializer) throws IOException {
 +            GraphSONUtil.writeStartObject(requestMessage, jsonGenerator, typeSerializer);
 +
 +            jsonGenerator.writeStringField(SerTokens.TOKEN_REQUEST, requestMessage.getRequestId().toString());
 +            jsonGenerator.writeStringField(SerTokens.TOKEN_OP, requestMessage.getOp());
 +            jsonGenerator.writeStringField(SerTokens.TOKEN_PROCESSOR, requestMessage.getProcessor());
 +            jsonGenerator.writeObjectField(SerTokens.TOKEN_ARGS, requestMessage.getArgs());
 +
 +            GraphSONUtil.writeEndObject(requestMessage, jsonGenerator, typeSerializer);
 +        }
 +    }
 +
 +    public final static class RequestMessageDeserializer extends AbstractObjectDeserializer<RequestMessage> {
 +        protected RequestMessageDeserializer() {
 +            super(RequestMessage.class);
 +        }
 +
 +        @Override
 +        public RequestMessage createObject(final Map<String, Object> data) {
 +            final Map<String, Object> args = (Map<String, Object>) data.get(SerTokens.TOKEN_ARGS);
 +            RequestMessage.Builder builder = RequestMessage.build(data.get(SerTokens.TOKEN_OP).toString())
 +                    .overrideRequestId(UUID.fromString(data.get(SerTokens.TOKEN_REQUEST).toString()));
 +
 +            if (data.containsKey(SerTokens.TOKEN_PROCESSOR))
 +                builder = builder.processor(data.get(SerTokens.TOKEN_PROCESSOR).toString());
 +
 +            if (args != null) {
 +                for (Map.Entry<String, Object> kv : args.entrySet()) {
 +                    builder = builder.addArg(kv.getKey(), kv.getValue());
 +                }
 +            }
 +
 +            return builder.create();
 +        }
 +    }
 +
 +    public final static class ResponseMessageSerializer extends StdSerializer<ResponseMessage> {
 +        public ResponseMessageSerializer() {
 +            super(ResponseMessage.class);
 +        }
 +
 +        @Override
 +        public void serialize(final ResponseMessage responseMessage, final JsonGenerator jsonGenerator,
 +                              final SerializerProvider serializerProvider) throws IOException {
 +            ser(responseMessage, jsonGenerator, serializerProvider, null);
 +        }
 +
 +        @Override
 +        public void serializeWithType(final ResponseMessage responseMessage, final JsonGenerator jsonGenerator,
 +                                      final SerializerProvider serializerProvider,
 +                                      final TypeSerializer typeSerializer) throws IOException {
 +            ser(responseMessage, jsonGenerator, serializerProvider, typeSerializer);
 +        }
 +
 +        public void ser(final ResponseMessage responseMessage, final JsonGenerator jsonGenerator,
 +                        final SerializerProvider serializerProvider,
 +                        final TypeSerializer typeSerializer) throws IOException {
 +            GraphSONUtil.writeStartObject(responseMessage, jsonGenerator, typeSerializer);
 +
 +            jsonGenerator.writeStringField(SerTokens.TOKEN_REQUEST, responseMessage.getRequestId() != null ? responseMessage.getRequestId().toString() : null);
 +            jsonGenerator.writeFieldName(SerTokens.TOKEN_STATUS);
 +
 +            GraphSONUtil.writeStartObject(responseMessage, jsonGenerator, typeSerializer);
 +            jsonGenerator.writeStringField(SerTokens.TOKEN_MESSAGE, responseMessage.getStatus().getMessage());
 +            jsonGenerator.writeNumberField(SerTokens.TOKEN_CODE, responseMessage.getStatus().getCode().getValue());
 +            jsonGenerator.writeObjectField(SerTokens.TOKEN_ATTRIBUTES, responseMessage.getStatus().getAttributes());
 +            GraphSONUtil.writeEndObject(responseMessage, jsonGenerator, typeSerializer);
 +
 +            jsonGenerator.writeFieldName(SerTokens.TOKEN_RESULT);
 +
 +            GraphSONUtil.writeStartObject(responseMessage, jsonGenerator, typeSerializer);
 +
 +            if (null == responseMessage.getResult().getData()){
 +                jsonGenerator.writeNullField(SerTokens.TOKEN_DATA);
 +            } else {
 +                jsonGenerator.writeFieldName(SerTokens.TOKEN_DATA);
 +                final Object result = responseMessage.getResult().getData();
 +                serializerProvider.findTypedValueSerializer(result.getClass(), true, null).serialize(result, jsonGenerator, serializerProvider);
 +            }
 +
 +            jsonGenerator.writeObjectField(SerTokens.TOKEN_META, responseMessage.getResult().getMeta());
 +            GraphSONUtil.writeEndObject(responseMessage, jsonGenerator, typeSerializer);
 +
 +            GraphSONUtil.writeEndObject(responseMessage, jsonGenerator, typeSerializer);
 +        }
 +    }
 +    
 +    public final static class ResponseMessageDeserializer extends AbstractObjectDeserializer<ResponseMessage> {
 +        protected ResponseMessageDeserializer() {
 +            super(ResponseMessage.class);
 +        }
 +        
 +        @Override
 +        public ResponseMessage createObject(final Map<String, Object> data) {
 +            final Map<String, Object> status = (Map<String, Object>) data.get(SerTokens.TOKEN_STATUS);
 +            final Map<String, Object> result = (Map<String, Object>) data.get(SerTokens.TOKEN_RESULT);
 +            return ResponseMessage.build(UUID.fromString(data.get(SerTokens.TOKEN_REQUEST).toString()))
 +                    .code(ResponseStatusCode.getFromValue((Integer) status.get(SerTokens.TOKEN_CODE)))
 +                    .statusMessage(String.valueOf(status.get(SerTokens.TOKEN_MESSAGE)))
 +                    .statusAttributes((Map<String, Object>) status.get(SerTokens.TOKEN_ATTRIBUTES))
 +                    .result(result.get(SerTokens.TOKEN_DATA))
 +                    .responseMetaData((Map<String, Object>) result.get(SerTokens.TOKEN_META))
 +                    .create();
 +        }
 +    }
 +}
diff --cc gremlin-util/src/test/java/org/apache/tinkerpop/gremlin/util/ser/AbstractGraphSONMessageSerializerV1Test.java
index 0000000000,0000000000..b62909a390
new file mode 100644
--- /dev/null
+++ b/gremlin-util/src/test/java/org/apache/tinkerpop/gremlin/util/ser/AbstractGraphSONMessageSerializerV1Test.java
@@@ -1,0 -1,0 +1,53 @@@
++/*
++ * Licensed to the Apache Software Foundation (ASF) under one
++ * or more contributor license agreements.  See the NOTICE file
++ * distributed with this work for additional information
++ * regarding copyright ownership.  The ASF licenses this file
++ * to you under the Apache License, Version 2.0 (the
++ * "License"); you may not use this file except in compliance
++ * with the License.  You may obtain a copy of the License at
++ *
++ * http://www.apache.org/licenses/LICENSE-2.0
++ *
++ * Unless required by applicable law or agreed to in writing,
++ * software distributed under the License is distributed on an
++ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
++ * KIND, either express or implied.  See the License for the
++ * specific language governing permissions and limitations
++ * under the License.
++ */
++package org.apache.tinkerpop.gremlin.util.ser;
++
++import org.apache.tinkerpop.gremlin.structure.io.graphson.GraphSONMapper;
++import org.apache.tinkerpop.shaded.jackson.core.StreamReadConstraints;
++import org.junit.Test;
++
++import java.util.HashMap;
++import java.util.Map;
++
++import static org.junit.Assert.assertEquals;
++
++public class AbstractGraphSONMessageSerializerV1Test {
++    @Test
++    public void shouldApplyMaxTokenLengthsOnConfigure() {
++        // Initialize bare-bones AbstractGraphSONMessageSerializerV1
++        final AbstractGraphSONMessageSerializerV1 serializer = new AbstractGraphSONMessageSerializerV1() {
++            @Override byte[] obtainHeader() { return new byte[0]; }
++            @Override GraphSONMapper.Builder configureBuilder(GraphSONMapper.Builder builder) { return builder;}
++            @Override public String[] mimeTypesSupported() {return new String[0]; }
++        };
++
++        final Map<String, Object> config = new HashMap<>();
++        config.put("maxNumberLength", 999);
++        config.put("maxStringLength", 12345);
++        config.put("maxNestingDepth", 55);
++
++        serializer.configure(config, null);
++
++        final StreamReadConstraints constraints = serializer.getMapper().getFactory().streamReadConstraints();
++
++        assertEquals(999, constraints.getMaxNumberLength());
++        assertEquals(12345, constraints.getMaxStringLength());
++        assertEquals(55, constraints.getMaxNestingDepth());
++    }
++}
diff --cc gremlin-util/src/test/java/org/apache/tinkerpop/gremlin/util/ser/AbstractGraphSONMessageSerializerV2Test.java
index 0000000000,0000000000..14232c5c82
new file mode 100644
--- /dev/null
+++ b/gremlin-util/src/test/java/org/apache/tinkerpop/gremlin/util/ser/AbstractGraphSONMessageSerializerV2Test.java
@@@ -1,0 -1,0 +1,53 @@@
++/*
++ * Licensed to the Apache Software Foundation (ASF) under one
++ * or more contributor license agreements.  See the NOTICE file
++ * distributed with this work for additional information
++ * regarding copyright ownership.  The ASF licenses this file
++ * to you under the Apache License, Version 2.0 (the
++ * "License"); you may not use this file except in compliance
++ * with the License.  You may obtain a copy of the License at
++ *
++ * http://www.apache.org/licenses/LICENSE-2.0
++ *
++ * Unless required by applicable law or agreed to in writing,
++ * software distributed under the License is distributed on an
++ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
++ * KIND, either express or implied.  See the License for the
++ * specific language governing permissions and limitations
++ * under the License.
++ */
++package org.apache.tinkerpop.gremlin.util.ser;
++
++import org.apache.tinkerpop.gremlin.structure.io.graphson.GraphSONMapper;
++import org.apache.tinkerpop.shaded.jackson.core.StreamReadConstraints;
++import org.junit.Test;
++
++import java.util.HashMap;
++import java.util.Map;
++
++import static org.junit.Assert.assertEquals;
++
++public class AbstractGraphSONMessageSerializerV2Test {
++    @Test
++    public void shouldApplyMaxTokenLengthsOnConfigure() {
++        // Initialize bare-bones AbstractGraphSONMessageSerializerV2
++        final AbstractGraphSONMessageSerializerV2 serializer = new AbstractGraphSONMessageSerializerV2() {
++            @Override byte[] obtainHeader() { return new byte[0]; }
++            @Override GraphSONMapper.Builder configureBuilder(GraphSONMapper.Builder builder) { return builder;}
++            @Override public String[] mimeTypesSupported() {return new String[0]; }
++        };
++
++        final Map<String, Object> config = new HashMap<>();
++        config.put("maxNumberLength", 999);
++        config.put("maxStringLength", 12345);
++        config.put("maxNestingDepth", 55);
++
++        serializer.configure(config, null);
++
++        final StreamReadConstraints constraints = serializer.getMapper().getFactory().streamReadConstraints();
++
++        assertEquals(999, constraints.getMaxNumberLength());
++        assertEquals(12345, constraints.getMaxStringLength());
++        assertEquals(55, constraints.getMaxNestingDepth());
++    }
++}