You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Spring Boot中RequestScope仓库Autowire未为新请求创建实例

问题分析与解决方案

核心误区:打印的是代理对象的哈希值

你看到的同一个hashCode,本质是Spring为request-scoped bean创建的代理对象是单例的,而非实际的Repository实例复用。这个代理会在每个请求上下文里动态获取真正的request-scoped Repository实例,但代理本身的哈希值不会变,导致你误以为实例没更新。

正确验证方式

要确认实际实例是否为请求级别的,需要获取代理背后的真实对象再打印哈希值。可以用Spring的AopTestUtils工具类(需引入spring-test依赖):

修改服务类中的打印代码:

import org.springframework.test.util.AopTestUtils;

// ... 其他代码

@Override
@TransactionAttribute(TransactionAttributeType.REQUIRED)
public void createMasterTableEntry(String jsonData, String mandantId, String dataIdentifier) {
    // 获取真实的request-scoped实例
    MasterRepository realRepo = AopTestUtils.getTargetObject(masterRepository);
    loggers.info(">>> 真实实例hashCode: " + realRepo.hashCode());
    loggers.info(">>> 代理对象hashCode: " + masterRepository.hashCode());
}

此时你会发现,代理对象的hashCode始终不变,但真实实例的hashCode会随每个请求变化。

针对你尝试的方案的修正

1. @Scope配置的补充

你的Repository上的@Scope配置是正确的,由于MasterRepository是接口,也可以将proxyMode设置为ScopedProxyMode.INTERFACES,效果一致。

2. ObjectFactory/Provider的正确用法

如果你用ObjectFactory或Provider注入,需要每次请求时调用get()方法获取新实例,而不是直接打印工厂/提供者本身的hashCode:

@Autowired
private transient ObjectFactory<MasterRepository> repoFactory;

// 或者用Provider
// @Autowired
// private transient Provider<MasterRepository> repoProvider;

@Override
@TransactionAttribute(TransactionAttributeType.REQUIRED)
public void createMasterTableEntry(String jsonData, String mandantId, String dataIdentifier) {
    MasterRepository repo = repoFactory.getObject();
    // MasterRepository repo = repoProvider.get();
    loggers.info(">>> 实例hashCode: " + repo.hashCode());
}

这样每次调用get()都会返回当前请求上下文的新实例。

额外检查点

  • 确保你的请求确实是不同的HTTP请求(比如用Postman多次发送、不同浏览器窗口请求),而非同一个请求内的多次方法调用。
  • 确认Spring Boot的自动配置没有覆盖你的scope设置,避免额外的Repository代理配置冲突。

内容的提问来源于stack exchange,提问作者mariya cherian

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.27 13:32:29