简体   繁体   English

无法自动连接使用来自两个不同类的@Bean定义的bean

[英]Unable to autowire beans defined using @Bean from two different classes

I have two classes CustomerDAOImpl and UserDAOImpl, both annotated with @Repository annotation. 我有两个类CustomerDAOImpl和UserDAOImpl,都用@Repository注释进行了注释。 I have @Bean defined and autowired in each class. 我在每个类中都有@Bean定义和自动装配。

@Repository
public class CustomerDAOImpl implements CustomerDAO {
private static final String CUSTOMER_LOCK_INSERT = "INSERT INTO CUSTOMER_LOCKS (customerid, userid, session) VALUES (?, ?, ?)";

    @Bean
    @Lazy(true)
    public PreparedStatement customerLockAddStmt () {
        return cassandraTemplate.getSession().prepare(CUSTOMER_LOCK_INSERT);
    }

    @Autowired
    @Lazy
    PreparedStatement customerLockAddStmt;

    @Autowired
    CassandraOperations cassandraTemplate;

    public void create(CustomerLock lock) {
    ...
    Statement statement = customerLockAddStmt.bind(lock.customerId,lock.userId, lock.sessionId);
    cassandraTemplate.execute(statement);

    }

   }

Exactly the same way, I have defined, autowired and used following beans in UserDAOImpl class methods(just showing the bean definitions and autowiring code to keep it clean and short here): 完全相同,我在UserDAOImpl类方法中定义,自动装配并使用了以下bean(仅显示bean定义和自动装配代码以使其简洁明了):

    @Bean
    @Lazy(true)
    public PreparedStatement userAddStmt () {
        return cassandraTemplate.getSession().prepare(USER_INSERT);
    }

    @Bean
    @Lazy(true)
    public PreparedStatement userUpdateStmt () {
        return cassandraTemplate.getSession().prepare(USER_UPDATE);
    }

    @Autowired
    @Lazy
    PreparedStatement userAddStmt;

    @Autowired
    @Lazy
    PreparedStatement userUpdateStmt;

    @Autowired
    CassandraOperations cassandraTemplate;

   public void update(User user){
   //Beans userAddStmt and userUpdateStmt defined and autowired in this class are being used here
   ....
   }

Now both these DAO Beans are being autowired in my service class OrderServiceImpl (annotated with @Service); 现在,这两个DAO Bean都被自动连接到我的服务类OrderServiceImpl中(以@Service注释); here is the snippet: 这是代码段:

@Service
    public class OrderServiceImpl implements OrderService {
       @Autowired
       UserDAO userDAO;
       @Autowired
       CustomerDAO customerDAO;

       public void createOrder(Order order) {
       ....
       customerDAO.create(CustomerLock); // Getting the exception on this line
       ....
       userDAO.update(user);
       ....
       }
    }

When OrderService code executes "customerDAO.create(CustomerLock);" 当OrderService代码执行“ customerDAO.create(CustomerLock);”时 , I'm getting this exception. ,我遇到了这个异常。

No qualifying bean of type [com.datastax.driver.core.PreparedStatement] is defined: expected single matching bean but found 2: userAddStmt,userUpdateStmt". 没有定义类型为[com.datastax.driver.core.PreparedStatement]的合格Bean:预期的单个匹配Bean,但找到2:userAddStmt,userUpdateStmt”。

After getting this error, I added the attribute name="customerLockAddStmt" in "customerLockAddStmt" bean definition and used @Qualifier("customerLockAddStmt") while autowiring this bean, it worked but now it fails on following line due to the same error for the beans wired in userDAOImpl: 收到此错误后,我在“ customerLockAddStmt” bean定义中添加了属性名称=“ customerLockAddStmt”,并在自动装配该bean时使用了@Qualifier(“ customerLockAddStmt”),它可以工作,但是由于相同的错误,下一行失败在userDAOImpl中连接的bean:

userDAO.update(user); 

No qualifying bean of type [com.datastax.driver.core.PreparedStatement] is defined: expected single matching bean but found 1: customerLockAddStmt". 没有定义类型为[com.datastax.driver.core.PreparedStatement]的合格bean:期望的单个匹配bean,但找到1:customerLockAddStmt。

Could someone please help? 有人可以帮忙吗?

The Spring IoC container will manage the dependency between objects using configurations; Spring IoC容器将使用配置来管理对象之间的依赖关系。 it wires the related objects, instantiates and supplies them based on your configuration. 它连接相关对象,实例化并根据您的配置提供它们。 It doesn't matter if you have multiple beans of the same type, the container will handle that till the point you need them — which is your case. 拥有多个相同类型的bean无关紧要,容器将处理该问题直到您需要它们为止-这就是您的情况。

You have multiple beans of the same type, and they are available to be injected indeed, but the container can't figure it out what's the one you are asking for at that time , so basically you need more control over the selection process and hence, Spring's @Qualifier annotation can be used. 你有相同类型的多个豆,他们是可以被确实注入,但容器无法弄清楚什么是你当时问了一个,所以基本上你需要在选择过程中 ,从而更好地控制 ,可以使用Spring的@Qualifier批注。

On the other hand, if you have many annotation-driven injection by name, do not primarily use @Autowired ; 另一方面,如果按名称有很多注释驱动的注入,则不要主要使用@Autowired instead, use the @Resource which is semantically defined to identify a specific target component by its unique name, with the declared type being irrelevant for the matching process. 而是使用@Resource ,该语义已定义为通过其唯一名称标识特定目标组件,而声明的类型与匹配过程无关。

UPDATE: You can refer to this post and also to the Spring Framework Reference Documentation (Dependency Injection and Inversion of Control) . 更新:您可以参考这篇文章,也可以参考Spring Framework参考文档(依赖注入和控制反转)

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM