0

我在使用 jUnit 测试和 bean 代理时遇到了一个非常奇怪的问题。作为我的测试的一部分,我手动将 bean 添加到应用程序上下文中,并强制 bean 重新连接使用AutowireCapableBeanFactory.autowire()以强制自动更新。

如果我在 jUnit 测试中放置一个断点并检查我正在自动更新的 bean,我可以看到我的字段已正确更新并包括我以编程方式添加到上下文中的新 bean。

但是,当执行移动到实际 bean 并且我在我正在测试的方法中放置一个断点时,我添加到上下文中的 bean 不会出现。

我的 Bean-under-test 方法用@Transactional. 如果我删除@Transactional注释,自动装配字段会正确更新。

我尝试将 @Transaction 添加到我的 jUnit 测试方法中,但它没有任何影响。

Junit(实现 BeanDefinitionRegistryPostProcessor):

@Test
@Rollback
@Transactional
public void testExecuteSinglePatch() throws Exception {
    GenericBeanDefinition definition = new GenericBeanDefinition();
    definition.setBeanClass(Patch1.class);
    definition.setAutowireMode(GenericBeanDefinition.AUTOWIRE_BY_TYPE);
    definition.setLazyInit(false);
    registry.registerBeanDefinition("PATCH_1", definition);

    applicationContext.getBeansOfType(Patch.class);
    // reinit the patchEngine
    autowireBeanFactory.autowireBean(patchEngine);
    patchEngine.execute();

    assertEquals(1, patchRepository.findByName( new Patch1().getName()).size() );
}

被测Bean(PatchEngine):

@Inject private Map<String, Patch> availablePatches;

@Transactional
public void execute() throws Exception{

    // loop over all the pending patches, and apply them.  Keep looping over while patches exist and at least one patch is applied per iteration
    boolean appliedPatch = true;
    while( !availablePatches.isEmpty() && appliedPatch ){
        // no applied patches this iteration yet
        appliedPatch = false;

        // do some logic here
    }
}

当我将调试上下文设置为 jUnit test 并检查patchEngine时,bean id 与patchEngine.availablePatches我将调试上下文设置为 patchEngine.execute 方法时找到的 bean id 不同。

但是,如果我@transactional从方法中删除注释execute(),那么 ID 是相同的。

谁能帮我理解发生了什么?为什么会@Transactional影响依赖注入?@Transactional 如何影响代理以及如何确保正确填充代理?注释是否会导致使用不同的上下文?有没有办法解决这个问题?

我正在使用 Spring 3.2.4.RELEASE 和 jUnit 4.11。这可能是Spring错误吗?

4

0 回答 0