Annotation-specified bean name conflicts with existing, non-compatible bean definition - java

I'm using Spring 2.5.4 and am creating a Java application that I'm deploying onto Weblogic.
I have a class in an external library (which included in the WEB-INF/classes directory of the resulting WAR file of my application) that I want to use in my code. I've created an instance variable for an object of the class in my code and added the #Autowired annotation and a getter and setter. In my application context file I have declared a bean of the library class' type and added the following:
<context:annotation-config />
<context:component-scan base-package="com.mycompany" />
... in order to register an AutowiredAnnotationBeanPostProcessor that will scan the classes and process the annotation.
When I try and deploy the application, I get the following error:
java.lang.IllegalStateException: Annotation-specified bean name 'myBean' for bean
class [com.mycompany.package.ClassName] conflicts with existing, non-compatible
bean definition of same name and class [com.mycompany.otherPackage.ClassName]
I think this is because there's a class in the library which has the same name as one in my application code (both class' package names start with "com.mycompany"). Nb. this is NOT the class that I have added, but a different one. Is there any way I can circumvent this problem without changing the name of the class in my application?
Thanks for any assistance.

Old question but throwing my 2c of bad experience with similar problem.
If you have 2 classes with same name, but in different packages was there a time when you had your other class referenced by the failing Spring context? If so, I'd recommend to clean the AS cached files (typically the place where the WAR is extracted), clean/rebuild your WAR and deploy again. Restarting the app server is also recommended.
I found that application servers and web containers alike (Weblogic, WAS, Jboss, Tomcat) tend to leave behind the old classes and when application is deployed those stale .class files are loaded in JVM via some old references, which most of the time messes up the Spring context loader.
Typical scenario is when you have renamed/moved a class from one package to another, or even kept the package name the same but moved it to another module (jar). In such cases cached (left over) files in the AS work directory can cause big headaches. Wiping out the work directory in your AS should resolve the issue outright.

You should use #qualifier to avoid this kind of conflict please refer section 3.9.3.

I fixed the problem by removing the autowiring completely and accessing the bean by explicitly creating a reference to it through the application context and the getBean() method.

This would better fit as a comment to #Pavel Lechev's answer, but I don't have enough rep to comment yet.
For other's finding this, here's what I did to solve this problem. I am using Wildfly 9.0.2.Final and, IntelliJ IDEA 2016.1.3 Build #IU-145.1617. These steps should presumably work with JBoss as well.
Stop Wildfly server.
Navigate to $WILDFLY_HOME/standalone/. Delete the three following folders: lib/, log/ and temp/.
In IntelliJ, Build > Build Artifacts > All Artifacts > Clean (or just the artifacts you are deploying).
In IntelliJ, Build > Rebuild Project
Restart Wildfly and redeploy your artifact(s).
These steps remedied my issue of duplicate bean names detected in the Spring context after refactoring a package name upstream from a couple of Controllers.

Related

Using SpringExtension with Tomcat and Hibernate web app

