JAVA/Spring Boot
(디버깅)일대다 양방향 Response Error
ri5
2021. 7. 2. 17:54
Error log
java.lang.IllegalStateException: Cannot call sendError() after the response has been committed
Game
@Getter
@Entity
@Table(name = "GAMES")
@NoArgsConstructor
public class Game {
// 게임 아이디(PK)
@Id
@Column(name = "GAME_ID")
private Long gameId;
// 게임 이름
@Column(name = "GAME_NAME")
private String gameName;
// 게임 정보
@Column(name = "GAME_INFO")
private String gameInfo;
...
@OneToMany(mappedBy = "game")
private List<GameTag> gameTags = new ArrayList<>();
@Builder
public Game(Long gameId, String gameName, String gameInfo, Date launchDate, String evaluation, String imgUrl, String videoUrl, String devCompany, String distributor) {
this.gameId = gameId;
this.gameName = gameName;
this.gameInfo = gameInfo;
this.launchDate = launchDate;
this.evaluation = evaluation;
this.imgUrl = imgUrl;
this.videoUrl = videoUrl;
this.devCompany = devCompany;
this.distributor = distributor;
}
}
Response
@Getter
public class GamesListResponseDto {
// 게임 아이디(PK)
private Long gameId;
// 게임 이름
private String gameName;
// 게임 정보
private String gameInfo;
....
private List<GameTag> gameTags = new ArrayList<>();
public GamesListResponseDto(Game entity) {
this.gameId = entity.getGameId();
this.gameName = entity.getGameName();
this.gameInfo = entity.getGameInfo();
this.launchDate = entity.getLaunchDate();
this.evaluation = entity.getEvaluation();
this.imgUrl = entity.getImgUrl();
this.videoUrl = entity.getVideoUrl();
this.devCompany = entity.getDevCompany();
this.distributor = entity.getDistributor();
this.gameTags = entity.getGameTags();
}
}
Service
@Transactional(readOnly = true)
public List<GamesListResponseDto> findAllDesc() {
return gameRepository.findAllDesc().stream()
.map(GamesListResponseDto::new)
.collect(Collectors.toList());
}
DEBUG
Game 안에 있는 GameTag 리스트가 Game을 참조하고 GameTag안에 있는 Game이 서로를 참조하면서 무한 재귀함수가 실행 되게 된다.
Game Entity에게 @JsonIdentityInfo 또는 @JsonIgnore 설정을 해서 무한재귀를 끊어야 한다.