SpringBoot+MongoDB无法向List中添加对象问题求助
问题分析与解决方案
核心问题
- 未显式持久化Player实体变更:MongoDB的Spring Data框架不会像JPA那样自动跟踪实体状态修改,仅修改Player的games列表后,必须调用
playerRepository.save()才能将变更同步到数据库。 - DBRef关联的Game未提前持久化:
@DBRef存储的是关联文档的ID,必须先将Game保存到数据库生成gameId,再将其添加到Player的games列表,否则关联关系无法生效。
具体修改方案
1. 调整GameServiceImpl的playGame方法
先保存Game生成ID,再更新Player的关联关系,最后持久化Player:
@Override public Game playGame(String playerId) { if(playerService.getAllPlayers().isEmpty()){ throw new HttpException(HttpStatus.INSUFFICIENT_STORAGE,"There is no registered player"); } Player player = playerService.findPlayerById(playerId); if(player==null){ throw new HttpException(HttpStatus.NOT_FOUND,"Player with this id is not found"); } Game gamePlayed = playGameService.play(); gamePlayed.setPlayer(player); // 先保存Game,生成唯一ID Game savedGame = gameRepository.save(gamePlayed); player.calculateRate(); // 将已持久化的Game添加到Player列表,并保存Player playerService.saveGame(savedGame, playerId); return savedGame; }
2. 修改PlayerServiceImpl的saveGame方法
添加Player的显式保存逻辑:
@Override public void saveGame(Game game, String playerId){ Optional<Player> playerOpt = playerRepository.findById(playerId); if(playerOpt.isPresent()){ Player player = playerOpt.get(); player.getGames().add(game); // 持久化Player的关联变更 playerRepository.save(player); } }
补充说明
- 原MySQL环境中JPA的EntityManager会自动托管实体修改,无需手动调用save;但MongoDB的Spring Data无此特性,必须手动触发持久化操作。
@DBRef会在Player文档中存储Game的ID引用,结合Game配置的lazy=true,查询Player时可按需懒加载关联的Game列表。
内容的提问来源于stack exchange,提问作者Anna kuzmina
相关产品推荐
相关产品推荐

