java - 如何在 Spring Boot MVC 中更新数据
问题描述
我有 Spring Boot MVC 上最常见的项目。我正在尝试通过 PUT 写入更新数据。
@RestController
@RequestMapping(CommentController.PATH)
public class CommentController {
public final static String PATH = "/comments";
@Autowired
private CommentService service;
@PutMapping("/{id}")
public Comment update(@RequestBody Comment comment, @PathVariable Long id) {
return service.update(id, comment);
}
}
@Service
public class CommentService {
@Autowired
private CommentRepository repository;
public Comment update(Long id, Comment entity) {
Optional<Comment> optionalEntityFromDB = repository.findById(id);
return optionalEntityFromDB
.map(e -> saveAndReturnSavedEntity(entity, e))
.orElseThrow(getNotFoundExceptionSupplier("Cannot update - not exist entity by id: " + id, OBJECT_NOT_FOUND));
}
private Comment saveAndReturnSavedEntity(Comment entity, Comment entityFromDB) {
entity.setId(entityFromDB.getId());
return repository.save(entity);
}
}
@Repository
public interface CommentRepository extends JpaRepository<Comment, Long> {
}
@Entity
public class Comment {
@Id
@Column
@GeneratedValue(strategy = GenerationType.IDENTITY)
protected Long id;
@Column(name = "name")
protected String name;
}
然后我编写了一个能够检查更新数据的测试:
@SpringBootTest
@RunWith(SpringRunner.class)
@Transactional
// DBUnit config:
@DatabaseSetup("/comment.xml")
@TestExecutionListeners({
TransactionalTestExecutionListener.class,
DependencyInjectionTestExecutionListener.class,
DbUnitTestExecutionListener.class
})
public class CommentControllerTest {
private MockMvc mockMvc;
private static String route = PATH + "/{id}";
@Autowired
private CommentController commentController;
@Autowired
private CommentRepository commentRepository;
@PersistenceContext
private EntityManager entityManager;
@Before
public void setup() {
mockMvc = MockMvcBuilders.standaloneSetup(commentController)
.build();
}
@Test
public void update_ShouldReturnCreated2() throws Exception {
int id = 1;
String name = "JohnNew";
Comment expectedComment = new Comment();
expectedComment.setName(name);
ObjectWriter ow = new ObjectMapper().writer().withDefaultPrettyPrinter();
String json = ow.writeValueAsString(expectedComment);
this.mockMvc.perform(put(route, id)
.contentType(MediaType.APPLICATION_JSON_UTF8)
.content(json))
.andDo(print());
entityManager.clear();
entityManager.flush();
Comment commentUpdated = commentRepository.findById(1L).get();
assertThat(commentUpdated.getName(), equalTo(name)); // not equals!
}
}
评论.xml:
<dataset>
<Comment id="1" name="John" />
</dataset>
但问题是数据没有更新。如果启用 Hibernat 的日志记录,那么也没有对数据库的更新请求。我究竟做错了什么?
解决方案
您@Transactional
缺少CommentService
. 虽然在每个方法级别添加它可能会更好,但尝试将它添加到类级别以验证这可以解决问题:
@Service
@Transactional
public class CommentService {
推荐阅读
- javascript - 以 html 输出时,Bootstrap 弹出框不起作用
- android - Webview 和 iFrame 视频全屏问题
- axios - Nuxt Axios 模块读取状态码
- javascript - 升级到 webpack 4,导入不起作用
- angular - 在角度 5 和材料中使用错误处理程序时,Snackbar 位置错误
- java - 错误整数自定义值Java
- reactjs - 使用 React Redux thunk 的加载器
- javascript - 以编程方式触发 D3 画笔事件
- docker - Docker GUI 字体问题
- java - 如何在 docker 容器上使用 Java 运行 docker exec