Bean Validation은 @NonNull을 검사하지 않는다
수강 신청 DTO의 두 필드에 @NotNull을 걸고, 애플리케이션 서비스에는 @Validated를 달아 두었다. 그런데 리뷰에서 나는 그 사이에 있어야 할 @Valid가 빠져 있는 것을 발견했다. 그 상태에서는 DTO에 제약을 몇 개 걸어 두어도 Bean Validation 검사가 시작되지 않는다 같은 자리에 함정이…
framework애 대한 내용입니다
수강 신청 DTO의 두 필드에 @NotNull을 걸고, 애플리케이션 서비스에는 @Validated를 달아 두었다. 그런데 리뷰에서 나는 그 사이에 있어야 할 @Valid가 빠져 있는 것을 발견했다. 그 상태에서는 DTO에 제약을 몇 개 걸어 두어도 Bean Validation 검사가 시작되지 않는다 같은 자리에 함정이…
어떤 프로퍼티 조합이 고유하고 그 값으로 엔티티 하나를 특정할 수 있으면 자연 키 후보로 본다. 회원의 이메일이 그랬고, 강의의 강사와 제목 조합도 그랬다. 그런데 두 경우에 서로 다른 결정이 나왔다. 이메일에는 @NaturalId를 붙였고, 강사와 제목에는 유니크 제약만 걸었다. Hibernate에서 @NaturalId를…
상태를 가진 도메인을 개발할 때 가장 흔한 구조는 엔티티에 status 컬럼을 두고, 서비스 코드에서 if (course.getStatus() == DRAFT) 같은 조건문으로 전이를 검사하는 방식이다. 처음에는 잘 동작한다. 문제는 그 강의를 다루는 코드가 두 곳, 세 곳으로 늘어날 때다. 어느 상태에서 어느…
아키텍처 규칙은 대부분 문서에만 있다. “슬라이스 사이에는 순환 의존을 두지 않는다”고 적어 놓고, 코드 리뷰에서 걸러 내기를 기대한다. 그런데 리뷰어가 놓치면 그대로 들어가고, 한 번 들어간 순환 의존은 시간이 지날수록 걷어 내기 어려워진다 결론부터 말하면 이런 규칙은 테스트 코드로 강제할…
테스트 픽스처를 열어 보면 이런 코드가 있다 닉네임은 KimWhat이고 비밀번호는 verysecret이다. 이 값이 무슨 의미인지는 아무도 설명하지 않는다. 그냥 형식 검증을 통과할 만한 길이로 아무렇게나 정한 값이다. 그런데 이 값은 검증 코드에도 그대로 박혀 있다 이 테스트가 통과한다고 해서 비밀번호…
애플리케이션 서비스 클래스를 하나 열어 보면 이런 상태가 되어 있다 네 줄 모두 이 클래스가 무슨 일을 하는지에 대한 설명이 아니다. 스프링 빈으로 등록하고, 트랜잭션을 걸고, 파라미터 검증을 켜고, 생성자를 만들어 달라는 지시다. 애플리케이션 서비스를 새로 만들 때마다 이 네…
헥사고날 아키텍처를 배우고 나면 안과 밖의 경계는 선명해진다. 어댑터는 밖에, 도메인은 안에. 포트로만 소통한다. 그런데 정작 실무에서 막히는 지점은 그 다음이다. 회원 하나만 있을 때는 헥사곤 하나로 충분했는데, 강사가 들어오고 강의가 들어오면 헥사곤 안쪽이 금세 뒤엉킨다. 여기서 자연스럽게 떠오르는 발상이…
Member 엔티티가 있으니 MemberService 하나, MemberController 하나. 스프링을 배우면 대부분 이 구조로 시작한다. 처음에는 편하다. 문제는 N개월 뒤에 온다. MemberService는 메서드 열다섯 개짜리 클래스가 되고, 그것을 주입받은 코드만 봐서는 무슨 목적으로 쓰는지 알 수 없다. 헥사고날 아키텍처는 이 지점에서 다른…
Google Play Console에 “8월 31일까지 API 36을 타겟팅하지 않으면 앱을 업데이트할 수 없다”는 정책 알림이 떴다. 처음엔 계정에 있는 다른 앱 얘기인 줄 알고 엉뚱한 프로젝트를 열었고, 나중엔 비공개 테스트 트랙에만 새 빌드를 올려놓고 다 됐다고 착각했다. 두 번 다…
빌드는 이미 TestFlight에 올라가 있었다. 심사 제출은 그 빌드를 고르고 버튼만 누르면 될 줄 알았다. 그런데 “심사에 추가”를 누르자 두 개의 필드가 비어 있다며 막혔고, 그 앞단에는 App Privacy 설문·연령등급·수출 규정 같은 “답을 정해야 하는” 질문들이 줄지어 있었다. 심사 제출은…