();
+ }).orElse(new HashMap<>());
}
private JsonbComponentInstanceCreator initComponentInstanceCreator() {
diff --git a/src/main/java/org/eclipse/yasson/internal/MappingContext.java b/src/main/java/org/eclipse/yasson/internal/MappingContext.java
index 9a91c2543..a5608fd58 100644
--- a/src/main/java/org/eclipse/yasson/internal/MappingContext.java
+++ b/src/main/java/org/eclipse/yasson/internal/MappingContext.java
@@ -1,5 +1,5 @@
/*
- * Copyright (c) 2015, 2023 Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2015, 2024 Oracle and/or its affiliates. All rights reserved.
*
* This program and the accompanying materials are made available under the
* terms of the Eclipse Public License v. 2.0 which is available at
@@ -25,7 +25,7 @@
/**
* JSONB mappingContext. Created once per {@link jakarta.json.bind.Jsonb} instance. Represents a global scope.
* Holds internal model.
- *
+ *
* Thread safe.
*/
public class MappingContext {
@@ -90,13 +90,13 @@ private static Function, ClassModel> createParseClassModelFunction(Clas
? ClassCustomization.empty()
: parentClassModel.getClassCustomization(),
jsonbContext.getConfigProperties().getPropertyNamingStrategy());
- // PolymorphismSupport configPolymorphism = jsonbContext.getConfigProperties().getPolymorphismSupport();
-// if (configPolymorphism != null) {
-// customization = mergeConfigAndAnnotationPolymorphism(configPolymorphism,
-// configPolymorphism.getClassPolymorphism(aClass),
-// customization,
-// aClass);
-// }
+ /*PolymorphismSupport configPolymorphism = jsonbContext.getConfigProperties().getPolymorphismSupport();
+ if (configPolymorphism != null) {
+ customization = mergeConfigAndAnnotationPolymorphism(configPolymorphism,
+ configPolymorphism.getClassPolymorphism(aClass),
+ customization,
+ aClass);
+ }*/
ClassModel newClassModel = new ClassModel(aClass,
customization,
parentClassModel,
@@ -108,39 +108,39 @@ private static Function, ClassModel> createParseClassModelFunction(Clas
};
}
-// private static ClassCustomization mergeConfigAndAnnotationPolymorphism(PolymorphismSupport generalPolymorphism,
-// Optional maybeClassPolymorphism,
-// ClassCustomization customization,
-// Class> aClass) {
-// PolymorphismConfig polymorphismConfig = customization.getPolymorphismConfig();
-// PolymorphismConfig.Builder polyConfigBuilder;
-// if (polymorphismConfig != null) {
-// polyConfigBuilder = PolymorphismConfig.builder().of(polymorphismConfig);
-// } else {
-// polyConfigBuilder = PolymorphismConfig.builder();
-// maybeClassPolymorphism.ifPresent(classPolymorphism -> polyConfigBuilder
-// .inherited(!classPolymorphism.getBoundClass().equals(aClass)));
-// }
-// generalPolymorphism.getKeyName().filter(s -> !s.isEmpty()).ifPresent(polyConfigBuilder::fieldName);
-// generalPolymorphism.useClassNames().ifPresent(polyConfigBuilder::useClassNames);
-// polyConfigBuilder.whitelistedPackages(generalPolymorphism.getWhitelistedPackages());
-//
-// maybeClassPolymorphism.ifPresent(classPolymorphism -> {
-// classPolymorphism.getKeyName().filter(s -> !s.isEmpty()).ifPresent(polyConfigBuilder::fieldName);
-// classPolymorphism.useClassNames().ifPresent(polyConfigBuilder::useClassNames);
-// classPolymorphism.getFormat().ifPresent(polyConfigBuilder::format);
-// classPolymorphism.getAliases().forEach(polyConfigBuilder::alias);
-// polyConfigBuilder.whitelistedPackages(classPolymorphism.getWhitelistedPackages());
-// });
-// PolymorphismConfig polyConfigMerged = polyConfigBuilder.build();
-// if (polyConfigMerged.getFieldName() == null || polyConfigMerged.getFieldName().isEmpty()) {
-// throw new JsonbException("Polymorphism type field name cannot be null or empty: " + aClass);
-// }
-// return ClassCustomization.builder()
-// .of(customization)
-// .polymorphismConfig(polyConfigMerged)
-// .build();
-// }
+ /*private static ClassCustomization mergeConfigAndAnnotationPolymorphism(PolymorphismSupport generalPolymorphism,
+ Optional maybeClassPolymorphism,
+ ClassCustomization customization,
+ Class> aClass) {
+ PolymorphismConfig polymorphismConfig = customization.getPolymorphismConfig();
+ PolymorphismConfig.Builder polyConfigBuilder;
+ if (polymorphismConfig != null) {
+ polyConfigBuilder = PolymorphismConfig.builder().of(polymorphismConfig);
+ } else {
+ polyConfigBuilder = PolymorphismConfig.builder();
+ maybeClassPolymorphism.ifPresent(classPolymorphism -> polyConfigBuilder
+ .inherited(!classPolymorphism.getBoundClass().equals(aClass)));
+ }
+ generalPolymorphism.getKeyName().filter(s -> !s.isEmpty()).ifPresent(polyConfigBuilder::fieldName);
+ generalPolymorphism.useClassNames().ifPresent(polyConfigBuilder::useClassNames);
+ polyConfigBuilder.whitelistedPackages(generalPolymorphism.getWhitelistedPackages());
+
+ maybeClassPolymorphism.ifPresent(classPolymorphism -> {
+ classPolymorphism.getKeyName().filter(s -> !s.isEmpty()).ifPresent(polyConfigBuilder::fieldName);
+ classPolymorphism.useClassNames().ifPresent(polyConfigBuilder::useClassNames);
+ classPolymorphism.getFormat().ifPresent(polyConfigBuilder::format);
+ classPolymorphism.getAliases().forEach(polyConfigBuilder::alias);
+ polyConfigBuilder.whitelistedPackages(classPolymorphism.getWhitelistedPackages());
+ });
+ PolymorphismConfig polyConfigMerged = polyConfigBuilder.build();
+ if (polyConfigMerged.getFieldName() == null || polyConfigMerged.getFieldName().isEmpty()) {
+ throw new JsonbException("Polymorphism type field name cannot be null or empty: " + aClass);
+ }
+ return ClassCustomization.builder()
+ .of(customization)
+ .polymorphismConfig(polyConfigMerged)
+ .build();
+ }*/
/**
* Search for class model, without parsing if not found.
diff --git a/src/main/java/org/eclipse/yasson/internal/ReflectionUtils.java b/src/main/java/org/eclipse/yasson/internal/ReflectionUtils.java
index 66ccac94e..1e465ecb3 100644
--- a/src/main/java/org/eclipse/yasson/internal/ReflectionUtils.java
+++ b/src/main/java/org/eclipse/yasson/internal/ReflectionUtils.java
@@ -1,5 +1,5 @@
/*
- * Copyright (c) 2015, 2023 Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2015, 2024 Oracle and/or its affiliates. All rights reserved.
*
* This program and the accompanying materials are made available under the
* terms of the Eclipse Public License v. 2.0 which is available at
@@ -26,7 +26,6 @@
import java.util.List;
import java.util.Objects;
import java.util.Optional;
-import java.util.logging.Logger;
import jakarta.json.bind.JsonbException;
@@ -38,7 +37,7 @@
*/
public class ReflectionUtils {
- private static final Logger LOGGER = Logger.getLogger(ReflectionUtils.class.getName());
+ /*private static final Logger LOGGER = Logger.getLogger(ReflectionUtils.class.getName());*/
private ReflectionUtils() {
throw new IllegalStateException("Utility classes should not be instantiated.");
@@ -47,7 +46,6 @@ private ReflectionUtils() {
/**
* Get raw type by type.
* Only for ParametrizedTypes, GenericArrayTypes and Classes.
- *
* Empty optional is returned if raw type cannot be resolved.
*
* @param type Type to get class information from, not null.
@@ -60,19 +58,17 @@ public static Optional> getOptionalRawType(Type type) {
return Optional.of((Class>) ((ParameterizedType) type).getRawType());
} else if (type instanceof GenericArrayType) {
return Optional.of(((GenericArrayType) type).getClass());
+ } else if (type instanceof WildcardType) {
+ return Optional.of((Class>) ((WildcardType) type).getUpperBounds()[0]);
} else if (type instanceof TypeVariable) {
TypeVariable> typeVariable = TypeVariable.class.cast(type);
if (Objects.nonNull(typeVariable.getBounds())) {
- Optional> specializedClass = Optional.empty();
- for (Type bound : typeVariable.getBounds()) {
- Optional> boundRawType = getOptionalRawType(bound);
- if (boundRawType.isPresent() && !Object.class.equals(boundRawType.get())) {
- if (!specializedClass.isPresent() || specializedClass.get().isAssignableFrom(boundRawType.get())) {
- specializedClass = Optional.of(boundRawType.get());
- }
- }
- }
- return specializedClass;
+ return Arrays.stream(typeVariable.getBounds())
+ .map(ReflectionUtils::getOptionalRawType)
+ .filter(Optional::isPresent)
+ .filter(clazz -> !Object.class.equals(clazz.get()))
+ .reduce((clazz1, clazz2) -> clazz1.map(clazzGet1 -> clazzGet1.isAssignableFrom(clazz2.get())).orElse(false) ? clazz2 : clazz1)
+ .orElse(Optional.empty());
}
}
return Optional.empty();
@@ -81,7 +77,7 @@ public static Optional> getOptionalRawType(Type type) {
/**
* Get raw type by type.
* Resolves only ParametrizedTypes, GenericArrayTypes and Classes.
- *
+ *
* Exception is thrown if raw type cannot be resolved.
*
* @param type Type to get class information from, not null.
@@ -92,7 +88,7 @@ public static Class> getRawType(Type type) {
.orElseThrow(() -> new JsonbException(Messages.getMessage(MessageKeys.TYPE_RESOLUTION_ERROR, type)));
}
- /**
+ /*/**
* Get a raw type of any type.
* If type is a {@link TypeVariable} recursively search type chain for resolution of typevar.
* If type is a {@link WildcardType} find most specific upper / lower bound, which can be used. If most specific
@@ -102,7 +98,7 @@ public static Class> getRawType(Type type) {
* @param type type to resolve, typically field type or generic bound, not null.
* @return resolved raw class
*/
- public static Class> resolveRawType(List chain, Type type) {
+ /*public static Class> resolveRawType(List chain, Type type) {
if (type instanceof Class) {
return (Class>) type;
} else if (type instanceof ParameterizedType) {
@@ -110,7 +106,7 @@ public static Class> resolveRawType(List chain, Type type) {
} else {
return getRawType(resolveType(chain, type));
}
- }
+ }*/
/**
* Resolve a type by chain.
@@ -136,27 +132,27 @@ private static Type resolveType(List chain, Type type, boolean warn) {
if (toResolve instanceof WildcardType) {
return resolveMostSpecificBound(chain, (WildcardType) toResolve, warn);
} else if (toResolve instanceof TypeVariable) {
- return resolveItemVariableType(chain, (TypeVariable>) toResolve, warn);
+ return resolveItemVariableType(chain, (TypeVariable>) toResolve/*, warn*/);
} else if (toResolve instanceof ParameterizedType) {
return resolveTypeArguments((ParameterizedType) toResolve, chain.get(chain.size() - 1));
}
return type;
}
- /**
+ /*/**
* Resolves type by item information and wraps it with {@link Optional}.
*
* @param chain hierarchy of all wrapping types.
* @param type type
* @return resolved type wrapped with Optional
*/
- public static Optional resolveOptionalType(List chain, Type type) {
+ /*public static Optional resolveOptionalType(List chain, Type type) {
try {
return Optional.of(resolveType(chain, type, false));
} catch (RuntimeException e) {
return Optional.empty();
}
- }
+ }*/
/**
* Resolve a bounded type variable type by its wrapper types.
@@ -165,24 +161,24 @@ public static Optional resolveOptionalType(List chain, Type type) {
*
* @param chain chain to search "runtime" generic type of a TypeVariable.
* @param typeVariable type to search in chain for, not null.
- * @param warn whether or not to log a warning message when bounds are not found
+// * @param warn whether or not to log a warning message when bounds are not found
* @return Type of a generic "runtime" bound, not null.
*/
- public static Type resolveItemVariableType(List chain, TypeVariable> typeVariable, boolean warn) {
-// if (chain == null) {
-// Optional> optionalRawType = getOptionalRawType(typeVariable);
-// if (optionalRawType.isPresent()) {
-// return optionalRawType.get();
-// }
-
- // //Bound not found, treat it as an Object.class
-// if (warn) {
-// LOGGER.warning(Messages.getMessage(MessageKeys.GENERIC_BOUND_NOT_FOUND,
-// typeVariable,
-// typeVariable.getGenericDeclaration()));
-// }
-// return Object.class;
-// }
+ public static Type resolveItemVariableType(List chain, TypeVariable> typeVariable/*, boolean warn*/) {
+ /*if (chain == null) {
+ Optional> optionalRawType = getOptionalRawType(typeVariable);
+ if (optionalRawType.isPresent()) {
+ return optionalRawType.get();
+ }
+
+ //Bound not found, treat it as an Object.class
+ if (warn) {
+ LOGGER.warning(Messages.getMessage(MessageKeys.GENERIC_BOUND_NOT_FOUND,
+ typeVariable,
+ typeVariable.getGenericDeclaration()));
+ }
+ return Object.class;
+ }*/
Type returnType = typeVariable;
for (int i = chain.size() - 1; i >= 0; i--) {
Type type = chain.get(i);
@@ -200,23 +196,23 @@ public static Type resolveItemVariableType(List chain, TypeVariable> typ
}
return returnType;
-// //Embedded items doesn't hold information about variable types
-// if (chain instanceof EmbeddedItem) {
-// return resolveItemVariableType(chain.getWrapper(), typeVariable, warn);
-// }
-//
-// ParameterizedType wrapperParameterizedType = findParameterizedSuperclass(chain.getRuntimeType());
-//
-// VariableTypeInheritanceSearch search = new VariableTypeInheritanceSearch();
-// Type foundType = search.searchParametrizedType(wrapperParameterizedType, typeVariable);
-// if (foundType != null) {
-// if (foundType instanceof TypeVariable) {
-// return resolveItemVariableType(chain.getWrapper(), (TypeVariable>) foundType, warn);
-// }
-// return foundType;
-// }
-//
-// return resolveItemVariableType(chain.getWrapper(), typeVariable, warn);
+ //Embedded items doesn't hold information about variable types
+ /*if (chain instanceof EmbeddedItem) {
+ return resolveItemVariableType(chain.getWrapper(), typeVariable, warn);
+ }
+
+ ParameterizedType wrapperParameterizedType = findParameterizedSuperclass(chain.getRuntimeType());
+
+ VariableTypeInheritanceSearch search = new VariableTypeInheritanceSearch();
+ Type foundType = search.searchParametrizedType(wrapperParameterizedType, typeVariable);
+ if (foundType != null) {
+ if (foundType instanceof TypeVariable) {
+ return resolveItemVariableType(chain.getWrapper(), (TypeVariable>) foundType, warn);
+ }
+ return foundType;
+ }
+
+ return resolveItemVariableType(chain.getWrapper(), typeVariable, warn);*/
}
/**
@@ -328,7 +324,7 @@ public static Constructor getDefaultConstructor(Class clazz, boolean r
* @return type of JsonbAdapter
*/
public static ParameterizedType findParameterizedType(Class> classToSearch, Class> parameterizedInterface) {
- Class current = classToSearch;
+ Class> current = classToSearch;
while (current != Object.class) {
for (Type currentInterface : current.getGenericInterfaces()) {
if (currentInterface instanceof ParameterizedType
@@ -361,15 +357,15 @@ public static boolean isResolvedType(Type type) {
return type instanceof Class>;
}
- private static ParameterizedType findParameterizedSuperclass(Type type) {
+ /*private static ParameterizedType findParameterizedSuperclass(Type type) {
if (type == null || type instanceof ParameterizedType) {
return (ParameterizedType) type;
}
if (!(type instanceof Class)) {
throw new JsonbException("Can't resolve ParameterizedType superclass for: " + type);
}
- return findParameterizedSuperclass(((Class) type).getGenericSuperclass());
- }
+ return findParameterizedSuperclass(((Class>) type).getGenericSuperclass());
+ }*/
/**
* Resolves a wildcard most specific upper or lower bound.
@@ -431,7 +427,6 @@ public String toString() {
public boolean equals(Object o) {
if (o instanceof GenericArrayType) {
GenericArrayType that = (GenericArrayType) o;
-
return Objects.equals(genericComponentType, that.getGenericComponentType());
} else {
return false;
diff --git a/src/main/java/org/eclipse/yasson/internal/VariableTypeInheritanceSearch.java b/src/main/java/org/eclipse/yasson/internal/VariableTypeInheritanceSearch.java
index 263cc4e21..0ceefca7d 100644
--- a/src/main/java/org/eclipse/yasson/internal/VariableTypeInheritanceSearch.java
+++ b/src/main/java/org/eclipse/yasson/internal/VariableTypeInheritanceSearch.java
@@ -1,5 +1,5 @@
/*
- * Copyright (c) 2015, 2022 Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2015, 2024 Oracle and/or its affiliates. All rights reserved.
*
* This program and the accompanying materials are made available under the
* terms of the Eclipse Public License v. 2.0 which is available at
@@ -83,11 +83,11 @@ Type searchParametrizedType(Type typeToSearch, TypeVariable> typeVar) {
return matchedGenericType;
}
parameterizedSubclasses.push(parameterizedType);
- return searchParametrizedType(((Class) parameterizedType.getRawType()).getGenericSuperclass(), typeVar);
+ return searchParametrizedType(((Class>) parameterizedType.getRawType()).getGenericSuperclass(), typeVar);
}
- private Type checkSubclassRuntimeInfo(TypeVariable typeVar) {
- if (parameterizedSubclasses.size() == 0) {
+ private Type checkSubclassRuntimeInfo(TypeVariable> typeVar) {
+ if (parameterizedSubclasses.isEmpty()) {
return typeVar;
}
ParameterizedType parametrizedSubclass = parameterizedSubclasses.pop();
@@ -98,17 +98,21 @@ private Type searchRuntimeTypeArgument(ParameterizedType runtimeType, TypeVariab
if (ReflectionUtils.getRawType(runtimeType) != typeVar.getGenericDeclaration()) {
return null;
}
- TypeVariable[] bounds = typeVar.getGenericDeclaration().getTypeParameters();
- for (int i = 0; i < bounds.length; i++) {
- if (bounds[i].equals(typeVar)) {
- Type matchedGenericType = runtimeType.getActualTypeArguments()[i];
+ TypeVariable>[] bounds = typeVar.getGenericDeclaration().getTypeParameters();
+ Type[] actualTypeArguments = runtimeType.getActualTypeArguments();
+ int i = 0;
+
+ for (TypeVariable> bound : bounds) {
+ if (bound.equals(typeVar)) {
+ Type matchedGenericType = actualTypeArguments[i];
//Propagated generic types to another generic classes
if (matchedGenericType instanceof TypeVariable>) {
- return checkSubclassRuntimeInfo((TypeVariable) matchedGenericType);
+ return checkSubclassRuntimeInfo((TypeVariable>) matchedGenericType);
}
//found runtime matchedGenericType
return matchedGenericType;
}
+ i++;
}
return null;
}
@@ -120,6 +124,6 @@ private static ParameterizedType findParameterizedSuperclass(Type type) {
if (!(type instanceof Class)) {
throw new JsonbException(Messages.getMessage(MessageKeys.RESOLVE_PARAMETRIZED_TYPE, type));
}
- return findParameterizedSuperclass(((Class) type).getGenericSuperclass());
+ return findParameterizedSuperclass(((Class>) type).getGenericSuperclass());
}
}
diff --git a/src/main/java/org/eclipse/yasson/internal/components/AbstractComponentBinding.java b/src/main/java/org/eclipse/yasson/internal/components/AbstractComponentBinding.java
index f3be5887b..380c31fff 100644
--- a/src/main/java/org/eclipse/yasson/internal/components/AbstractComponentBinding.java
+++ b/src/main/java/org/eclipse/yasson/internal/components/AbstractComponentBinding.java
@@ -1,5 +1,5 @@
/*
- * Copyright (c) 2016, 2020 Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2016, 2024 Oracle and/or its affiliates. All rights reserved.
*
* This program and the accompanying materials are made available under the
* terms of the Eclipse Public License v. 2.0 which is available at
@@ -17,24 +17,31 @@
/**
* Wrapper for user components, components, (de)serializer.
- * Contains resolved binding type an component.
+ * Contains resolved binding type and component.
+ *
+ * @param type of component
*/
-public abstract class AbstractComponentBinding {
+public abstract class AbstractComponentBinding {
private final Type bindingType;
+ private final C component;
+
/**
* Creates info.
*
* @param bindingType type to which component is bound.
+ * @param component bound component.
*/
- public AbstractComponentBinding(Type bindingType) {
+ public AbstractComponentBinding(Type bindingType, C component) {
Objects.requireNonNull(bindingType);
+ Objects.requireNonNull(component);
this.bindingType = bindingType;
+ this.component = component;
}
/**
- * Resolved binding type of a component.
+ * Resolved binding type of the component.
*
* @return binding type
*/
@@ -42,10 +49,21 @@ public Type getBindingType() {
return bindingType;
}
+ /**
+ * Get actual user component.
+ *
+ * @return user component.
+ */
+ public C getComponent(){
+ return component;
+ }
+
/**
* Class of user component.
*
* @return component class
*/
- public abstract Class> getComponentClass();
+ public Class> getComponentClass(){
+ return component.getClass();
+ }
}
diff --git a/src/main/java/org/eclipse/yasson/internal/components/AdapterBinding.java b/src/main/java/org/eclipse/yasson/internal/components/AdapterBinding.java
index 16c57d7ae..3b8fbe785 100644
--- a/src/main/java/org/eclipse/yasson/internal/components/AdapterBinding.java
+++ b/src/main/java/org/eclipse/yasson/internal/components/AdapterBinding.java
@@ -1,5 +1,5 @@
/*
- * Copyright (c) 2016, 2020 Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2016, 2024 Oracle and/or its affiliates. All rights reserved.
*
* This program and the accompanying materials are made available under the
* terms of the Eclipse Public License v. 2.0 which is available at
@@ -19,13 +19,14 @@
/**
* Wrapper for JsonbAdapter generic information and an components itself.
+ *
+ * @param The type for the @{@link JsonbAdapter} that JSONB doesn't know how to handle.
+ * @param The type for the @{@link JsonbAdapter} that JSONB knows how to handle out of the box.
*/
-public class AdapterBinding extends AbstractComponentBinding {
+public class AdapterBinding extends AbstractComponentBinding> {
private final Type toType;
- private final JsonbAdapter, ?> adapter;
-
/**
* Adapter info with type to "adapt from", type to "adapt to" and an components itself.
*
@@ -33,17 +34,15 @@ public class AdapterBinding extends AbstractComponentBinding {
* @param toType to not null
* @param adapter components not null
*/
- public AdapterBinding(Type fromType, Type toType, JsonbAdapter, ?> adapter) {
- super(fromType);
+ public AdapterBinding(Type fromType, Type toType, JsonbAdapter adapter) {
+ super(fromType, adapter);
Objects.requireNonNull(toType);
- Objects.requireNonNull(adapter);
this.toType = toType;
- this.adapter = adapter;
}
/**
* Represents a type to which to adapt into.
- *
+ *
* During marshalling object property is adapted to this type and result is marshalled.
* During unmarshalling object is unmarshalled into this type first, than converted to field type and set.
*
@@ -52,18 +51,4 @@ public AdapterBinding(Type fromType, Type toType, JsonbAdapter, ?> adapter) {
public Type getToType() {
return toType;
}
-
- /**
- * Get actual components to adapt object value.
- *
- * @return components
- */
- public JsonbAdapter, ?> getAdapter() {
- return adapter;
- }
-
- @Override
- public Class> getComponentClass() {
- return adapter.getClass();
- }
}
diff --git a/src/main/java/org/eclipse/yasson/internal/components/BeanManagerInstanceCreator.java b/src/main/java/org/eclipse/yasson/internal/components/BeanManagerInstanceCreator.java
index 456015a06..3e6d542ff 100644
--- a/src/main/java/org/eclipse/yasson/internal/components/BeanManagerInstanceCreator.java
+++ b/src/main/java/org/eclipse/yasson/internal/components/BeanManagerInstanceCreator.java
@@ -1,5 +1,5 @@
/*
- * Copyright (c) 2016, 2022 Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2016, 2024 Oracle and/or its affiliates. All rights reserved.
*
* This program and the accompanying materials are made available under the
* terms of the Eclipse Public License v. 2.0 which is available at
@@ -31,7 +31,7 @@
* CDI instance manager.
* Instances are created and stored per instance of {@link JsonBinding}.
* Calling close on JsonBinding, cleans up Jsonb CDI instances and in case of "dependant" scope its dependencies.
- *
+ *
* CDI API dependency is optional, this class is never referenced / loaded if CDI API is not resolvable.
*/
public class BeanManagerInstanceCreator implements JsonbComponentInstanceCreator {
@@ -61,9 +61,9 @@ public BeanManagerInstanceCreator(Object beanManager) {
* @return New instance of bean class with injected content.
*/
@Override
- @SuppressWarnings("unchecked")
public T getOrCreateComponent(Class componentClass) {
- return (T) injectionTargets.computeIfAbsent(componentClass, clazz -> {
+ @SuppressWarnings("unchecked")
+ T instance = (T) injectionTargets.computeIfAbsent(componentClass, clazz -> {
final AnnotatedType aType = beanManager.createAnnotatedType(componentClass);
final InjectionTarget injectionTarget = beanManager.getInjectionTargetFactory(aType)
.createInjectionTarget(null);
@@ -71,8 +71,9 @@ public T getOrCreateComponent(Class componentClass) {
final T beanInstance = injectionTarget.produce(creationalContext);
injectionTarget.inject(beanInstance, creationalContext);
injectionTarget.postConstruct(beanInstance);
- return new CDIManagedBean(beanInstance, injectionTarget, creationalContext);
+ return new CDIManagedBean<>(beanInstance, injectionTarget, creationalContext);
}).getInstance();
+ return instance;
}
@Override
@@ -82,9 +83,16 @@ public void close() throws IOException {
}
private void cleanupBean(CDIManagedBean bean) {
- bean.getInjectionTarget().preDestroy(bean.getInstance());
- bean.getInjectionTarget().dispose(bean.getInstance());
- bean.getCreationalContext().release();
+ InjectionTarget injectionTarget = bean.getInjectionTarget();
+ if (injectionTarget != null) {
+ injectionTarget.preDestroy(bean.getInstance());
+ injectionTarget.dispose(bean.getInstance());
+ }
+
+ CreationalContext creationalContext = bean.getCreationalContext();
+ if (creationalContext != null) {
+ creationalContext.release();
+ }
}
/**
diff --git a/src/main/java/org/eclipse/yasson/internal/components/ComponentBindings.java b/src/main/java/org/eclipse/yasson/internal/components/ComponentBindings.java
index 3033bd5b0..020777d9c 100644
--- a/src/main/java/org/eclipse/yasson/internal/components/ComponentBindings.java
+++ b/src/main/java/org/eclipse/yasson/internal/components/ComponentBindings.java
@@ -1,5 +1,5 @@
/*
- * Copyright (c) 2016, 2020 Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2016, 2024 Oracle and/or its affiliates. All rights reserved.
*
* This program and the accompanying materials are made available under the
* terms of the Eclipse Public License v. 2.0 which is available at
@@ -13,19 +13,28 @@
package org.eclipse.yasson.internal.components;
import java.lang.reflect.Type;
+import java.util.Objects;
+
+import jakarta.json.bind.adapter.JsonbAdapter;
+import jakarta.json.bind.serializer.JsonbDeserializer;
+import jakarta.json.bind.serializer.JsonbSerializer;
/**
* Wrapper holding singleton instances of user defined components - Adapters, (De)Serializers.
+ *
+ * @param The type for the @{@link JsonbAdapter} that JSONB doesn't know how to handle.
+ * Also type for the @{@link JsonbSerializer} to serialize and for the @{@link JsonbDeserializer} to deserialize.
+ * @param The type for @{@link JsonbAdapter} that JSONB knows how to handle out of the box.
*/
-public class ComponentBindings {
+public class ComponentBindings {
private final Type bindingType;
- private final SerializerBinding serializer;
+ private final SerializerBinding serializerBinding;
- private final DeserializerBinding deserializer;
+ private final DeserializerBinding deserializerBinding;
- private final AdapterBinding adapterInfo;
+ private final AdapterBinding adapterBinding;
/**
* Construct empty bindings for a given type.
@@ -39,19 +48,53 @@ public ComponentBindings(Type bindingType) {
/**
* Creates an instance and populates it with bindings for a given type.
*
- * @param bindingType Type components are bound to.
- * @param serializer Serializer.
- * @param deserializer Deserializer.
- * @param adapter Adapter.
+ * @param bindingType Type components are bound to.
+ * @param serializerBinding Serializer.
+ * @param deserializerBinding Deserializer.
+ * @param adapterBinding Adapter.
*/
- public ComponentBindings(Type bindingType,
- SerializerBinding serializer,
- DeserializerBinding deserializer,
- AdapterBinding adapter) {
+ private ComponentBindings(Type bindingType,
+ SerializerBinding serializerBinding,
+ DeserializerBinding deserializerBinding,
+ AdapterBinding adapterBinding) {
+ Objects.requireNonNull(bindingType);
this.bindingType = bindingType;
- this.serializer = serializer;
- this.deserializer = deserializer;
- this.adapterInfo = adapter;
+ this.serializerBinding = serializerBinding;
+ this.deserializerBinding = deserializerBinding;
+ this.adapterBinding = adapterBinding;
+ }
+
+ /**
+ * Creates a copy of the given bindings and new serializer.
+ *
+ * @param bindings Deserializer and adapter will be copied from this instance.
+ * @param serializerBinding New serializer. The bound type for the copy will be also taken from this serializer.
+ */
+ public ComponentBindings(ComponentBindings bindings,
+ SerializerBinding serializerBinding) {
+ this(Objects.requireNonNull(serializerBinding).getBindingType(), serializerBinding, bindings.deserializerBinding, bindings.adapterBinding);
+ }
+
+ /**
+ * Creates a copy of the given bindings and new deserializer.
+ *
+ * @param bindings Serializer and adapter will be copied from this instance.
+ * @param deserializerBinding New deserializer. The bound type for the copy will be also taken from this deserializer.
+ */
+ public ComponentBindings(ComponentBindings bindings,
+ DeserializerBinding deserializerBinding) {
+ this(Objects.requireNonNull(deserializerBinding).getBindingType(), bindings.serializerBinding, deserializerBinding, bindings.adapterBinding);
+ }
+
+ /**
+ * Creates a copy of the given bindings and new adapter.
+ *
+ * @param bindings Serializer and serializer will be copied from this instance.
+ * @param adapterBinding New adapter. The bound type for the copy will be also taken from this adapter.
+ */
+ public ComponentBindings(ComponentBindings bindings,
+ AdapterBinding adapterBinding) {
+ this(Objects.requireNonNull(adapterBinding).getBindingType(), bindings.serializerBinding, bindings.deserializerBinding, adapterBinding);
}
/**
@@ -68,8 +111,8 @@ public Type getBindingType() {
*
* @return serializer
*/
- public SerializerBinding getSerializer() {
- return serializer;
+ public SerializerBinding getSerializerBinding() {
+ return serializerBinding;
}
/**
@@ -77,8 +120,8 @@ public SerializerBinding getSerializer() {
*
* @return deserializer
*/
- public DeserializerBinding getDeserializer() {
- return deserializer;
+ public DeserializerBinding getDeserializerBinding() {
+ return deserializerBinding;
}
/**
@@ -86,8 +129,8 @@ public DeserializerBinding getDeserializer() {
*
* @return adapterInfo
*/
- public AdapterBinding getAdapterInfo() {
- return adapterInfo;
+ public AdapterBinding getAdapterBinding() {
+ return adapterBinding;
}
}
diff --git a/src/main/java/org/eclipse/yasson/internal/components/DeserializerBinding.java b/src/main/java/org/eclipse/yasson/internal/components/DeserializerBinding.java
index b2ed21bb4..0518530ef 100644
--- a/src/main/java/org/eclipse/yasson/internal/components/DeserializerBinding.java
+++ b/src/main/java/org/eclipse/yasson/internal/components/DeserializerBinding.java
@@ -1,5 +1,5 @@
/*
- * Copyright (c) 2016, 2020 Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2016, 2024 Oracle and/or its affiliates. All rights reserved.
*
* This program and the accompanying materials are made available under the
* terms of the Eclipse Public License v. 2.0 which is available at
@@ -21,9 +21,7 @@
*
* @param type of contained deserializer
*/
-public class DeserializerBinding extends AbstractComponentBinding {
-
- private final JsonbDeserializer jsonbDeserializer;
+public class DeserializerBinding extends AbstractComponentBinding> {
/**
* Creates a new instance.
@@ -32,21 +30,6 @@ public class DeserializerBinding extends AbstractComponentBinding {
* @param jsonbDeserializer Deserializer.
*/
public DeserializerBinding(Type bindingType, JsonbDeserializer jsonbDeserializer) {
- super(bindingType);
- this.jsonbDeserializer = jsonbDeserializer;
- }
-
- /**
- * Gets deserializer if any.
- *
- * @return Deserializer.
- */
- public JsonbDeserializer getJsonbDeserializer() {
- return jsonbDeserializer;
- }
-
- @Override
- public Class> getComponentClass() {
- return jsonbDeserializer.getClass();
+ super(bindingType, jsonbDeserializer);
}
}
diff --git a/src/main/java/org/eclipse/yasson/internal/components/SerializerBinding.java b/src/main/java/org/eclipse/yasson/internal/components/SerializerBinding.java
index 6baafde34..19fe3778e 100644
--- a/src/main/java/org/eclipse/yasson/internal/components/SerializerBinding.java
+++ b/src/main/java/org/eclipse/yasson/internal/components/SerializerBinding.java
@@ -1,5 +1,5 @@
/*
- * Copyright (c) 2016, 2020 Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2016, 2024 Oracle and/or its affiliates. All rights reserved.
*
* This program and the accompanying materials are made available under the
* terms of the Eclipse Public License v. 2.0 which is available at
@@ -21,9 +21,7 @@
*
* @param type of jsonb serializer
*/
-public class SerializerBinding extends AbstractComponentBinding {
-
- private final JsonbSerializer jsonbSerializer;
+public class SerializerBinding extends AbstractComponentBinding> {
/**
* Creates a new instance.
@@ -32,26 +30,6 @@ public class SerializerBinding extends AbstractComponentBinding {
* @param jsonbSerializer Serializer. Can be null.
*/
public SerializerBinding(Type bindingType, JsonbSerializer jsonbSerializer) {
- super(bindingType);
- this.jsonbSerializer = jsonbSerializer;
- }
-
- /**
- * Returns a serializer if any.
- *
- * @return Serializer.
- */
- public JsonbSerializer getJsonbSerializer() {
- return jsonbSerializer;
- }
-
- /**
- * Class of user component.
- *
- * @return Component class.
- */
- @Override
- public Class> getComponentClass() {
- return jsonbSerializer.getClass();
+ super(bindingType, jsonbSerializer);
}
}
diff --git a/src/main/java/org/eclipse/yasson/internal/deserializer/AdapterDeserializer.java b/src/main/java/org/eclipse/yasson/internal/deserializer/AdapterDeserializer.java
index b54e72ab7..9c97ec2bf 100644
--- a/src/main/java/org/eclipse/yasson/internal/deserializer/AdapterDeserializer.java
+++ b/src/main/java/org/eclipse/yasson/internal/deserializer/AdapterDeserializer.java
@@ -1,5 +1,5 @@
/*
- * Copyright (c) 2021, 2022 Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2021, 2024 Oracle and/or its affiliates. All rights reserved.
*
* This program and the accompanying materials are made available under the
* terms of the Eclipse Public License v. 2.0 which is available at
@@ -26,14 +26,14 @@
class AdapterDeserializer implements ModelDeserializer