考虑Controller-Service-Repository arch。
TokenService中的成功方法声明我是正确的。
@Transactional
public Token getByString(String tokenString) {
Token t = tr.loadTokenByString(tokenString);
t.setTokenType("SERVICE MODIF"); // note this test line works and changes are propagated to db
em.flush();
return t;
}
现在我们在控制器处理程序映射内部调用以前的服务方法并提取令牌:
logger.info(urlToken);
Object obj;
Token token;
obj = tokenService.getByString(urlToken);
User u;
if (obj != null) {
token = (Token) obj;
// tokenService.save(token); - am angry lost detached entity throwing exception that i am detached
token.setTokenType("helllo"); // this does not propagate to db since entity is detached
logger.info(token.toString());
u = token.getUser();
userService.activateUser(u);
}
从评论中可以看出,下一个setTokenType
内部控制器调用没有做任何事情,因此我调用save
来检查状态,而没有进一步猜测通知我实体已经分离。
这是否意味着我必须在服务类中进行所有更改?控制器上下文有什么问题,如果我只需要调用一个mutator,我不想被迫创建一个完整的存储库服务链来从控制器O.o中创建它。
我记得在我的大脑深处,需要一些神奇的过滤器来解释控制器上下文,但那是很久以前的事了,我不记得需要什么样的过滤器。也许我完全错了。
我怀疑我能够merge
在控制器内,因为asfaik even .flush
会在我忘记声明服务事务时抛出异常。我怀疑,直接声明控制器处理程序方法事务和autowire持久化上下文只是为了调用合并是可能的,甚至是正确的。
理想情况当然是即使在Controller链调用检索到实体时也要保持实体的持久状态。
答案 0 :(得分:0)
当您声明该方法事务时,它将是事务性的。只有那个。
事务完成后,您无法对此进行任何更改,无论您与之关联的引用对象是什么,都不再由会话管理。 (因为交易结束了。)
如果要更改托管状态中的对象,请在事务方法中自行执行(在同一事务中)。