SpringBoot 레이어드 아키텍처

semin Ryu·2024년 6월 10일
0

Spring Boot 레이어드 아키텍처는 아래와 같이 구성되어 있습니다. 이 구조에서 각 컴포넌트의 역할을 간단하게 설명해보겠습니다.

DTO (Data Transfer Object)

  • 계층 간 데이터 교환을 하기 위해 사용되는 객체
  • 주로 데이터베이스와 비즈니스 로직, 또는 클라이언트와 서버 간의 데이터 교환을 단순화하기 위해 사용
  • 로직을 가지지 않는 순수한 데이터 객체
  • 속성과 그 속성에 접근하기 위한 getter, setter 메소드를 가진 클래스
@NoArgsConstructor
@AllArgsConstructor
@Builder
@Getter
@Setter
@ToString
public class UserDTO {
		private String name;
    private Integer age;
    private String major;
}

Entity

  • DB 테이블에 매핑되는 객체
  • JPA를 사용하는 애플리케이션에서는 각 Entity가 데이터베이스 테이블의 한 행과 대응
  • @Entity - 실제 DB 테이블과 매칭될 Class임을 명시, 해당 클래스가 JPA 엔티티 클래스라고 정의
  • @Table - 엔티티가 매핑될 테이블 지정
  • @Column - 특정 클래스 필드를 테이블의 컬럼에 매핑.
  • @Id - 해당 테이블의 PK필드를 나타냄
  • @GeneratedValue - 주 키의 생성 전략을 명시
  • @JoinColum - 외래키 매핑
  • @OneToOne, @ManyToOne, @OneToMany - 일 대 일, 일 대 다, 다 대 다 매핑
@Entity
@Table(name = "user")
@NoArgsConstructor
@Getter
@Setter
@Builder
@ToString
public class UserEntity{

	@Id // primary Key
	@GeneratedValue(strategy = GenerationType.IDENTITY)
	private Long id;
	
	@Column
	private String name;
	
	@Column
	private String address;
	
	@Column(name = "major")
	private String major;

}

Controller

  • 사용자의 요청을 받아 처리하는 역할
  • @Controller 명시
  • REST API의 경우 @RestController 사용
  • @Autowired로 Service를 주입받아 비즈니스 로직의 결과를 사용자에게 전달
  • @RequestMapping로 특정 경로의 요청을 처리하는 메소드와 연결
@Controller
public class UserController {

    UserService userService;

    @Autowired    
    public UserController (UserService userService){
		    this.userService = userService; // Service 주입
    }

    @RequestMapping(value = "/user",method = RequestMethod.POST)
    public String saveUser(UserDTO user){
        userService.saveUser(user); // service에서 비즈니스 로직 수행 후
        return "save";
    }
    
    @GetMapping(value = "/user/{id}")
    public UserDTO getUser(@PathVariable("id") Long id){
        UserDTO getUserDTO = userService.getUser(id);
        return user;
    }
    
}

Service

  • 비즈니스 로직을 수행하는 역할
  • @Service 명시
  • @Autowired로 DAO 주입
  • 여러 DAO를 조합하여 복잡한 비즈니스 요구사항 충족
  • 필요한 데이터를 DTO 또는 도메인 객체 형태로 Controller에 전달
@Service
public class UserService {

    UserDAO userDAO; 

    @Autowired
		public UserService (UserDAO userDAO){
				this.userDAO = userDAO;
		}

		// User 저장
    public void saveUser(UserDTO user){
		    UserEntity userEntity = UserEntity.builder()
											        .name(user.getName())
											        .address(user.getAddress())
											        .major(user.getMajor())
											        .build();
											        
        userDAO.saveUser(userEntity);
    }
    
    // User id로 User 정보 조회
    public UserDTO getUser(Long id){
				UserEntity userEntity = userDAO.getUserEntity(id);
	
        UserDTO user = UserDTO.builder()
								        .name(userEntity.getName())
								        .address(userEntity.getAddress())
								        .major(userEntity.getMajor())
								        .build();
		    return user;
    }
    
}

DAO (Data Access Object)

  • DB의 Data에 접근하기 위한 객체, 실제로 DB에 접근하는 객체
  • JPA에서는 DB에 Data를 CRUD하는 Repository 객체들이 DAO
  • DAO에서 DB와 데이터에 관련된 로직을 처리함
  • DAO 클래스는 일반적으로 ‘인터페이스-구현체’ 구성으로 생성
    • Service layer에서 DAO객체를 주입받을때 인터페이스를 선언하는 방식으로 구성
      • DAO - 인터페이스
      • DAOImpl - 구현체
@Repository
public class UserDAOImpl implements UserDAO{

    UserRepository userRepository;

    @Autowired
    public UserDAOImpl(UserRepository userRepository) {
        this.userRepository = userRepository;
    }

    @Override
    public UserEntity getUserEntity(Long id){
        UserEntity user = userRepository.getReferenceById(id);
        return user;
    }
    
    @Override
    public void saveUser(UserDTO user){
        UserEntity user = userRepository.save(user);
    }
    
}

Repository

  • JPA의 JpaRepository를 상속받아 구현됨
  • 데이터의 지속성과 조회를 담당
  • 비즈니스 로직에서 분리되어 데이터 접근 기술에 중점을 둠
  • JPA 상속
    • JpaRepository<도메인 객체, ID>를 상속 받기
  • Repository는 함수명으로 기능을 제작, 그래서 함수명에 오타가 나면 안된다
    • 일반 객체 조회는 findBy로 시작
    • By 뒤에 변수명 적어줌 ( 첫 글자는 대문자)
      • Ex) findByName, findById
public interface UserRepository extends JpaRepository<UserEntity,Long>{
			UserEntity findByName(String name);
			UserEntity findById(Long id);
}
profile
류세민님의 개발블로그 입니다

0개의 댓글