From 6cdcb8a6934b05e0cb44dfef9bb114c3b0170eb0 Mon Sep 17 00:00:00 2001 From: Fabrizio Cucci Date: Mon, 25 Sep 2017 22:21:15 +0100 Subject: [PATCH] Register providers added in `Feature`s Because providers registered in `Feature`s were not considered, registering a HK2 binder in a `Feature` didn't work. This fixes #3675. --- .../jersey/model/internal/CommonConfig.java | 54 ++++++++++--------- 1 file changed, 30 insertions(+), 24 deletions(-) diff --git a/core-common/src/main/java/org/glassfish/jersey/model/internal/CommonConfig.java b/core-common/src/main/java/org/glassfish/jersey/model/internal/CommonConfig.java index 34d3d31bdb..6937d9146d 100644 --- a/core-common/src/main/java/org/glassfish/jersey/model/internal/CommonConfig.java +++ b/core-common/src/main/java/org/glassfish/jersey/model/internal/CommonConfig.java @@ -52,12 +52,14 @@ import java.util.Map; import java.util.Set; import java.util.TreeSet; +import java.util.function.Consumer; import java.util.function.Function; import java.util.function.Predicate; import java.util.logging.Level; import java.util.logging.Logger; import java.util.stream.Collectors; +import javax.annotation.Priority; import javax.ws.rs.ConstrainedTo; import javax.ws.rs.Priorities; import javax.ws.rs.RuntimeType; @@ -65,13 +67,10 @@ import javax.ws.rs.core.Feature; import javax.ws.rs.core.FeatureContext; -import javax.annotation.Priority; - import org.glassfish.jersey.ExtendedConfig; import org.glassfish.jersey.internal.LocalizationMessages; import org.glassfish.jersey.internal.ServiceFinder; import org.glassfish.jersey.internal.inject.Binder; -import org.glassfish.jersey.internal.inject.CompositeBinder; import org.glassfish.jersey.internal.inject.InjectionManager; import org.glassfish.jersey.internal.spi.AutoDiscoverable; import org.glassfish.jersey.internal.spi.ForcedAutoDiscoverable; @@ -625,45 +624,52 @@ public void configureAutoDiscoverableProviders(final InjectionManager injectionM */ public void configureMetaProviders(InjectionManager injectionManager, ManagedObjectsFinalizer finalizer) { // First, configure existing binders - Set configuredBinders = configureBinders(injectionManager, Collections.emptySet()); + Set registeredBinders = registerBinders(injectionManager, Collections.emptySet()); // Check whether meta providers have been initialized for a config this config has been loaded from. if (!disableMetaProviderConfiguration) { // Register external meta objects - configureExternalObjects(injectionManager); + Set registeredExternalObjects = registerExternalObjects(injectionManager, Collections.emptySet()); // Next, configure all features configureFeatures(injectionManager, new HashSet<>(), resetRegistrations(), finalizer); - // At last, configure any new binders added by features - configureBinders(injectionManager, configuredBinders); + // At last, configure any new binders and external meta objects added by features + registerBinders(injectionManager, registeredBinders); + registerExternalObjects(injectionManager, registeredExternalObjects); } } - private Set configureBinders(InjectionManager injectionManager, Set configured) { - Set allConfigured = Collections.newSetFromMap(new IdentityHashMap<>()); - allConfigured.addAll(configured); - - Collection binders = getBinder(configured); - if (!binders.isEmpty()) { - injectionManager.register(CompositeBinder.wrap(binders)); - allConfigured.addAll(binders); - } + private Set registerBinders(InjectionManager injectionManager, Set registeredBinders) { + return register(injectionManager::register, registeredBinders, getBinders()); + } - return allConfigured; + private Set registerExternalObjects(InjectionManager injectionManager, Set registeredExternalObjects) { + return register(injectionManager::register, registeredExternalObjects, getExternalObjects(injectionManager)); } - private Collection getBinder(Set configured) { + private Collection getBinders() { return componentBag.getInstances(ComponentBag.BINDERS_ONLY) .stream() .map(CAST_TO_BINDER) - .filter(binder -> !configured.contains(binder)) .collect(Collectors.toList()); } - private void configureExternalObjects(InjectionManager injectionManager) { - componentBag.getInstances(model -> ComponentBag.EXTERNAL_ONLY.test(model, injectionManager)) - .forEach(injectionManager::register); - componentBag.getClasses(model -> ComponentBag.EXTERNAL_ONLY.test(model, injectionManager)) - .forEach(injectionManager::register); + private Collection getExternalObjects(InjectionManager injectionManager) { + List externalObjects = new ArrayList<>(); + externalObjects.addAll(componentBag.getClasses(model -> ComponentBag.EXTERNAL_ONLY.test(model, injectionManager))); + externalObjects.addAll(componentBag.getInstances(model -> ComponentBag.EXTERNAL_ONLY.test(model, injectionManager))); + return externalObjects; + } + + private Set register(Consumer register, Set registered, Collection registrables) { + + registrables.stream() + .filter(registrable -> !registered.contains(registrable)) + .forEach(register); + + Set newRegistered = Collections.newSetFromMap(new IdentityHashMap<>()); + newRegistered.addAll(registered); + newRegistered.addAll(registrables); + return newRegistered; } private void configureFeatures(InjectionManager injectionManager,