짧게 글을 써보겠다
글 제목처럼 가끔 예전에 만들어졌던 DTO를 활용하는 경우가 있다
이럴때 사용할 수 있는 어노테이션이 있다!
@JsonIgnoreProperties({"xxx", "yyy"}}
private UserRes user;
@JsonIgnoreProperties({"xxx", "yyy"}}
private UserRes user;
user 안에 xxx와 yyy는 json response 필드에 포함하지 않는다는 어노테이션이다
매우 유용하게 활용할 수 있다..! 애초에 null인지 아닌지까지 보여주고싶지 않은 필드에 사용할 수 있다
추가로 리스트의 정보는 ToString을 할때 위험한 부분이 있다. exclude 어노테이션을 잘 사용해서 로그를출력할때나 값을 가져올때 순환참조를 피해야 한다
@ToString(exclude = {"profileInfoList"})
public class ProfileResponse {
private ProfileInfo profile;
private List<ProfileInfo> profileInfoList;
}
+
null인 필드는 response에서 제외하고 싶을때
@JsonInclude(JsonInclude.Include.NON_NULL)을 사용하면 된다
@JsonInclude(Include.NON_NULL)
private ProfileInfo profile;
또는 스프링 2.5버전 이후에서는 yaml이나 properties파일에 모든 ObjectMapper 에 동작하도록 작성할 수 있다
// properties
spring.jackson.default-property-inclusion: NON_NULL
// yaml
spring:
jackson:
default-property-inclusion: non_null
개인적으로는 처음 개발시작부터 협의된 것이 아니라면 null 인 필드도 response로 내려주는게 좋다고 생각한다
왜냐하면 프론트단에서 DB 레이어에서 가져온 response를 상세히 알 수 없기 때문이다(여러 정보를 주고 프론트 코드로 처리하는게 맞다고 생각)
추가로 정말 중요한 얘기를 덧붙여본다
DTO가 아닌 Entity를 직접 Response로 내려보내면 안되는 이유
우리가 인스턴스화하는 모든 것은 메모리 영역에 올라가는것이다
A 엔티티가 인스턴스화 되었고 Setter나 위험의 가능성이 있는 메서드가 열려있는 채로
어떤 요청의 응답에 A 인스턴스가 포함되어있는 경우 값이 프로그래머의 의도를 벗어나서 바뀔 위험성이 있다
엔티티를 그대로 두고 @JsonIgnore를 사용하는 방법이 있겠지만
프로젝션을 사용해서 필요한 필드들을 DTO에 꽂아두는게 안전한 방법이다
메모리처럼 생각해보자
밥그릇 하나를 두고 여러사람들이 건드리는 경우와
여러사람에게 필요한 밥그릇을 갖다주는 경우이다
밥 그릇에 담긴 정보는 동일할지라도 가르키고 있는 주소지는 다른 것이다
추가로 우리 회사의 모든 DB정보를 외부에 노출하는 불상사도 막을 수 있다(엔티티를 그대로 내려보내는 경우)
JPA를 쓰는 경우 예전에 스프링 구버전에서 JavaBean을 정의내리고 사용하기 위해 @Setter를 다 붙여주고 사용하는데 엔티티를 그대로 Response한다? 매우 위험성이 있다..
우리는 사람이고 실수할 수 있다. 그리고 프로그래머는 자바와 스프링을 이용해서 반복된 코드를 메서드로 줄이고, 반복된 클래스를 인터페이스/추상클래스 등의 설계로 빼낼 수 있어야 한다(물론 이 레벨은 나도 도달못했다)
Secure Coding을 하는 습관을 들여보는것은 어떨까?
'Backend > Java - Spring' 카테고리의 다른 글
jar Build Task(Feat. thin/plain, fat/uber) + no main manifest attribute in ... (0) | 2022.09.04 |
---|---|
스프링 시큐리티 + 소셜로그인 구현(2) - 테스트해보기 (3) | 2022.04.21 |
스프링 시큐리티 + 소셜로그인 구현(1) - 앱 등록하고 키값 얻기 (0) | 2022.04.18 |
댓글