Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

For tests #2586

Draft
wants to merge 6 commits into
base: master
from
Draft

For tests #2586

Changes from all commits
Commits
File filter...
Filter file types
Jump to…
Jump to file or symbol
Failed to load files and symbols.

Always

Just for now

@@ -10,7 +10,7 @@

<groupId>com.fasterxml.jackson.core</groupId>
<artifactId>jackson-databind</artifactId>
<version>3.0.0-SNAPSHOT</version>
<version>3.0.0-SNAPSHOT-lambda</version>
<name>jackson-databind</name>
<packaging>bundle</packaging>
<description>General data-binding functionality for Jackson: works on core streaming API</description>
@@ -27,7 +27,7 @@
<properties>
<!-- Can not use default, since group id != Java package name here -->
<osgi.export>com.fasterxml.jackson.databind.*;version=${project.version}</osgi.export>
<!-- fix for databind#2299: using jackson-databind in an OSGi environment under Android -->
<!-- fix for databind#2299: using jackson-databind in an OSGi environment under Android -->
<osgi.import>
org.w3c.dom.bootstrap;resolution:=optional,
*
@@ -452,8 +452,18 @@
*<p>
* Feature is enabled by default.
*/
EAGER_DESERIALIZER_FETCH(true)

EAGER_DESERIALIZER_FETCH(true),

/**
* Feature that determines whether properties should be set by
* dynamicly generated class invoking setter or standard reflection
*
* This should make deserialization about 3% faster.
*
* Feature is disabled by default.
*/
LAMBDA_METAFACTORY_AS_INVOKER(false)

;

private final boolean _defaultState;
@@ -800,6 +800,7 @@ protected SettableBeanProperty constructSettableProperty(DeserializationContext
TypeDeserializer typeDeser = type.getTypeHandler();
SettableBeanProperty prop;
if (mutator instanceof AnnotatedMethod) {

prop = new MethodProperty(propDef, type, typeDeser,
beanDesc.getClassAnnotations(), (AnnotatedMethod) mutator);
} else {
@@ -2,7 +2,9 @@

import java.io.IOException;
import java.lang.annotation.Annotation;
import java.lang.reflect.InvocationTargetException;
import java.lang.reflect.Method;
import java.util.function.*;

import com.fasterxml.jackson.core.JsonParser;
import com.fasterxml.jackson.core.JsonToken;
@@ -12,6 +14,14 @@
import com.fasterxml.jackson.databind.introspect.*;
import com.fasterxml.jackson.databind.jsontype.TypeDeserializer;
import com.fasterxml.jackson.databind.util.Annotations;
import com.fasterxml.jackson.databind.util.LambdaMetafactoryUtils;

// https://github.com/FasterXML/jackson-databind/issues/2083
// TODO:
// - tests of performance
// - create pull request
// - add support for Java 9,10,11,12,13


/**
* This concrete sub-class implements property that is set
@@ -29,6 +39,8 @@
* "regular" method-accessible properties.
*/
protected final transient Method _setter;
protected final transient BiConsumer consumer;
protected final transient BiFunction function;

/**
* @since 2.9
@@ -42,6 +54,8 @@ public MethodProperty(BeanPropertyDefinition propDef,
super(propDef, type, typeDeser, contextAnnotations);
_annotated = method;
_setter = method.getAnnotated();
consumer = getConsumer();
function = getFunction();
_skipNulls = NullsConstantProvider.isSkipper(_nullProvider);
}

@@ -50,13 +64,19 @@ protected MethodProperty(MethodProperty src, JsonDeserializer<?> deser,
super(src, deser, nva);
_annotated = src._annotated;
_setter = src._setter;
consumer = getConsumer();
function = getFunction();

_skipNulls = NullsConstantProvider.isSkipper(nva);
}

protected MethodProperty(MethodProperty src, PropertyName newName) {
super(src, newName);
_annotated = src._annotated;
_setter = src._setter;
consumer = getConsumer();
function = getFunction();

_skipNulls = src._skipNulls;
}

@@ -67,9 +87,20 @@ protected MethodProperty(MethodProperty src, Method m) {
super(src);
_annotated = src._annotated;
_setter = m;
consumer = getConsumer();
function = getFunction();

_skipNulls = src._skipNulls;
}

private BiConsumer getConsumer() {
return LambdaMetafactoryUtils.getBiConsumerObjectSetter(_setter);
}

private BiFunction getFunction() {
return LambdaMetafactoryUtils.getBiFunctionObjectSetter(_setter);
}

@Override
public SettableBeanProperty withName(PropertyName newName) {
return new MethodProperty(this, newName);
@@ -138,7 +169,7 @@ public void deserializeAndSet(JsonParser p, DeserializationContext ctxt,
value = _valueDeserializer.deserializeWithType(p, ctxt, _valueTypeDeserializer);
}
try {
_setter.invoke(instance, value);
invokeWithoutResult(isConsumerEnabled(ctxt), instance, value);
} catch (Exception e) {
_throwAsIOE(p, e, value);
}
@@ -167,19 +198,48 @@ public Object deserializeSetAndReturn(JsonParser p,
value = _valueDeserializer.deserializeWithType(p, ctxt, _valueTypeDeserializer);
}
try {
Object result = _setter.invoke(instance, value);
Object result = invokeWithResult(isConsumerEnabled(ctxt), instance, value);
return (result == null) ? instance : result;
} catch (Exception e) {
_throwAsIOE(p, e, value);
return null;
}
}

private boolean isConsumerEnabled(DeserializationContext ctxt) {
return ctxt.isEnabled(DeserializationFeature.LAMBDA_METAFACTORY_AS_INVOKER);
}


private void invokeWithoutResult(boolean useConsumer, Object instance, Object value) throws InvocationTargetException, IllegalAccessException {
// if (useConsumer) {
if (consumer != null) {
consumer.accept(instance, value);
} else {
_setter.invoke(instance, value);
}
// } else {
// _setter.invoke(instance, value);
// }
}

private Object invokeWithResult(boolean useConsumer, Object instance, Object value) throws InvocationTargetException, IllegalAccessException {
// if (useConsumer) {
if (function != null) {
return function.apply(instance, value);
} else {
return _setter.invoke(instance, value);
}
// } else {
// return _setter.invoke(instance, value);
// }
}

@Override
public final void set(Object instance, Object value) throws IOException
{
try {
_setter.invoke(instance, value);
invokeWithoutResult(false, instance, value);
} catch (Exception e) {
// 15-Sep-2015, tatu: How could we get a ref to JsonParser?
_throwAsIOE(e, value);
@@ -190,7 +250,7 @@ public final void set(Object instance, Object value) throws IOException
public Object setAndReturn(Object instance, Object value) throws IOException
{
try {
Object result = _setter.invoke(instance, value);
Object result = invokeWithResult(false, instance, value);
return (result == null) ? instance : result;
} catch (Exception e) {
// 15-Sep-2015, tatu: How could we get a ref to JsonParser?
ProTip! Use n and p to navigate between commits in a pull request.
You can’t perform that action at this time.