Back-End

[Spring] 기초 공부1

Minch13r 2025. 4. 19. 13:35

1. 의존관계와 결합도

의존관계의 이해

의존관계는 객체 간의 상호작용을 의미함. 예를 들어, LoginController, LoginAction, 로그인 기능 등은 DAO와 의존관계가 있음. 이러한 의존관계 설계에 따라 애플리케이션의 유지보수성과 확장성이 결정됨.

결합도와 그 중요성

결합도는 모듈 간의 상호 의존 정도를 나타내는 지표. 결합도가 높을수록 유지보수가 어려워짐.

  • 높은 결합도: Controller가 DAO를 직접 사용하는 경우
  • 낮은 결합도: Controller가 Service를 통해 DAO에 접근하는 경우
// 높은 결합도 (지양해야 함)
public class LoginController {
    private UserDAO userDAO = new UserDAO();
    
    public String login(String id, String password) {
        return userDAO.findUser(id, password);
    }
}

// 낮은 결합도 (권장)
public class LoginController {
    private UserService userService;
    
    public LoginController(UserService userService) {
        this.userService = userService;
    }
    
    public String login(String id, String password) {
        return userService.login(id, password);
    }
}

DAO를 직접 사용하면 안 되는 이유

  1. 데이터베이스 변경 시 영향: SQL 쿼리 변경 시 DAO를 직접 사용하는 모든 클래스 수정 필요.
  2. 데이터 접근 기술 변경: JDBC → MyBatis → JPA로 변경 시 코드 변경이 광범위하게 발생.
  3. 비즈니스 로직과 데이터 접근 로직의 혼합: 관심사 분리 원칙에 위배.

2. 스프링 컨테이너와 설정 파일

서블릿 컨테이너와 스프링 컨테이너

스프링 애플리케이션에서는 두 가지 주요 컨테이너가 작동:

  1. 서블릿 컨테이너(톰캣): web.xml을 통해 설정, DispatcherServlet(DS)을 생성.
  2. 스프링 컨테이너: DS-servlet.xml 또는 Java 기반 설정을 통해 POJO 객체들을 관리.
※ 서블릿 컨테이너(톰캣) ⇒ web.xml
  - 유일한 not POJO(서블릿)인 DispatcherServlet을 생성

※ 스프링 컨테이너 ⇒ DS-servlet.xml
  - 나머지 POJO 객체들을 생성하고 관리
  - 과거 applicationContext.xml의 역할

 

각 설정 파일은 해당 컨테이너와 1:1 관계. 스프링에서 제공하는 DispatcherServlet을 사용하려면 WEB-INF 하위에 DS-servlet.xml 설정 파일이 필요.

3. 컴포넌트 어노테이션

XML 설정 대신 어노테이션을 사용하여 빈을 등록 가능. @Component는 스프링이 관리하는 객체임을 나타내는 기본 어노테이션.

@Component의 특수화된 어노테이션들

  • @Service: 비즈니스 로직을 처리하는 서비스 계층의 컴포넌트
  • @Repository: 데이터 접근 계층의 컴포넌트 (DAO)
  • @Controller: 웹 요청을 처리하는 컨트롤러 컴포넌트
@Controller
public class LoginController {
    // 컨트롤러 로직
}

@Service
public class UserService {
    // 서비스 로직
}

@Repository
public class UserDAO {
    // 데이터 접근 로직
}

@Controller의 장점

  1. 효율적인 메모리 관리: 스프링 컨테이너가 객체 생명주기를 관리.
  2. 가독성 향상: 클래스의 역할을 명확히 표현.
  3. 타입 인식: DispatcherServlet이 해당 클래스를 컨트롤러로 인식.
  4. 자유도 향상:
    • 메서드 인자: request 객체를 단일 사용 가능
    • 메서드명: 자유롭게 정의 가능 (handleRequest 제약 없음)
    • 반환 타입: ModelAndView 대신 String 사용 가능 (더 가벼운 객체)
    • 관련 로직 메서드들을 함께 작성하여 높은 응집도 유지 가능

4. 요청 매핑과 커맨드 객체

@RequestMapping과 핸들러 매핑

@RequestMapping은 클라이언트 요청을 처리할 메서드를 지정하는 어노테이션으로, HandlerMapper 역할. 메서드 위에 적용 필요.

@Controller
public class LoginController {
    
    @RequestMapping(value="/login.do", method=RequestMethod.GET)
    public String loginForm() {
        return "login";  // login.jsp로 이동
    }
    
    @RequestMapping(value="/login.do", method=RequestMethod.POST)
    public String loginProcess(UserVO user) {
        // 로그인 처리 로직
        return "redirect:/main.do";
    }
}

REST API 개념

같은 URL에 대해 HTTP 메서드(GET, POST, PUT, DELETE 등)에 따라 다른 기능을 제공하는 것을 REST API라고 함.

  • GET /login.do: 로그인 페이지 이동
  • POST /login.do: 로그인 기능 제공

이는 더 직관적이고 RESTful한 API 설계를 가능하게 함.

커맨드 객체

스프링 MVC에서는 클라이언트의 요청 파라미터를 객체로 바인딩하여 처리 가능. 이렇게 자동으로 생성되고 바인딩된 객체를 커맨드 객체라고 함.

@RequestMapping(value="/login.do", method=RequestMethod.POST)
public String loginProcess(UserVO user) {
    // UserVO 객체는 자동으로 생성되고 요청 파라미터가 바인딩됨.
    // 이 UserVO 객체가 커맨드 객체.
    return "redirect:/main.do";
}

 

스프링 컨테이너는 필요한 객체들을 자동으로 생성하고 의존성을 주입. 이렇게 탄생한 객체들을 커맨드 객체라고 하며, 개발자는 객체 생성 없이 바로 사용 가능.

5. 스프링 MVC의 발전과 현재

과거 스프링 MVC는 XML 기반 설정이 주를 이루었지만, 현재는 Java 기반 설정과 어노테이션을 통한 설정이 주류.

최신 스프링 부트에서의 변화

스프링 부트에서는 자동 설정을 통해 많은 설정이 간소화:

  • web.xml 대신 WebApplicationInitializer 구현 또는 스프링 부트의 자동 설정 사용
  • XML 설정 파일 대신 @Configuration 클래스 사용
  • 내장 서블릿 컨테이너(Tomcat, Jetty, Undertow)를 통한 배포 간소화
@SpringBootApplication
public class Application {
    public static void main(String[] args) {
        SpringApplication.run(Application.class, args);
    }
}

@RestController
public class LoginController {
    
    @GetMapping("/login")
    public String loginForm() {
        return "login";
    }
    
    @PostMapping("/login")
    public String loginProcess(@RequestBody UserVO user) {
        // 로그인 처리 로직
        return "redirect:/main";
    }
}

'Back-End' 카테고리의 다른 글

[Spring] 내용 정리  (1) 2025.04.21
[Spring] 어노테이션 정리  (1) 2025.04.20
[Spring] 기초 공부  (1) 2025.04.15
JDBC와 JPA  (1) 2025.04.07
[JAVA] JSTL이란?  (2) 2025.03.19