I am working on a project where we developed various jars as small modules. Then these jars were added as dependencies in a base project.
In the base projects applicationContext we have imported the applicationContext of all dependendant jars using the following line
<import resource="classpath*:applicationContext.xml" />
The above line makes sure that all the applicationContexts.xml s get loaded. On code analysis I found that each of the module in its applicationContext has the dataSource injected. Although all the jars are going to use the same datasource still each of the jar is instantiating its own datasource. Is there a way by which I can specify a global datasource which can be injected through base class itself.
In each of the jars we have a datasource injected which the jar uses to perform database operations. I would want the jars to use a datasource of base jar instead of its own datsources.
Related
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?
Let say I have an external jar named data-access-0.0.1.jar that contains Spring annotation like #Component, #Bean. But this jar does NOT contain the main method to run as a Spring application (means no #SpringBootApplication, no #ComponentScan, ...).
Now I have another jar named employee.0.0.1.jar (does have the main method to run as Spring boot application - #SpringBootApplication), that use data-access-0.0.1.jar as a dependency. But somehow it does not scan #Bean, #Component in an external jar (error when starting the app, no bean with type "myComponent" found).
I think #ComponentScan in employee-0.0.1.jar should configure base packages include a package from the external jar and it should work, but I do not want to apply this mechanism. I want to somehow configure in the external jar so that any another jar that depend on it should scan the whole jar for autowiring
I have to make a plugin manager that handle Spring Bean inside jar contains in a specific external folder, in my case it's externalPlugin.
The folder externalPlugin is in my classpath.
My problem is that spring don't load beans when there are inside the jar.
If the jar file is extracted in /externalPlugin folder, Spring boot loads correctly the beans.
Is there a specific way to create jar , that spring loads correctly bean inside JAR? or even is it possible to load bean in external Jar?
Thank you for your time.
In my spring boot application, in order to load external Bean, I use the annotation
#ComponentScan({"com.app","com.plugin"})
To know if my bean are loaded I use and print the result of
String[] beanNames = ctx.getBeanNamesForType(AbstractPlugin.class);
external plugin jars are created as follow with jar cvf command
/externalPlugin/pluginA.jar
|-META-INF/
| |-MANIFEST.mf
|
|-com/
|-plugin/
|- beanA1.class
|- beanA2.class
package com.plugin
#Component
public class BeanA1 extends AbstractPlugin{
}
package com.plugin
#Component
public class BeanA2 extends AbstractPlugin{
}
found what i needed
http://www.codevomit.xyz/bootlog/blog/how-to-provide-spring-boot-fat-jar
and specialy generate jar with eclispe
I have a very simple Spring JPA Repository which is packed into a JAR and stored in the local maven repository.
I can use the JPA Repository in my Unit-Tests and in a little Main-Test-Routine. It gets #Autowired without any problem.
Here is the definition of my JPA-Repository:
public interface TestRepo extends CrudRepository<Seminar , Integer > {
List<Seminar> findAll();
}
And in the applicationContext.xml of the JAR:
<jpa:repositories base-package="de.dmsb.my.core"
entity-manager-factory-ref="entityManagerFactory"
transaction-manager-ref="transactionManager">
</jpa:repositories>
There a also some other Services defined in this JAR too which can be used in the JAR and in the WAR, which includes the JAR as a dependency with maven.
But as soon as a try to #Autowire the the JPA-Repository:
#Autowired
TestRepo testRepo;
I get an runtime error that there is no suitable bean defined. Other beans work - but as soon as it comes to JPA-Repositories it doesn't work.
I mean of course you cannot #Autowire a interface - and in the WAR there is not JPA-Repository bean in the ApplicationContext when I debug it - all the other beans from the JAR are there.
Any idea what the problem might be?
Goal:
List item
I have a spring webapp project, which is using component scan for configuration and autowiring interface implementation through maven submodules
the main project is dependant on the other modules thus the jar's of the submodules are placed in the /WEB-INF/lib folder
the submodules (aka plugins) have common package parent name x.y.z.extension eg. x.y.z.extension.pluginA
the classes in this package are annotated with #Component or #Configuration
in the servlet xml configuration i have placed such component-scan information:
Code:
<context:spring-configured />
<context:component-scan base-package="x.y.z.extension" />
With the mentioned configuration everything is working correctly.
What I would like to achieve:
List item
remove dependency of the main webapp maven module and other modules - the core webapp will be shipped without plugins
create subfolder e.g. "WEB-INF/classes/plugins" in the classpath classes dir
put there the mentioned jar's from submodules (or extract the jar content to eg. WEB-INF/classes/plugins/pluginA) - this could be done during "plugin installation" with webapp restart after new plugin installation
spring automagically should detect annotated classes and load it into the application context (and use not annotated classes in the plugin jar (annotated classes are mainly interface implementation but they are using some not annotated classes in the jar))
and ... of course this does not work The classes are not found.
If it possible to achieve this only using spring ecosystem, or should I take a look into other examples e.g. jspf ?
How can I modify classpath scanning with spring and also keep automatic component scanning ?
thanks !