英文:
Spring boot is caching results without enabling it
问题
我现在已经使用Spring Boot有几年时间了,但最近遇到了一个不寻常的错误。在从我的Angular应用程序调用Spring Boot应用程序的GET API时,返回的行数比数据库中实际存在的行数少。
上述提到的问题在重新部署Spring Boot应用程序后得到了解决。我怀疑这可能是某种缓存问题,因此我将其命名为这个标题。
**注意:我没有在应用程序上启用缓存。**
另一个嫌疑对象是EntityManager没有得到刷新。我使用Spring Repository来获取数据,实体管理器不是由我的自定义代码处理的。所以,我不确定这种情况是如何发生的。
我正在使用AWS RDS PostgreSQL实例作为我的数据库。
经过两天的努力追寻,我把它放在这里寻求专家的意见。
@Data
@EntityListeners(AuditingEntityListener.class)
@NoArgsConstructor
@AllArgsConstructor
@Entity
@Table(name = "user")
public class User {
@Id
@GeneratedValue(strategy = GenerationType.SEQUENCE, generator = "uid_gen_seq")
@SequenceGenerator(name = "uid_gen_seq", allocationSize = 1)
@Column(name = "user_id", updatable = false, nullable = false)
private long userId;
private String name;
private String address;
@Column(name = "ph_no")
private String phNo;
@Column(name = "rent_pass")
private int rentPass;
@CreatedBy
private String createdBy;
@LastModifiedBy
private String modifiedBy;
}
控制器方法:
@GetMapping(produces = MediaType.APPLICATION_JSON_VALUE)
public ResponseEntity<List<UserVO>> getAllUsers()
throws Exception, NoContentException {
return ResponseEntity.ok(userService.getAllUsers());
}
服务方法:
@Override
public List<UserVO> getAllUsers() throws NoContentException {
logger.info("获取所有用户");
List<User> users = userRepository.findAll();
List<UserVO> userVOs = converter.convertToVO(users);
return userVOs;
}
**更新:**
我认为我已经将可能的情况缩小到了一个。那就是会话未得到刷新。根据我的理解,调用存储库方法会隐式创建并关闭一个会话。除非服务或控制器方法已经用@Transactional注解标记。
在我的情况下,服务方法没有用@Transactional注解标记,但会话仍然没有得到刷新。
作为一种解决方法,我已经使用@Transactional(TxType.REQUIRED_NEW)注解标记了这些方法,以避免使用任何旧会话。目前这是有效的,但我仍然对没有这个解决方法时应用程序的行为不太满意。
英文:
I am using Spring boot from a couple of years now but recently I encountered an unusual error. While calling the spring boot app's GET API from my angular app, it is returning less number of rows than the actual number present on DB.
The above mentioned issue is resolved the moment spring boot app is redeployed. Suspecting it to be some sort of caching issue I have kept this title.
Note: I have not enabled caching on the app.
Another suspect is EntityManager not getting refreshed. I'm using Spring repository to fetch the data, entity manager is not handled by my custom code. So, I'm not sure how that can happen.
I am using AWS RDS postgresql instance as my db.
After two days of unsuccessful pursuit, I put it here for expert's opinions
@Data
@EntityListeners(AuditingEntityListener.class)
@NoArgsConstructor
@AllArgsConstructor
@Entity
@Table(name = "user")
public class User {
@Id
@GeneratedValue(strategy = GenerationType.SEQUENCE, generator = "uid_gen_seq")
@SequenceGenerator(name = "uid_gen_seq", allocationSize = 1)
@Column(name = "user_id", updatable = false, nullable = false)
private long userId;
private String name;
private String address;
@Column(name = "ph_no")
private String phNo;
@Column(name = "rent_pass")
private int rentPass;
@CreatedBy
private String createdBy;
@LastModifiedBy
private String modifiedBy;
}
Controller method:
@GetMapping(produces = MediaType.APPLICATION_JSON_VALUE)
public ResponseEntity<List<UserVO>> getAllUsers()
throws Exception, NoContentException {
return ResponseEntity.ok(userService.getAllUsers());
}
Service method:
@Override
public List<UserVO> getAllUsers() throws NoContentException {
logger.info("Get all users");
List<User> users = userRepository.findAll();
List<UserVO> userVOs = converter.convertToVO(users);
return userVOs;
}
Update:
I think I have narrowed down the possible cases to 1. That's session not getting refreshed. As per my understanding, calling a repository method implicitly creates a session and closes it. Unless the service or controller method has been annotated with @Transactional.
The service methods in my case were not annotated with @Transactional, still the session was not getting refresh.
As a workaround I have annotated the methods with @Transactional(TxType.REQUIRED_NEW) to avoid any old session getting used. This is working as of now but I'm still not convinced with the behavior of the application without this workaround.
答案1
得分: 0
你是如何插入数据的?如果不是通过你的应用程序插入的,那么缓存不会重新加载。
参考这个答案 - https://stackoverflow.com/questions/2707903/are-entities-cached-in-jpa-by-default
英文:
How are you inserting the data? if you are not inserting through your app, then the caches are not reloaded.
See this answer - https://stackoverflow.com/questions/2707903/are-entities-cached-in-jpa-by-default
专注分享java语言的经验与见解,让所有开发者获益!
评论