下面列出了com.fasterxml.jackson.databind.ser.impl.ObjectIdWriter#com.fasterxml.jackson.annotation.ObjectIdGenerator 实例代码,或者点击链接到github查看源代码,也可以在右侧发表评论。
/**
* We must override this method, to prevent errors when scopes are the same,
* but underlying class (on which to access property) is different.
*/
@Override
public boolean canUseFor(ObjectIdGenerator<?> gen) {
if (gen.getClass() == getClass()) {
PropertyBasedObjectIdGenerator other = (PropertyBasedObjectIdGenerator) gen;
if (other.getScope() == _scope) {
/* 26-Jul-2012, tatu: This is actually not enough, because the property
* accessor within BeanPropertyWriter won't work for other property fields
* (see [https://github.com/FasterXML/jackson-module-jaxb-annotations/issues/9]
* for details).
* So we need to verify that underlying property is actually the same.
*/
return (other._property == _property);
}
}
return false;
}
/** @since 4.3 */
@Override
public ObjectIdGenerator<?> objectIdGeneratorInstance(MapperConfig<?> config,
Annotated annotated, Class<?> implClass) {
return (ObjectIdGenerator<?>) this.beanFactory.createBean(implClass);
}
/** @since 4.3 */
@Override
public ObjectIdGenerator<?> objectIdGeneratorInstance(MapperConfig<?> config,
Annotated annotated, Class<?> implClass) {
return (ObjectIdGenerator<?>) this.beanFactory.createBean(implClass);
}
/**
* {@inheritDoc}
*
* Used by generated {@link AbstractBeanJsonSerializer}
*/
@Override
@SuppressWarnings("UnusedDeclaration")
public void addGenerator(ObjectIdGenerator<?> generator) {
if (null == generators) {
generators = new ArrayList<ObjectIdGenerator<?>>();
}
generators.add(generator);
}
/**
* {@inheritDoc}
*
* Used by generated {@link AbstractBeanJsonSerializer}
*/
@Override
@SuppressWarnings({"UnusedDeclaration", "unchecked"})
public <T> ObjectIdGenerator<T> findObjectIdGenerator(ObjectIdGenerator<T> gen) {
if (null != generators) {
for (ObjectIdGenerator<?> generator : generators) {
if (generator.canUseFor(gen)) {
return (ObjectIdGenerator<T>) generator;
}
}
}
return null;
}
@SuppressWarnings("unchecked")
protected ObjectIdWriter(JavaType t, SerializableString propName,
ObjectIdGenerator<?> gen, JsonSerializer<?> ser, boolean alwaysAsId)
{
idType = t;
propertyName = propName;
generator = gen;
serializer = (JsonSerializer<Object>) ser;
this.alwaysAsId = alwaysAsId;
}
/**
* Factory method called by {@link com.fasterxml.jackson.databind.ser.std.BeanSerializerBase}
* with the initial information based on standard settings for the type
* for which serializer is being built.
*
* @since 2.3
*/
public static ObjectIdWriter construct(JavaType idType, PropertyName propName,
ObjectIdGenerator<?> generator, boolean alwaysAsId)
{
String simpleName = (propName == null) ? null : propName.getSimpleName();
SerializableString serName = (simpleName == null) ? null : new SerializedString(simpleName);
return new ObjectIdWriter(idType, serName, generator, null, alwaysAsId);
}
protected ObjectIdInfo(PropertyName prop, Class<?> scope, Class<? extends ObjectIdGenerator<?>> gen,
boolean alwaysAsId, Class<? extends ObjectIdResolver> resolver)
{
_propertyName = prop;
_scope = scope;
_generator = gen;
_alwaysAsId = alwaysAsId;
if (resolver == null) {
resolver = SimpleObjectIdResolver.class;
}
_resolver = resolver;
}
@SuppressWarnings("unchecked")
protected ObjectIdReader(JavaType t, PropertyName propName, ObjectIdGenerator<?> gen,
JsonDeserializer<?> deser, SettableBeanProperty idProp, ObjectIdResolver resolver)
{
_idType = t;
propertyName = propName;
generator = gen;
this.resolver = resolver;
_deserializer = (JsonDeserializer<Object>) deser;
idProperty = idProp;
}
/**
* Factory method called by {@link com.fasterxml.jackson.databind.ser.std.BeanSerializerBase}
* with the initial information based on standard settings for the type
* for which serializer is being built.
*/
public static ObjectIdReader construct(JavaType idType, PropertyName propName,
ObjectIdGenerator<?> generator, JsonDeserializer<?> deser,
SettableBeanProperty idProp, ObjectIdResolver resolver)
{
return new ObjectIdReader(idType, propName, generator, deser, idProp, resolver);
}
/**
* Used by generated {@link AbstractBeanJsonSerializer}
*
* @param generator instance of generator to add
*/
@SuppressWarnings( "UnusedDeclaration" )
public void addGenerator( ObjectIdGenerator<?> generator ) {
if ( null == generators ) {
generators = new ArrayList<ObjectIdGenerator<?>>();
}
generators.add( generator );
}
/**
* Used by generated {@link AbstractBeanJsonSerializer}
*
* @param gen generator used to find equivalent generator
* @param <T> a T object.
*
* @return a {@link com.fasterxml.jackson.annotation.ObjectIdGenerator} object.
*/
@SuppressWarnings( {"UnusedDeclaration", "unchecked"} )
public <T> ObjectIdGenerator<T> findObjectIdGenerator( ObjectIdGenerator<T> gen ) {
if ( null != generators ) {
for ( ObjectIdGenerator<?> generator : generators ) {
if ( generator.canUseFor( gen ) ) {
return (ObjectIdGenerator<T>) generator;
}
}
}
return null;
}
BeanIdentityInfo( String propertyName, boolean alwaysAsId, Class<? extends ObjectIdGenerator<?>> generator, Class<?> scope ) {
this.propertyName = propertyName;
this.alwaysAsId = alwaysAsId;
this.generator = generator;
this.scope = scope;
this.idABeanProperty = true;
this.type = Optional.absent();
}
BeanIdentityInfo( String propertyName, boolean alwaysAsId, Class<? extends ObjectIdGenerator<?>> generator, Class<?> scope,
JType type ) {
this.propertyName = propertyName;
this.alwaysAsId = alwaysAsId;
this.generator = generator;
this.scope = scope;
this.idABeanProperty = false;
this.type = Optional.of( type );
}
private TypeSpec generateIdentifierSerializationInfo(BeanIdentityInfo identityInfo,
Optional<CodeBlock> serializerType) {
TypeSpec.Builder builder = TypeSpec
.anonymousClassBuilder("$L, $S", identityInfo.isAlwaysAsId(), identityInfo.getPropertyName());
if (identityInfo.isIdABeanProperty()) {
Map<Element, TypeMirror> fieldsMap = orderedFields();
Optional<Map.Entry<Element, TypeMirror>> propertyEntry = fieldsMap
.entrySet()
.stream()
.filter(entry -> entry.getKey().getSimpleName().toString().equals(identityInfo.getPropertyName()))
.findFirst();
if (propertyEntry.isPresent()) {
builder.superclass(ParameterizedTypeName.get(ClassName.get(PropertyIdentitySerializationInfo.class), TypeName.get(beanType), Type.wrapperType(propertyEntry.get().getValue())));
buildBeanPropertySerializerBody(builder, propertyEntry.get());
} else {
messager.printMessage(Diagnostic.Kind.ERROR, "Property [" + identityInfo.getPropertyName() + "] not found in type [" + beanType.toString() + "]!.");
}
} else {
TypeMirror qualifiedType = identityInfo.getType().get();
builder.superclass(ParameterizedTypeName.get(ClassName.get(AbstractIdentitySerializationInfo.class), TypeName.get(beanType), TypeName.get(qualifiedType)));
builder.addMethod(MethodSpec.methodBuilder("newSerializer")
.addModifiers(Modifier.PROTECTED)
.addAnnotation(Override.class)
.returns(ParameterizedTypeName.get(ClassName.get(JsonSerializer.class), DEFAULT_WILDCARD))
.addStatement("return $L", serializerType.get())
.build());
TypeName generatorType = ParameterizedTypeName.get(ClassName.get(ObjectIdGenerator.class), TypeName.get(qualifiedType));
TypeName returnType = ParameterizedTypeName.get(ClassName.get(ObjectIdSerializer.class), TypeName.get(qualifiedType));
builder.addMethod(MethodSpec.methodBuilder("getObjectId")
.addModifiers(Modifier.PUBLIC)
.addAnnotation(Override.class)
.returns(returnType)
.addParameter(TypeName.get(beanType), "bean")
.addParameter(JsonSerializationContext.class, "ctx")
.addStatement("$T generator = new $T().forScope($T.class)",
generatorType, identityInfo.getGenerator(), identityInfo.getScope().get())
.addStatement("$T scopedGen = ctx.findObjectIdGenerator(generator)", generatorType)
.beginControlFlow("if (null == scopedGen)")
.addStatement("scopedGen = generator.newForSerialization(ctx)")
.addStatement("ctx.addGenerator(scopedGen)")
.endControlFlow()
.addStatement("return new $T(scopedGen.generateId(bean), getSerializer())", returnType)
.build());
}
return builder.build();
}
/** @since 4.3 */
@Override
public ObjectIdGenerator<?> objectIdGeneratorInstance(MapperConfig<?> config, Annotated annotated, Class<?> implClass) {
return (ObjectIdGenerator<?>) this.beanFactory.createBean(implClass);
}
public WritableObjectId(ObjectIdGenerator<?> generator) {
this.generator = generator;
}
@Override
public ObjectIdGenerator<Object> forScope(Class<?> scope) {
return (scope == _scope) ? this : new PropertyBasedObjectIdGenerator(scope, _property);
}
@Override
public ObjectIdGenerator<Object> newForSerialization(Object context) {
// No state, can return this
return this;
}
public ObjectIdInfo(PropertyName name, Class<?> scope, Class<? extends ObjectIdGenerator<?>> gen,
Class<? extends ObjectIdResolver> resolver)
{
this(name, scope, gen, false, resolver);
}
protected ObjectIdInfo(PropertyName prop, Class<?> scope, Class<? extends ObjectIdGenerator<?>> gen,
boolean alwaysAsId)
{
this(prop, scope, gen, alwaysAsId, SimpleObjectIdResolver.class);
}
@Override
public JsonDeserializer<?> createContextual(DeserializationContext ctxt,
BeanProperty property) throws JsonMappingException
{
final AnnotationIntrospector intr = ctxt.getAnnotationIntrospector();
if (property != null && intr != null) {
final AnnotatedMember accessor = property.getMember();
if (accessor != null) {
ObjectIdInfo objectIdInfo = intr.findObjectIdInfo(accessor);
if (objectIdInfo != null) { // some code duplication here as well (from BeanDeserializerFactory)
JavaType idType;
ObjectIdGenerator<?> idGen;
SettableBeanProperty idProp = null;
ObjectIdResolver resolver = ctxt.objectIdResolverInstance(accessor, objectIdInfo);
// 2.1: allow modifications by "id ref" annotations as well:
objectIdInfo = intr.findObjectReferenceInfo(accessor, objectIdInfo);
Class<?> implClass = objectIdInfo.getGeneratorType();
if (implClass == ObjectIdGenerators.PropertyGenerator.class) {
PropertyName propName = objectIdInfo.getPropertyName();
idProp = (_properties == null) ? null : _properties.get(propName.getSimpleName());
if (idProp == null) {
ctxt.reportBadDefinition(_baseType, String.format(
"Invalid Object Id definition for %s: cannot find property with name '%s'",
handledType().getName(), propName));
}
idType = idProp.getType();
idGen = new PropertyBasedObjectIdGenerator(objectIdInfo.getScope());
/*
ctxt.reportBadDefinition(_baseType, String.format(
/
"Invalid Object Id definition for abstract type %s: cannot use `PropertyGenerator` on polymorphic types using property annotation",
handledType().getName()));
*/
} else { // other types simpler
resolver = ctxt.objectIdResolverInstance(accessor, objectIdInfo);
JavaType type = ctxt.constructType(implClass);
idType = ctxt.getTypeFactory().findTypeParameters(type, ObjectIdGenerator.class)[0];
idGen = ctxt.objectIdGeneratorInstance(accessor, objectIdInfo);
}
JsonDeserializer<?> deser = ctxt.findRootValueDeserializer(idType);
ObjectIdReader oir = ObjectIdReader.construct(idType, objectIdInfo.getPropertyName(),
idGen, deser, idProp, resolver);
return new AbstractDeserializer(this, oir, null);
}
}
}
if (_properties == null) {
return this;
}
// Need to ensure properties are dropped at this point, regardless
return new AbstractDeserializer(this, _objectIdReader, null);
}
@Override
public ObjectIdGenerator<Object> forScope(Class<?> scope) {
return (scope == _scope) ? this : new PropertyBasedObjectIdGenerator(scope);
}
@Override
public ObjectIdGenerator<Object> newForSerialization(Object context) {
return this;
}
public ReadableObjectId(ObjectIdGenerator.IdKey key) {
_key = key;
}
public ObjectIdGenerator.IdKey getKey() {
return _key;
}
@Override
public LogicalOperator deserialize(JsonParser jp, DeserializationContext ctxt) throws IOException,
JsonProcessingException {
ObjectIdGenerator<Integer> idGenerator = new ObjectIdGenerators.IntSequenceGenerator();
JsonLocation start = jp.getCurrentLocation();
JsonToken t = jp.getCurrentToken();
LogicalOperator parent = null;
LogicalOperator first = null;
LogicalOperator prev = null;
Integer id = null;
while (true) {
String fieldName = jp.getText();
t = jp.nextToken();
switch (fieldName) { // switch on field names.
case "@id":
id = _parseIntPrimitive(jp, ctxt);
break;
case "input":
JavaType tp = ctxt.constructType(LogicalOperator.class);
JsonDeserializer<Object> d = ctxt.findRootValueDeserializer(tp);
parent = (LogicalOperator) d.deserialize(jp, ctxt);
break;
case "do":
if (!jp.isExpectedStartArrayToken()) {
throwE(
jp,
"The do parameter of sequence should be an array of SimpleOperators. Expected a JsonToken.START_ARRAY token but received a "
+ t.name() + "token.");
}
int pos = 0;
while ((t = jp.nextToken()) != JsonToken.END_ARRAY) {
// logger.debug("Reading sequence child {}.", pos);
JsonLocation l = jp.getCurrentLocation(); // get current location
// first so we can
// correctly reference the
// start of the object in
// the case that the type
// is wrong.
LogicalOperator o = jp.readValueAs(LogicalOperator.class);
if (pos == 0) {
if (!(o instanceof SingleInputOperator) && !(o instanceof SourceOperator)) {
throwE(
l,
"The first operator in a sequence must be either a ZeroInput or SingleInput operator. The provided first operator was not. It was of type "
+ o.getClass().getName());
}
first = o;
} else {
if (!(o instanceof SingleInputOperator)) {
throwE(l, "All operators after the first must be single input operators. The operator at position "
+ pos + " was not. It was of type " + o.getClass().getName());
}
SingleInputOperator now = (SingleInputOperator) o;
now.setInput(prev);
}
prev = o;
pos++;
}
break;
default:
throwE(jp, "Unknown field name provided for Sequence: " + jp.getText());
}
t = jp.nextToken();
if (t == JsonToken.END_OBJECT) {
break;
}
}
if (first == null) {
throwE(start, "A sequence must include at least one operator.");
}
if ((parent == null && first instanceof SingleInputOperator)
|| (parent != null && first instanceof SourceOperator)) {
throwE(start,
"A sequence must either start with a ZeroInputOperator or have a provided input. It cannot have both or neither.");
}
if (parent != null && first instanceof SingleInputOperator) {
((SingleInputOperator) first).setInput(parent);
}
// set input reference.
if (id != null) {
ReadableObjectId rid = ctxt.findObjectId(id, idGenerator, null);
rid.bindItem(prev);
// logger.debug("Binding id {} to item {}.", rid.id, rid.item);
}
return first;
}
@Override
public void bindItem(ObjectIdGenerator.IdKey id, Object pojo) {
}
@Override
public Object resolveId(ObjectIdGenerator.IdKey id) {
return store == null ? null : store.findByKey(id.scope, id.key);
}
@Override
public ObjectIdGenerator<?> objectIdGeneratorInstance(MapperConfig<?> config, Annotated annotated, Class<?> implClass) {
return null;
}