SpringBoot: Can't Autowire Class from Other Jar Library
Solution 1
I have now found the solution on my problem. I have to move up my main MyApp.java one package level higher in order to scan my data libraries.
Instead of putting my MyApp.java
under my.app
package, I have to move it under my
in order to successfully scan my libraries with my.data.jpa
and my.data.jdbc
packages.
Solution 2
Adding @ComponentScan
won't work if the class you're attempting to Autowire isn't annotated with @Component
. In order to get this to work, you'll have to annotate a method in your @Configuration
class. Something like this should allow you to autowire the class:
@Configuration
public class ConfigClass{
@Bean
public JPADataService jpaDataService(){
return new JPADataService();
}
}
Solution 3
You need to config spring.factories
at external jar:
external-jar-project
|--java
|--resources
|-- META-INF
|-- spring.factories
the contect of spring.factoires, like this:
org.springframework.boot.autoconfigure.EnableAutoConfiguration=xxx
Jown
Updated on July 31, 2022Comments
-
Jown almost 2 years
I am developing a SpringBoot application (e.g. MyApp) with dependency to two data projects with different implementation:
data-jdbc.jar
- built using the
spring-boot-starter-jdbc
which exposes JDBCDataService class that will be used by my application
Sample Code:
@Service public class JDBCDataServiceImpl implements JDBCDataService { @Autowired private JDBCDataRepository jdbcDataRepository; ... }
- with package
my.data.jdbc
- there is no SpringBoot main class. Spring configuration only created for the unit test classes
- the repository classes are using
JDBCTemplate
Sample Repository:
@Repository public class JDBCDataRepositoryImpl implements JDBCDataRepository { @Autowired protected JdbcTemplate jdbcTemplate; ... }
data-jpa.jar
- built using the
spring-boot-starter-data-jpa
which also exposes JPADataService class that will also be used by my application
Sample Code:
@Service public class JPADataServiceImpl implements JPADataService { @Autowired private JPADataRepository jpaDataRepository; ... }
- with package
my.data.jpa
- there is no SpringBoot main class. Spring configuration only created for the unit test classes
- repository classes extends the
CrudRepository
interface
Sample Repository:
@Repository public interface JPADataRepository extends CrudRepository<MyObject, Integer{ ... }
In my SpringBoot project, I have the following SpringBoot main application:
@SpringBootApplication public class MyApp extends SpringBootServletInitializer { }
In my business service
MainService
class, I have the following injection@Service public class MainServiceImpl implements MainService { @Autowired private JDBCDataService jdbcDataService; @Autowired private JPADataService jpaDataService;
However, I have encountered the problem
"Could not Autowire. No beans of 'JPADataService' type found"
which only exists for the classJPADataService
but working fine forJDBCService
class.I have tried the solution found in the following questions, but none of these work in my case:
Can't I @Autowire a Bean which is present in a dependent Library Jar?
@ComponentScan(basePackages = {"org.example.main", "package.of.user.class"})
How can I @Autowire a spring bean that was created from an external jar?
@Configuration @ComponentScan("com.package.where.my.class.is") class Config { ... }
I have now found the solution on my problem. I have to move up my main MyApp.java one package level higher in order to scan my data libraries.
Instead of putting my
MyApp.java
undermy.app
package, I have to move it undermy
in order to successfully scan my libraries withmy.data.jpa
andmy.data.jdbc
packages. - built using the
-
Christopher Schneider almost 8 yearsI should add I'm not familiar with JPADataService. It may require some sort of configuration that I didn't account for.
-
Jown almost 8 yearsIf this is the case, it should also not work in
JDBCService
object as I have not declared this class in any Java configuration file in my application which uses them. AFAIK, using@SpringBootApplication
should do the magic for you :-) -
SHAKU over 6 yearsanybody know why '@ComponentScan' wont work? I am facing the same issue, my repository is even annotated with '@Repository' and added a ComponentScan with base package value, which is one level up where spring could see all the beans even from jar libraries. The application only worked when I moved up one level the SpringBootApplication as @Jown said.
-
ajaristi about 6 yearsWhy did this happen? It's a bug or a spring-boot feature?
-
Gagandeep Kalra about 6 yearsIt's not a bug, @ComponentScan by default picks up from package where main class is defined and it's sub-directories
-
Nisarg about 4 yearsPlease write your answer in English only.
-
Satya P about 3 yearsYou are a life savior @Jown. I spent almost a day to figure out the problem in my application. I added ComponentScan to my SpringBoot main application calls, it solved the actual problem, but that caused some other problem internal to my app. I have moved the SpringBoot main class, and it solved my problem. Literally you have saved my weekend.. kudos!