TIL - 0711
java-ims
내부 flow
- Request 메세지 파싱
- Request 객체 생성
- Request에 핸들러(컨트롤러) 요청 : path를 가지고 있기때문에 위임
- 컨트롤러에 Request 넘겨주며 처리 요청
- ResponseEntity(HttpMethod, Header, Body) 생성
- Response 객체 응답하기
Response 작성할 때 필요한 데이터를 가진 ResponseEntity 만들기
- 빌더 패턴으로 만들기
- 장점 : 조립하듯이 객체를 생성할 수 있음, 객체 생성 시 설정해야할 필드가 많아지면서 선택적으로 필드를 설정할 수 있게할 때 좋음(유연성), 특정 필드만 깔끔하게 기본값을 설정해둘 수 있음, 필드 각각의 할당 조건이 생길 때 분리해두면 코드가 간결해지는 효과를 볼 수 있음
public class ResponseEntity {
private HttpStatus status;
// TODO : 헤더를 만들어야함
private String body;
private ResponseEntity(HttpStatus status, String body) {
this.status = status;
this.body = body;
}
public static class Builder {
private static final String DEFAULT_BODY = "";
private HttpStatus status;
private String body;
public Builder() {
body = DEFAULT_BODY;
}
public Builder setStatus(HttpStatus status) {
this.status = status;
return this;
}
public Builder setBody(String body) {
this.body = body;
return this;
}
public ResponseEntity build() {
return new ResponseEntity(status, body);
}
}
}
Request params으로 Model 객체 생성하기 : ModelInitializer 생성
- reflection API 사용해서 생성하기 : 요청받은 targetType에 맞게 객체 생성
- declared와 일반 메소드 차이 : 해당 클래스에만 선언되어있는 것을 찾아오는 것과 상위 클래스에 선언되어있는 것을 모두 가져오는 차이
- 자바빈 규약에 맞게 모델 추상화해야함 : 약속이 되어있는 것을 꼭 지켜야함
public class ModelInitializer {
public static <T> Optional<T> init(Map<String, String> params, Class<T> targetType) {
try {
T instance = targetType.getDeclaredConstructor().newInstance();
List<Method> injectTargets = Arrays.stream(targetType.getDeclaredMethods()).filter(method -> method.getName().startsWith("set")).collect(toList());
.
.
.
.
return Optional.of(instance);
} catch (NoSuchMethodException | InstantiationException | IllegalAccessException | InvocationTargetException e) {
return Optional.empty();
}
}
}
- 수정할 부분이 있다면 injection 해주는 방식이 달라진다면? 자바빈 규약이 아니라 새로운 규약이 나와서 뭔가 다르게 동작해야한다면?
- injection 해야하는 대상을 뽑는 기준을 전략 패턴처리하면 됨 : ModelInitializer의 메소드가 static이 아니라 instance 메소드로 변경하고, 대상 뽑는 기준을 injection 할 수 있도록 변경하면 더 낫지않을까싶음
객체지향적인 코드인지 아닌지 계속해서 의심하기
- 혹시 다른 객체의 상태를 get해서 마음대로 변경하고 있는 것은 아닌지
- 많은 것(관심, 역할)을 하나의 객체가 처리하고 있는 것은 아닌지
jpa
연관관계 맵핑
- 연관관계 맵핑의 핵심은 객체지향적으로 관계를 맺는다는 것
- 데이터 중심적으로 했다면 관계를 맺는 것이 아니라 그냥 fk를 가지고 있는 것
- 객체지향적으로 했다면 참조변수를 가지고 있는 것(객체의 참조와 테이블 행의 key를 맵핑)
- 코딩을 할 때(설계할 때) 참조변수를 가지는 것과 fk를 쌩으로 가져있는 것은 큰 차이가 있음 : 객체지향적으로 코딩을 할 수 있다는 장점이 생김(내부적으로 쿼리를 날리는 것은 같으나 OOP 개발자는 OOP를 그대로
- 연관관계 맵핑할 때 주의할 점은 맵핑할 key가 할당되어있어야함 : jpa로 관리하는(영속), 관리했던(준영속 - id는 주어져있는) 엔티티 객체여야함