728x90
1. No newline at end of file 에러와 해결방법
⭐️ 클래스의 마지막 라인은 줄 바꿈을 해주는 것이 convention이기에 위와 같은 에러가 발생하였다!
필자는 ide로 intelli j를 사용하기에 intelli j 설정을 변경하여 해결해 주었다.
해결방법 : Settings - Editor - General -On save - Ensure every saved file ends with a line break 체크
2. application.properties와 application.yml의 차이점
프로젝트의 각종 설정을 application.properties를 통해서만 할 수 있을 줄 알았지만 application.yml로도 설정할 수 있었다. 그래서 둘 사이의 차이점이 무엇인지 정리해 보았다.
- ⭐️ 내부 구조의 차이
- ⭐️ properties의 경우 각 줄마다 key = value의 형태로 설정되어 있다.
- ⭐️ 반면, yml의 경우 들여 쓰기로 구분되는 계층 구조가 key : value의 형태로 설정되어 있다.
- 리스트 구조를 설정할 때 properties에서는 배열 인자값을 생성할 때와 마찬가지로 하나씩 설정해줘야 하지만, yml에서는 계층 구조로 설정해 줄 수 있다.
프로젝트의 규모가 커질수록 계층 구조를 사용하는 yml로 설정하는 것이 훨씬 간편해 보인다!
3. 단일 setter를 열어두는 것을 지양하는 이유
- ⭐️ 캡슐화 원칙 위반
- 객체 지향 프로그래밍인 자바에서 캡슐화는 중요한 개념이다. 캡슐화란 데이터와 해당 데이터를 조작하는 메서드를 함께 묶어 외부로부터의 접근을 제한함으로써 객체 내부를 숨기는 것인데, 단일 setter를 많이 열어두게 되면 객체 내부 상태를 외부에서 자유롭게 수정할 수 있으므로 캡슐화 원칙에 위배된다.
- ⭐️ 불변성 유지의 어려움
- 캡슐화 원칙을 위반했던 것과 마찬가지로 외부에서 객체 내부 상태를 변경할 수 있다면 객체의 불변성을 유지하지 못한다.
4. @RequiredArgsConstructor을 통해 '생성자 주입'
- 보통 의존성 주입 방식에는 필드 주입, 수정자 주입, 생성자 주입의 3가지 방법이 있는데 생성자 주입 방식을 주로 사용한다.
- 그러나 생성자 주입조차 번거롭다면 @RequiredArgsConstructor을 사용해 보자!
- ⭐️ @RequiredArgsConstructor란 final 혹은 @NotNull이 붙은 필드의 생성자를 자동으로 생성해 주는 롬복 어노테이션이다.
- 물론 lombok 플러그인 설치 및 적용해주어야 하고 build.gradle에 다음과 같이 의존성(dependencies)을 추가해주어야 한다.
// lombok plugin
implementation('org.projectlombok:lombok')
annotationProcessor('org.projectlombok:lombok')
// test 환경
testImplementation('org.projectlombok:lombok')
testAnnotationProcessor('org.projectlombok:lombok')
5. 스프링 프로젝트 계층
스프링 프로젝트에서는 전형적으로 다음과 같은 계층을 사용한다. (프로젝트에 따라 다르게 표현되기도 하지만 개념적으로는 아래의 4가지 계층을 기준으로 사용한다)
- ⭐️ 프레젠테이션 계층 (Presentation Layer)
- 웹 클라이언트들의 요청 및 응답을 처리한다.
- controller나 router 등의 컴포넌트들이 이 부분에 속한다.
- 서비스 및 데이터 액세스 계층에서의 exception을 이 계층에서 처리하기도 한다.
- ⭐️ 서비스 계층 (Service Layer)
- 비즈니스 로직을 처리한다.
- 프레젠테이션 계층과 데이터 엑세스 계층 사이를 연결하는 역할을 한다.
- service 인터페이스와 @service 어노테이션을 사용하여 구성된 service 구현 클래스가 이 계층에 속한다.
- ⭐️ 데이터 엑세스 계층 (Data Access Layer)
- ORM (JPA, Hilbernate)를 주로 사용하며 DB와의 상호작용을 담당한다.
- Repository와 DAO (Data Access Object) 등이 여기에 속한다.
- 서비스 계층에서 비즈니스 로직을 처리하기 위해 데이터를 CRUD 할 수 있는 인터페이스를 제공한다.
- ⭐️ 도메인 모델 계층 (Domain Model Layer)
- 비즈니스 객체 또는 엔티티를 정의한다. (그렇기에 엔티티 클래스라고도 부른다)
- 도메인 객체는 애플리케이션의 핵심 개념을 표현하며 비즈니스 로직을 포함할 수 있다.
6. DTO 용례
- Controller는 View와 도메인 Model 간의 데이터를 주고받을 때 주로 별도의 DTO를 사용한다.⭐️⭐️ 물론 도메인 객체 자체를 View에 직접 전달할 수 있지만, 민감한 도메인 비즈니스 데이터 및 기능들이 노출될 수 있고 Model과 View 사이에 의존성이 생기기 때문에 DTO를 사용한다.
- DTO를 사용하면 도메인 Model을 캡슐화하여 사용할 수 있다.
- ex) 다음과 같이 User.java (도메인 Model)과 UserController.java (컨트롤러)가 존재할 때 도메인 Model인 User을 그대로 View에 넘겨준다면 도메인 Model의 모든 속성이 외부에 노출되게 된다.
public class User {
public Long id;
public String name;
public String email;
public String password; //외부에 노출되서는 안 될 정보
public DetailInformation detailInformation; //외부에 노출되서는 안 될 정보
//비즈니스 로직, getter, setter 등 생략
}
@GetMapping
public ResponseEntity<User> showArticle(@PathVariable long id) {
User user = userService.findById(id);
return ResponseEntity.ok().body(user);
}
- 그렇기에 DTO를 사용하여 도메인 Model을 캡슐화하여 앞선 문제를 해결할 수 있다.
public class UserDto {
public final long id;
public final String name;
public final String email;
//생성자 생략
public static UserDto from(User user) {
return new UserDto(user.getId(), user.getName(), user.getEmail());
}
}
@GetMapping
public ResponseEntity<UserDto> showArticle(@PathVariable long id) {
User user = userService.findById(id);
return ResponseEntity.ok().body(UserDto.from(user));
}
7. 추가적인 학습 내용들
- Spring과 SpringBoot의 차이점
- 둘 모두 스프링 프레임워크를 기반으로 한 자바 웹 개발 프레임워크이다.
- Spring은 설정 파일을 직접 작성해야 하지만 SpringBoot는 자동 설정을 제공한다. 또한, SpringBoot는 내장 서버를 제공하여 쉽게 웹 애플리케이션을 실행할 수 있다.
- ⭐️ 따라서 Spring은 스프링 프레임워크를 보다 세밀하게 제어하고자 하는 경우에, SpringBoot는 빠르고 간단하게 애플리케이션을 개발하고자 하는 경우에 주로 사용된다.
- Call by reference vs Call by value
- ⭐️ Call by reference : 변수의 주소값이 복사되어 매개변수로 전달된다. 따라서 함수 내에서 해당 변수의 값이 변경되어도 호출한 쪽의 변수는 영향을 받지 않는다.
- ⭐️ Call by value : 인자의 값 자체가 복사되어 매개변수로 전달된다. 따라서 함수 내에서 해당 변수의 값을 변경하면 호출한 쪽의 변수도 변경된다.
- ⭐️ java에서 매개변수로 객체를 전달할 때 기본적으로 Call by reference가 사용된다.
- public static void main(String[] args) 의미
- mian 함수는 자바 프로그램의 시작점이다. 자바가상머신(JVM)은 main이라는 이름의 메서드를 찾아 프로그램을 시작한다!
- ⭐️ public : JVM이 main함수를 찾을 수 있도록 한다.
- ⭐️ static : JVM이 인스턴스 생성 없이 main함수를 곧바로 실행할 수 있도록 한다.
- ⭐️ void : main함수가 종료되면 프로그램도 종료되므로, return값이 필요하지 않다.
- ⭐️ String[] args : 커맨드라인 등을 통해, main함수 내부에서 사용할 수 있는 String 데이터를 전달할 수 있다.
'Backend > Spring' 카테고리의 다른 글
[세차새차] 양방향 매핑 지양과 순환 참조의 위험성 - 회원 관리 기능 개발 (2) | 2024.08.31 |
---|---|
[Kakao Tech Campus Step2] 2주차 회고 (0) | 2024.07.07 |
[Kakao Tech Campus Step2] 1주차 회고 (1) | 2024.06.30 |
[Spring Core] 초록 스터디 Step3 회고 (0) | 2024.05.03 |
[Spring MVC] 초록 스터디 Step1 회고 (1) | 2024.04.14 |