Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

How to solve NoSuchMethodError for javax.validation when deploying a spring boot application in weblogic server?

I am trying to deploy a simple spring boot application that will expose some rest api and I use hibernate entity manager to manipulate entity objects. When I try to deploy this application to Oracle Weblogic 12c, I get the following exception:

<Jan 11, 2016 6:20:14 PM BDT> <Error> <Console> <BEA-240003> <Administration Console encountered the following error: weblogic.application.ModuleException: java.lang.NoSuchMethodError: javax.validation.spi.ConfigurationState.getParameterNameProvider()Ljavax/validation/ParameterNameProvider;
at weblogic.application.internal.ExtensibleModuleWrapper.start(ExtensibleModuleWrapper.java:140)
at weblogic.application.internal.flow.ModuleListenerInvoker.start(ModuleListenerInvoker.java:124)
at weblogic.application.internal.flow.ModuleStateDriver$3.next(ModuleStateDriver.java:216)
at weblogic.application.internal.flow.ModuleStateDriver$3.next(ModuleStateDriver.java:211)
at weblogic.application.utils.StateMachineDriver.nextState(StateMachineDriver.java:42)
at weblogic.application.internal.flow.ModuleStateDriver.start(ModuleStateDriver.java:73)
at weblogic.application.internal.flow.StartModulesFlow.activate(StartModulesFlow.java:24)
at weblogic.application.internal.BaseDeployment$2.next(BaseDeployment.java:729)
at weblogic.application.utils.StateMachineDriver.nextState(StateMachineDriver.java:42)
at weblogic.application.internal.BaseDeployment.activate(BaseDeployment.java:258)
at weblogic.application.internal.SingleModuleDeployment.activate(SingleModuleDeployment.java:48)
at weblogic.application.internal.DeploymentStateChecker.activate(DeploymentStateChecker.java:165)
at weblogic.deploy.internal.targetserver.AppContainerInvoker.activate(AppContainerInvoker.java:80)
at weblogic.deploy.internal.targetserver.operations.AbstractOperation.activate(AbstractOperation.java:587)
at weblogic.deploy.internal.targetserver.operations.ActivateOperation.activateDeployment(ActivateOperation.java:150)
at weblogic.deploy.internal.targetserver.operations.ActivateOperation.doCommit(ActivateOperation.java:116)
at weblogic.deploy.internal.targetserver.operations.AbstractOperation.commit(AbstractOperation.java:339)
at weblogic.deploy.internal.targetserver.DeploymentManager.handleDeploymentCommit(DeploymentManager.java:846)
at weblogic.deploy.internal.targetserver.DeploymentManager.activateDeploymentList(DeploymentManager.java:1275)
at weblogic.deploy.internal.targetserver.DeploymentManager.handleCommit(DeploymentManager.java:442)
at weblogic.deploy.internal.targetserver.DeploymentServiceDispatcher.commit(DeploymentServiceDispatcher.java:176)
at weblogic.deploy.service.internal.targetserver.DeploymentReceiverCallbackDeliverer.doCommitCallback(DeploymentReceiverCallbackDeliverer.java:195)
at weblogic.deploy.service.internal.targetserver.DeploymentReceiverCallbackDeliverer.access$100(DeploymentReceiverCallbackDeliverer.java:13)
at weblogic.deploy.service.internal.targetserver.DeploymentReceiverCallbackDeliverer$2.run(DeploymentReceiverCallbackDeliverer.java:68)
at weblogic.work.SelfTuningWorkManagerImpl$WorkAdapterImpl.run(SelfTuningWorkManagerImpl.java:548)
at weblogic.work.ExecuteThread.execute(ExecuteThread.java:311)
at weblogic.work.ExecuteThread.run(ExecuteThread.java:263)
Caused by: java.lang.NoSuchMethodError: javax.validation.spi.ConfigurationState.getParameterNameProvider()Ljavax/validation/ParameterNameProvider;
at org.hibernate.validator.internal.engine.ValidatorFactoryImpl.<init>(ValidatorFactoryImpl.java:142)
at org.hibernate.validator.HibernateValidator.buildValidatorFactory(HibernateValidator.java:35)
at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:57)
at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
at java.lang.reflect.Method.invoke(Method.java:606)
at weblogic.validation.validator.ValidationProvider.invoke(ValidationProvider.java:75)
at weblogic.validation.validator.ValidationProvider.buildValidatorFactory(ValidationProvider.java:66)
at org.hibernate.validator.internal.engine.ConfigurationImpl.buildValidatorFactory(ConfigurationImpl.java:302)
.... rest of the stack trace has been omitted ....

