Je développe une application SpringBoot (par exemple, MyApp) avec dépendance à deux projets de données avec une implémentation différente:
data-jdbc.jar
spring-boot-starter-jdbc
qui expose la classe JDBCDataService qui sera utilisée par mon applicationExemple de code:
@Service
public class JDBCDataServiceImpl implements JDBCDataService {
@Autowired
private JDBCDataRepository jdbcDataRepository;
...
}
my.data.jdbc
JDBCTemplate
Exemple de référentiel:
@Repository
public class JDBCDataRepositoryImpl implements JDBCDataRepository {
@Autowired
protected JdbcTemplate jdbcTemplate;
...
}
data-jpa.jar
spring-boot-starter-data-jpa
qui expose également la classe JPADataService qui sera également utilisée par mon applicationExemple de code:
@Service
public class JPADataServiceImpl implements JPADataService {
@Autowired
private JPADataRepository jpaDataRepository;
...
}
my.data.jpa
CrudRepository
Exemple de référentiel:
@Repository
public interface JPADataRepository extends CrudRepository<MyObject, Integer{
...
}
Dans mon projet SpringBoot, j'ai l'application principale SpringBoot suivante:
@SpringBootApplication
public class MyApp extends SpringBootServletInitializer {
}
Dans ma classe de services professionnels MainService
, j'ai l'injection suivante
@Service
public class MainServiceImpl implements MainService {
@Autowired
private JDBCDataService jdbcDataService;
@Autowired
private JPADataService jpaDataService;
Cependant, j'ai rencontré le problème "Could not Autowire. No beans of 'JPADataService' type found"
qui n'existe que pour la classe JPADataService
mais qui fonctionne correctement pour la classe JDBCService
.
J'ai essayé la solution trouvée dans les questions suivantes, mais aucune de ces solutions ne fonctionne dans mon cas:
Je ne peux pas @Autowire un haricot présent dans un bocal de bibliothèque dépendant?
@ComponentScan(basePackages = {"org.example.main", "package.of.user.class"})
Comment puis-je @ Autowire un haricot de printemps qui a été créé à partir d'un pot externe?
@Configuration
@ComponentScan("com.package.where.my.class.is")
class Config {
...
}
J'ai maintenant trouvé la solution à mon problème. Je dois monter mon paquet principal MyApp.Java d'un niveau supérieur pour analyser mes bibliothèques de données.
Au lieu de placer mon package MyApp.Java
sous le package my.app
, je dois le déplacer sous my
pour pouvoir analyser correctement mes bibliothèques avec les packages my.data.jpa
et my.data.jdbc
.
J'ai maintenant trouvé la solution à mon problème. Je dois monter mon paquet principal MyApp.Java d'un niveau supérieur pour analyser mes bibliothèques de données.
Au lieu de placer mon package MyApp.Java
sous le package my.app
, je dois le déplacer sous my
pour pouvoir analyser correctement mes bibliothèques avec les packages my.data.jpa
et my.data.jdbc
.
L'ajout de @ComponentScan ne fonctionnera pas si la classe que vous essayez d'utiliser Autowire n'est pas annotée avec @Component. Pour que cela fonctionne, vous devez annoter une méthode dans votre classe @Configuration
. Quelque chose comme ceci devrait vous permettre d'autowire la classe:
@Configuration
public class ConfigClass{
@Bean
public JPADataService jpaDataService(){
return new JPADataService();
}
}
Vous devez configurer spring.factories
dans le fichier JAR externe:
external-jar-project
|--Java
|--resources
|-- META-INF
|-- spring.factories
le contexte de spring.factories, comme ceci:
org.springframework.boot.autoconfigure.EnableAutoConfiguration=xxx