We are trying to use spring-test's SpringExtension to write integration tests for our Spring and Hibernate-based Tomcat web application. Our sessionFactory bean configuration has the property configured mappingJarLocations with a sample value as /WEB-INF/lib/company-common*.jar which contains hibernate mapping files. In both actual deployment and Eclipse dev deployment, this works fine as the docBasePath (in Servlet environment) is appended to this pattern and the files are getting resolved. But this is not the case while running JUnit test cases either in a local or a CI environment.
We tried our best to use the provided support by having few overridden implementations of WebTestContextBootstraper, GenricXmlWebContextLoader, XmlWebApplicationContext, and WebDelegatingSmartContextLoader but had to finally give up as we cannot override the final method org.springframework.test.context.web.AbstractGenericWebContextLoader.loadContext(MergedContextConfiguration) to provide the custom implementation of XmlWebApplicationContext. Our current approach is to manually create the application context and use it in the tests.
Here is the project structure:
Project_WebApp
|--src/**
|--WebContent/**
|--pom.xml
When the app is packaged as Project_WebApp.war, the dependencies are inside WEB-INF/lib from the root of extracted war. When deployed as a webapp in Tomcat using Eclipse, the dependencies are copied to <Eclipse_Workspace_Dir>/.metadata/.plugins/org.eclipse.wst.server.core/tmp0/Project_WebApp/WEB-INF/lib. In both cases, the dependencies are available at <Resource_Base_Path>/WEB-INF/lib and Resource_Base_Path has no relation to Project_WebApp base directory.
Questions:
Did any one use SpringExtension in a scenario similar to above? If so can you suggest any alternative approaches?
Instead of /WEB-INF/lib/company-common*.jar, we tried a classpath-based pattern but didn't work as the obtained class path resources don't match the pattern. Is there anything else to try here?

ambiguous mapping while deploying

I'm using Jenkins 1.6.20 (Git Client Plugin 1.18.0, Git Plugin 2.4.0) to get the Java application code from bitbucket.org and deploy it to Apache Tomcat 8.0.23.
The error appears while deploying and looks like:
org.springframework.beans.factory.BeanCreationException: Error creating bean with name 'requestMappingHandlerMapping' defined in class path resource [org/spr$
public java.util.List by.ipps.accounting.ws.PositionWS.getEmployeePost(java.lang.Long)
to {[/positionListJson/{id}],methods=[GET],params=[],headers=[],consumes=[],produces=[application/json],custom=[]}: There is already 'resourceWS' bean method
public by.ipps.accounting.model.Employee.EmployeePost by.ipps.accounting.ws.ResourceWS.getEmployeePost(java.lang.Long) mapped.
bla-bla-bla ... so many errors ...
Caused by: java.lang.IllegalStateException: Ambiguous mapping found. Cannot map 'positionWS' bean method
public java.util.List by.ipps.accounting.ws.PositionWS.getEmployeePost(java.lang.Long)
to {[/positionListJson/{id}],methods=[GET],params=[],headers=[],consumes=[],produces=[application/json],custom=[]}: There is already 'resourceWS' bean method
public by.ipps.accounting.model.Employee.EmployeePost by.ipps.accounting.ws.ResourceWS.getEmployeePost(java.lang.Long) mapped.
The problem is that the class (with annotation #Controller) PositionWS with method getEmployeePost was renamed to ResourceWS a week ago, so exists no more, so I should not get this error.
To fix this I have to create a blank PositionWS controller (with no methods in it), commit & push that to bitbucket (and delete (cus i really don't need it) later and commit & push).
It seems to be like a bug in any of the applications I use. I can't find out in which app there is a bug to report it. Tell me please, if anyone faced such problems.
The heart of the issue was in incorrect configuration of Jenkins, it was my fault.
When I was configuring Jenkins I set maven goal as "install", but it must be "clean install". According to this Jenkins never deleted old files and kept them, so got a lot of issues of different kinds and with different log messages.
Due to Jenkins working specialty it downloads project files and try to assemble it on path /var/lib/jenkins/jobs/<projectName>/workspace/target/.
So I've drop the data in this folder and afterwards set maven goal to "clean install" and that fixed the issue.

Spring cannot resolve type in WEB-INF/libs

I recently start a spring web project with HBase. The problem is,spring seems unable to resolve types under WEB-INF/libs. it complains about "unresolved org.apache.hadoop.conf.Configuration" which is indirectly referenced from required .class file, which is actually in a .jar under the WEB-INF/lib library. Is there anything to be set for spring container to find it?
You need to make sure that Spring itself was loaded by the same class loader: the WAR class loader. This class loader should include all JARs in WEB-INF/lib and all .class files in WEB-INF/classes.
There's a way to pass a class loader into Spring to use a different class loader than the one that loaded it (or the Thread's context class loader), but that gets more complicated.
OK I got the problem. It seems that my project depended on hadoop-core-1.0.2 whilst hbase depend on hadoop-core-1.0.0 and that confused Spring. I fixed the dependency and problem solved.

Importing Spring beans from other Maven modules inside a WAR?

I have a new web app that is packaged as a WAR as part of a multi-module Maven project. The applicationContext.xml for this WAR references beans that are imported from the "service" module, which in turn imports beans from the "dao" module. The import statement in applicationContext.xml looks like this:
<import resource="classpath*:service.xml" />
and the one inside the service.xml file looks like this:
<import resource="classpath*:dao.xml" />
Neither Spring STS, nor Eclipse show any warnings or errors in my bean files. I reference the imported beans all over the place. The Maven build works fine and the DAO integration tests all pass (they use the beans). I don't have any service integration tests yet.
But when I start up the WAR in Jetty I get an error:
Error creating bean with name 'securityService'
Cannot resolve reference to bean 'userDAO' while setting constructor argument
All of the imported bean XML files can be found inside their respective JAR files in the WEB-INF/lib directory. Indeed, the service bean that threw the error is itself defined inside the service.xml file inside the service module's JAR file.
Apparently the service module can't find the bean that it imported from the dao module. Obviously I don't understand something...seems like this should this Just Work?
I enabled DEBUG logging for 'org.springframework' in order to see if I could learn anything. What I found were messages to the effect that the DAO beans had been created, but there was also a message about them having no name or id.
I check the file, and they all did have an id. So what was it? I check the XML namespace and saw:
http://www.springframework.org/schema/beans/spring-beans-2.0.xsd"
and noticed it was old (I am using Spring 3.0.2) and changed it to:
http://www.springframework.org/schema/beans/spring-beans-3.0.xsd
Once I changed it, Spring instantly threw half a dozen errors regarding beans that were defined incorrectly (but never used apparently). Once I fixed those errors, everything Just Worked. I've since gone through the entire system checking Spring XML file namespace versions.
Thanks to all for the help. Can't believe I wasted a day on this stupidity!!
The difference between the classpath:thingy.xml and classpath*:thingy.xml notation is that the former uses the standard classpath mechanism to resolve one resource (using ClassLoader.getResource(name)), whereas the latter will use ClassLoader.getResources(name) to retrieve all matching resources on the classpath, a distinction that should be irrelevant in your situation as I guess there is only one dao.xml file on the class path.
I think your problem is different, you are missing a leading slash.
Use this for a single resource
<import resource="classpath:/dao.xml" />
and this for multiple resources
<import resource="classpath*:/dao.xml" />
See
Spring Reference: The classpath*
prefix
Sun JavaDocs: ClassLoader
It should be like
<import resource="classpath:service.xml"/>
Are you having multiple applicationContexts and possibly the parent context is referring to a bean defined in the child context?

Classloader problem with EJB

I'm working on a project which includes persistence library (JPA 1.2), EJB 3 and Web presentation layer (JSF). I develop application using Eclipse and application is published on Websphere Application Server Community Edition (Geronimo 2.1.4) through eclipse plugin (but the same thing happens if I publish manually). When publishing to server I get the following error:
java.lang.NoClassDefFoundError: Could not fully load class: manager.administration.vehicles.VehicleTypeAdminBean
due to:manager/vehicles/VehicleType
in classLoader:
org.apache.geronimo.kernel.classloader.TemporaryClassLoader#18878c7
at org.apache.xbean.finder.ClassFinder.(ClassFinder.java:177)
at org.apache.xbean.finder.ClassFinder.(ClassFinder.java:146)...
In web.xml I have reference to EJB:
<ejb-local-ref>
<ejb-ref-name>ejb/VehicleTypeAdmin</ejb-ref-name>
<ejb-ref-type>Session</ejb-ref-type>
<local>manager.administration.vehicles.VehicleTypeAdmin</local>
<ejb-link>VehicleTypeAdminBean</ejb-link>
</ejb-local-ref>
EJB project has a reference to persistence project, and Web project has references to both projects. I don't get any compilation errors, so I suppose classes and references are correct.
I don't know if it is app server problem, but I ran previously application on the same server using same configuration parameters.
Does anybody have a clue what might be the problem?
Looks almost like it couldn't find the class manager.vehicles.VehicleType when it was attempting to create/load the class manager.administration.vehicles.VehicleTypeAdminBean.
I've encountered similar problems before. When the class loader attempts to load the class it looks at the import statements (and other class usage declarations) and then attempts to load those classes and so on until it reaches the bottom of the chain (ie java.lang.Object). If it cannot find one class along the chain (in your case it looks like it cannot load VehicleType) then it will state that it cannot load the class at the top of the chain (in your case VehicleTypeAdminBean).
Is the VehicleType class in a different jar? If you have a web module and and EJB module do you have the jar containing the VehicleType class in the appropriate place(s). Sometimes with web projects you have to put the jars in the WebContent/WEB-INF/lib folder or it won't find them.
Are both of these projects deployed separately (ie. two ears? or one ear and one war?) or are they together (ie, one ear with jars and a war inside?). I'm assuming the second given you declared your EJB local?
The jars that you are dependent on also have to be declared in your MANIFEST.MF files in the projects that use it.
I'm kind of running on guesses since I do not know your project structure. Showing that would help quite a bit. But I'd still check on where VehicleType is located with regards to your EJB class. You might find it isn't where you think it is come packaging or runtime.
Thanks #Chris for WebContent/WEB-INF/lib idea ! it works for me by following these steps :
1- Export my EJBs to a JAR (MyEJBs.jar)
2- I created another jar with your_installation_path/IBM/SDP/runtimes/your_version/binCreateEJBStrub.bat via CMD.exe, by executing this command :
createEJBStubs.bat <my_path>/MyEJBs.jar -newfile –quiet
3- A new jar will be automatically created in the same directory as MyEJBs.jar named MyEJBs_withStubs.jar
4- Put your new jar in WebContent/WEB-INF/lib
5- Call your EJBs by :
MyEJBRemote eJBRemote;
InitialContext ic = new InitialContext();
obj = ic.lookup("your_ejb_name_jndi");
eJBRemote = (MyEJBRemote ) PortableRemoteObject.narrow(obj,
MyEJBRemote.class);
eJBRemote = (MyEJBRemote ) obj;
Now you can call your EJBs from another EAR

Categories

Resources