In short, I am getting

java.lang.NoSuchMethodError: javax.validation.spi.ConfigurationState.getParameterNameProvider()Ljavax/validation/ParameterNameProvider;

I have gone through similar questions about this problem in stack overflow (like this, and, this), but could not fix the problem. I tried tweaking dependencies on hibernate-validator and javax validation api, but it did not help much. Here is some relevant part of my pom file:

    <dependency>
        <groupId>javax.validation</groupId>
        <artifactId>validation-api</artifactId>
        <version>1.1.0.Final</version>
    </dependency>

    <dependency>
        <groupId>org.hibernate</groupId>
        <artifactId>hibernate-core</artifactId>
        <version>5.0.6.Final</version>
    </dependency>

    <dependency>
        <groupId>org.hibernate</groupId>
        <artifactId>hibernate-entitymanager</artifactId>
        <version>5.0.6.Final</version>
    </dependency>

    <dependency>
        <groupId>org.hibernate</groupId>
        <artifactId>hibernate-validator</artifactId>
        <version>5.2.2.Final</version>
    </dependency>

    <dependency>
        <groupId>org.hibernate</groupId>
        <artifactId>hibernate-validator-annotation-processor</artifactId>
        <version>5.2.2.Final</version>
    </dependency>

And my WEB-INF/weblogic.xml file:

<?xml version="1.0" encoding="UTF-8"?>
<weblogic-web-app xmlns="http://www.bea.com/ns/weblogic/90"
              xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
              xsi:schemaLocation="http://www.bea.com/ns/weblogic/90
              http://www.bea.com/ns/weblogic/90/weblogic-web-app.xsd">

    <container-descriptor>
        <prefer-web-inf-classes>true</prefer-web-inf-classes>
        <show-archived-real-path-enabled>true</show-archived-real-path-enabled>
    </container-descriptor>

</weblogic-web-app>

The only validation annotation I have used so far is @NotNull (javax.validation.constraints.NotNull). WebLogic Server Version: 12.1.3.0.0 running on Java7.

PS: The project runs fine in Tomcat 8.

like image 482
Zobayer Hasan Avatar asked Dec 02 '22 15:12

Zobayer Hasan


2 Answers

Finally I was able to solve the problem. I wasn't aware of the fact that if prefer-web-inf-classes is disabled from Weblogic admin console, then weblogic ignores the directive specified in weblogic.xml file.

From Oracle's documentation:

The prefer-web-inf-classes element, if set to true, will cause classes located in the WEB-INF directory of a Web application to be loaded in preference to classes loaded in the application or system classloader. The default value is false. A value specified in the Administration Console will take precedence over a value set manually.

So, instead, I had to specify prefer-application-packages in weblogic.xml file. Here is the updated content of the file:

<?xml version="1.0" encoding="UTF-8"?>
<weblogic-web-app xmlns:wls="http://xmlns.oracle.com/weblogic/weblogic-web-app"
    xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
    xsi:schemaLocation="http://java.sun.com/xml/ns/javaee
    http://java.sun.com/xml/ns/javaee/ejb-jar_3_0.xsd
    http://xmlns.oracle.com/weblogic/weblogic-web-app
    http://xmlns.oracle.com/weblogic/weblogic-web-app/1.4/weblogic-web-app.xsd">

<wls:container-descriptor>
    <wls:prefer-application-packages>
        <package-name>org.springframework.*</package-name>
        <package-name>org.hibernate.*</package-name>
        <package-name>javax.validation.*</package-name>
        <package-name>javax.validation.spi.*</package-name>
        <package-name>org.slf4j.*</package-name>
    </wls:prefer-application-packages>
    <wls:show-archived-real-path-enabled>true</wls:show-archived-real-path-enabled>
</wls:container-descriptor>

</weblogic-web-app>

This stackoverflow post was quite helpful.

Thanks to everyone who tried to help.

like image 79
Zobayer Hasan Avatar answered Dec 21 '22 14:12

Zobayer Hasan


My guess is that Weblogic is using Bean Validation 1.0 which aligns with Hibernate Validator 4.x. I am not sure how to get Weblogic to use Bean Validation as bundled in your app (maybe that's what you try to do with prefer-web-inf-classes) or how to upgrade the whole app server to Bean Validation 1.1. Unless you are using method validation, you could try to use the latest 4.x release (4.3.2.Final). You would then remove the validation-api dependency from the pom (will be pulled in transitively anyways) or you set it to 1.0.0.GA.

like image 20
Hardy Avatar answered Dec 21 '22 12:12

Hardy