Skip to content

Commit

Permalink
Merge pull request #31702 from Ladicek/arc-fixes
Browse files Browse the repository at this point in the history
ArC fixes for spec compatibility, round 5
  • Loading branch information
Ladicek authored Mar 13, 2023
2 parents d65ba11 + a7a8c9e commit bb39d26
Show file tree
Hide file tree
Showing 62 changed files with 1,663 additions and 198 deletions.
34 changes: 31 additions & 3 deletions docs/src/main/asciidoc/cdi-reference.adoc
Original file line number Diff line number Diff line change
Expand Up @@ -11,9 +11,10 @@ include::_attributes.adoc[]
:sectnums:
:sectnumlevels: 4

Quarkus DI solution (also called ArC) is based on the https://jakarta.ee/specifications/cdi/2.0/cdi-spec-2.0.html[Contexts and Dependency Injection for Java 2.0, window="_blank"] specification.
However, it is not a full CDI implementation verified by the TCK.
Only a subset of the CDI features is implemented - see also <<supported_features,the list of supported features>> and <<limitations,the list of limitations>>.
Quarkus DI solution (also called ArC) is based on the https://jakarta.ee/specifications/cdi/4.0/jakarta-cdi-spec-4.0.html[Jakarta Contexts and Dependency Injection 4.0, window="_blank"] specification.
It aims to implement the CDI Lite specification, with selected improvements on top.
It is not a CDI Full implementation and is not verified by the TCK yet.
See also <<supported_features,the list of supported features>> and <<limitations,the list of limitations>>.
TIP: If you're new to CDI then we recommend you to read the xref:cdi.adoc[Introduction to CDI] first.
Expand Down Expand Up @@ -741,6 +742,7 @@ class Services {
+
NOTE: Interceptors can use `InvocationContext.getMethod()` to detect static methods and adjust the behavior accordingly.

[[unproxyable_classes_transformation]]
=== Ability to handle 'final' classes and methods

In normal CDI, classes that are marked as `final` and / or have `final` methods are not eligible for proxy creation,
Expand Down Expand Up @@ -1081,6 +1083,32 @@ NOTE: These endpoints are only available in the development mode, i.e. when you
In the development mode, it is also possible to enable monitoring of business method invocations and fired events.
Simply set the `quarkus.arc.dev-mode.monitoring-enabled` configuration property to `true` and explore the relevant Dev UI pages.

[[strict_mode]]
== Strict Mode

By default, ArC does not perform all validations required by the CDI specification.
It also improves CDI usability in many ways, some of them being directly against the specification.

To be able to eventually pass the CDI Lite TCK, ArC also has a _strict_ mode.
This mode enables additional validations and disables certain improvements that conflict with the specification.

To enable the strict mode, use the following configuration:

[source,properties]
----
quarkus.arc.strict-compatibility=true
----

Some other features affect specification compatibility as well:

* <<unproxyable_classes_transformation,Transformation of unproxyable classes>>
* <<remove_unused_beans,Unused beans removal>>

To get a behavior closer to the specification, these features should also be disabled.

Applications are recommended to use the default, non-strict mode, which makes CDI more convenient to use.
The "strictness" of the strict mode (the set of additional validations and the set of disabled improvements on top of the CDI specification) may change over time.

[[arc-configuration-reference]]
== ArC Configuration Reference

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -177,6 +177,22 @@ public class ArcConfig {
@ConfigItem(defaultValue = "true")
public boolean detectWrongAnnotations;

/**
* If set to {@code true}, the container will perform additional validations mandated by the CDI specification.
* Some improvements on top of the CDI specification may be disabled. Applications that work as expected
* in the strict mode should work without a change in the default, non-strict mode.
* <p>
* The strict mode is mainly introduced to allow passing the CDI Lite TCK. Applications are recommended
* to use the default, non-strict mode, which makes CDI more convenient to use. The "strictness" of
* the strict mode (the set of additional validations and the set of disabled improvements on top of
* the CDI specification) may change over time.
* <p>
* Note that {@link #transformUnproxyableClasses} and {@link #removeUnusedBeans} also has effect on specification
* compatibility. You may want to disable these features to get behavior closer to the specification.
*/
@ConfigItem(defaultValue = "false")
public boolean strictCompatibility;

/**
* Dev mode configuration.
*/
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -373,6 +373,7 @@ public boolean test(BeanInfo bean) {
builder.setJtaCapabilities(capabilities.isPresent(Capability.TRANSACTIONS));
builder.setGenerateSources(BootstrapDebug.DEBUG_SOURCES_DIR != null);
builder.setAllowMocking(launchModeBuildItem.getLaunchMode() == LaunchMode.TEST);
builder.setStrictCompatibility(arcConfig.strictCompatibility);

if (arcConfig.selectedAlternatives.isPresent()) {
final List<Predicate<ClassInfo>> selectedAlternatives = initClassPredicates(
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -129,6 +129,9 @@ private void generate() throws IOException, ExecutionException, InterruptedExcep
Thread.currentThread().getContextClassLoader(), new ConcurrentHashMap<>(),
beanArchiveIndex))
.setApplicationIndex(applicationIndex)
.setStrictCompatibility(true)
.setTransformUnproxyableClasses(false)
.setRemoveUnusedBeans(false)
.setBuildCompatibleExtensions(buildCompatibleExtensions)
.setAdditionalBeanDefiningAnnotations(Set.of(new BeanDefiningAnnotation(
DotName.createSimple(ExtraBean.class.getName()), null)))
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -43,11 +43,6 @@
<exclude name="testContextualDestroyCatchesException"/>
</methods>
</class>
<class name="org.jboss.cdi.tck.tests.implementation.initializer.broken.generic.GenericInitializerMethodTest">
<methods>
<exclude name="testGenericInitializerMethodNotAllowed"/>
</methods>
</class>
<class name="org.jboss.cdi.tck.interceptors.tests.contract.lifecycleCallback.LifecycleCallbackInterceptorTest">
<methods>
<exclude name="testPostConstructInterceptor"/>
Expand All @@ -61,11 +56,6 @@
<exclude name="testPublicLifecycleInterceptorMethod"/>
</methods>
</class>
<class name="org.jboss.cdi.tck.tests.implementation.disposal.method.definition.broken.unresolvedMethod.UnresolvedDisposalMethodDefinitionTest">
<methods>
<exclude name="testUnresolvedDisposalMethod"/>
</methods>
</class>
<class name="org.jboss.cdi.tck.interceptors.tests.contract.invocationContext.InvocationContextTest">
<methods>
<exclude name="testGetTargetMethod"/>
Expand All @@ -85,16 +75,6 @@
<exclude name="testTooManyScopesSpecifiedInJava"/>
</methods>
</class>
<class name="org.jboss.cdi.tck.tests.implementation.producer.method.broken.parameterizedTypeWithTypeParameter.ParameterizedReturnTypeWithTypeVariableTest">
<methods>
<exclude name="testNonDependentScopedProducerMethodWithParameterizedTypeWithTypeVariable"/>
</methods>
</class>
<class name="org.jboss.cdi.tck.tests.interceptors.definition.broken.nonDependent.NonDependentInterceptorTest">
<methods>
<exclude name="testDeploymentWithScopedInterceptor"/>
</methods>
</class>
<class name="org.jboss.cdi.tck.interceptors.tests.contract.lifecycleCallback.exceptions.LifecycleCallbackInterceptorExceptionTest">
<methods>
<exclude name="testLifecycleCallbackInterceptorCanCatchException"/>
Expand Down Expand Up @@ -165,20 +145,6 @@
<exclude name="testExceptions"/>
</methods>
</class>
<class name="org.jboss.cdi.tck.tests.interceptors.invocation.InterceptorInvocationTest">
<methods>
<exclude name="testDisposerMethodsAreIntercepted"/>
<exclude name="testInitializerMethodsNotIntercepted"/>
<exclude name="testProducerMethodsAreIntercepted"/>
<exclude name="testLifecycleCallbacksAreIntercepted"/>
<exclude name="testObjectMethodsAreNotIntercepted"/>
</methods>
</class>
<class name="org.jboss.cdi.tck.tests.lookup.byname.broken.prefix.ExpandedNamePrefix2Test">
<methods>
<exclude name="testDuplicateBeanNamePrefix"/>
</methods>
</class>
<class name="org.jboss.cdi.tck.interceptors.tests.bindings.broken.InvalidTransitiveInterceptorBindingAnnotationsTest">
<methods>
<exclude name="testInterceptorBindingsWithConflictingAnnotationMembersNotOk"/>
Expand Down Expand Up @@ -214,11 +180,6 @@
<exclude name="testDeploymentFails"/>
</methods>
</class>
<class name="org.jboss.cdi.tck.tests.implementation.producer.method.broken.parameterizedTypeWithTypeParameter.ParametrizedReturnTypeWithTypeVariable02Test">
<methods>
<exclude name="testNonDependentScopedProducerMethodWithParameterizedTypeWithTypeVariable"/>
</methods>
</class>
<class name="org.jboss.cdi.tck.tests.definition.scope.ScopeDefinitionTest">
<methods>
<exclude name="testScopeTypeHasCorrectTarget"/>
Expand All @@ -239,11 +200,6 @@
<exclude name="testGetInjectableReferenceOnBeanManager"/>
</methods>
</class>
<class name="org.jboss.cdi.tck.tests.interceptors.definition.broken.observer.async.InterceptorWithAsyncObserverMethodTest">
<methods>
<exclude name="testInterceptorWithAsyncObserverMethodNotOk"/>
</methods>
</class>
<class name="org.jboss.cdi.tck.interceptors.tests.order.aroundInvoke.AroundInvokeOrderTest">
<methods>
<exclude name="testInvocationOrder"/>
Expand Down Expand Up @@ -281,11 +237,6 @@
<exclude name="testDeploymentFails"/>
</methods>
</class>
<class name="org.jboss.cdi.tck.tests.lookup.clientProxy.unproxyable.finalMethod.PublicFinalMethodNotProxyableTest">
<methods>
<exclude name="testClassWithPublicFinalMethodCannotBeProxied"/>
</methods>
</class>
<class name="org.jboss.cdi.tck.tests.implementation.builtin.metadata.broken.typeparam.BeanTypeParamFieldTest">
<methods>
<exclude name="testDeploymentFails"/>
Expand All @@ -306,11 +257,6 @@
<exclude name="testAbstractClassDeclaredInJavaNotDiscovered"/>
</methods>
</class>
<class name="org.jboss.cdi.tck.tests.lookup.clientProxy.unproxyable.finalMethod.ProtectedFinalMethodNotProxyableTest">
<methods>
<exclude name="testClassWithPublicFinalMethodCannotBeProxied"/>
</methods>
</class>
<class name="org.jboss.cdi.tck.interceptors.tests.bindings.aroundConstruct.ConstructorInterceptionTest">
<methods>
<exclude name="testTypeLevelAndConstructorLevelBinding"/>
Expand Down Expand Up @@ -382,27 +328,6 @@
<exclude name="testMultipleLifecycleInterceptors"/>
</methods>
</class>
<class name="org.jboss.cdi.tck.tests.lookup.byname.broken.prefix.NamePrefixTest">
<methods>
<exclude name="testDuplicateBeanNamePrefix"/>
</methods>
</class>
<class name="org.jboss.cdi.tck.tests.lookup.clientProxy.unproxyable.finalMethod.NonPrivateNonStaticSuperclassMethodTest">
<methods>
<exclude name="testClassWithPublicFinalMethodCannotBeProxied"/>
</methods>
</class>
<class name="org.jboss.cdi.tck.tests.implementation.simple.definition.dependentWithPublicField.DependentWithPublicFieldTest">
<methods>
<exclude name="testNonDependentScopedBeanCanNotHavePublicField"/>
</methods>
</class>
<class name="org.jboss.cdi.tck.tests.event.observer.wildcardAndTypeVariable.ObserverMethodWithParametertizedTypeTest">
<methods>
<exclude name="testObserverMethodCanObserveArrayWildcard"/>
<exclude name="testObserverMethodCanObserveArrayTypeVariable"/>
</methods>
</class>
<class name="org.jboss.cdi.tck.tests.interceptors.definition.interceptorOrder.InterceptorOrderTest">
<methods>
<exclude name="testInterceptorsInvocationOrder"/>
Expand Down Expand Up @@ -433,11 +358,6 @@
<exclude name="testEventFireThrowsExceptionIfEventObjectTypeContainsUnresovableTypeVariable"/>
</methods>
</class>
<class name="org.jboss.cdi.tck.tests.lookup.clientProxy.unproxyable.finalMethod.PackagePrivateFinalMethodNotProxyableTest">
<methods>
<exclude name="testClassWithPublicFinalMethodCannotBeProxied"/>
</methods>
</class>
<class name="org.jboss.cdi.tck.tests.interceptors.definition.InterceptorDefinitionTest">
<methods>
<exclude name="testInstanceOfInterceptorForEveryEnabledInterceptor"/>
Expand All @@ -449,27 +369,14 @@
</class>
<class name="org.jboss.cdi.tck.tests.inheritance.generics.MemberLevelInheritanceTest">
<methods>
<exclude name="testObserverResolution"/>
<exclude name="testObserver"/>
<exclude name="testInjectionPoint"/>
<exclude name="testInjectionPointDefinition"/>
</methods>
</class>
<class name="org.jboss.cdi.tck.tests.lookup.byname.broken.prefix.ExpandedNamePrefixTest">
<methods>
<exclude name="testDuplicateBeanNamePrefix"/>
</methods>
</class>
<class name="org.jboss.cdi.tck.tests.definition.scope.inOtherBda.ScopeDefinedInOtherBDATest">
<methods>
<exclude name="testCustomScopeInOtherBDAisBeanDefiningAnnotation"/>
</methods>
</class>
<class name="org.jboss.cdi.tck.tests.interceptors.definition.broken.observer.InterceptorWithObserverMethodTest">
<methods>
<exclude name="testInterceptorWithObserverMethodNotOk"/>
</methods>
</class>
<class name="org.jboss.cdi.tck.tests.implementation.builtin.metadata.broken.injection.intercepted.InterceptedBeanFieldInjectionTest">
<methods>
<exclude name="testDeploymentFails"/>
Expand Down Expand Up @@ -508,11 +415,6 @@
<exclude name="testDeploymentFails"/>
</methods>
</class>
<class name="org.jboss.cdi.tck.tests.implementation.producer.field.definition.broken.typeVariable2.RequestScopedProducerFieldWithTypeVariableTest">
<methods>
<exclude name="testRequestScopedProducerFieldParameterizedWithTypeVariableNotAllowed"/>
</methods>
</class>
<class name="org.jboss.cdi.tck.tests.event.observer.ObserverNotificationTest">
<methods>
<exclude name="testObserverMethodNotInvokedIfNoActiveContext"/>
Expand Down
Loading

0 comments on commit bb39d26

Please sign in to comment.