https://sundaland.tistory.com/320
[ ▶ Handler Method : @SessionAttributes ]
@SessionAttributes 어노테이션은 HTTP 세션에 특정 모델 속성(Model Attribute)을 저장하여 여러 요청 간에 이 속성을 유지하고 사용할 수 있도록 해준다. 이는 주로 폼 데이터를 여러 단계에 걸쳐 처리하거나, 특정 상태를 유지할 필요가 있을 때 유용하다.
[ ▷ 기본 개념 ]
- @SessionAttributes는 컨트롤러 클래스 레벨에 적용되며, 해당 컨트롤러에서 사용되는 특정 모델 속성이나 속성 타입을 세션에 저장하도록 선언한다.
- 이 어노테이션을 사용하면, 한 번 요청에서 모델에 추가된 속성(예: pet 객체)이 여러 요청에 걸쳐 유지된다. 모델 속성은 세션에 저장되며, 다른 컨트롤러 메서드에서 이를 다시 꺼내 사용할 수 있다.
[ ▷ 예시 상황 ]
사용자가 반려동물 정보를 입력하는 폼을 여러 단계에 걸쳐 처리하고 싶다고 가정한다. 첫 번째 단계에서는 반려동물의 기본 정보를 입력하고, 두 번째 단계에서는 추가 정보를 입력한 뒤 모든 정보를 저장하는 흐름이다. 이런 경우 @SessionAttributes를 사용하면 Pet 객체를 세션에 저장하여 각 단계에서 이를 재사용할 수 있다.
▼ 예시 코드 (Java)
import org.springframework.stereotype.Controller;
import org.springframework.web.bind.annotation.SessionAttributes;
import org.springframework.web.bind.annotation.PostMapping;
import org.springframework.web.bind.annotation.ModelAttribute;
import org.springframework.web.bind.support.SessionStatus;
import org.springframework.validation.BindingResult;
@Controller
@SessionAttributes("pet") // "pet"이라는 모델 속성을 세션에 저장
public class EditPetForm {
// 첫 번째 단계: Pet 객체를 모델에 추가하여 세션에 저장
@ModelAttribute("pet")
public Pet setUpPetForm() {
return new Pet(); // 새로운 Pet 객체 생성
}
// 두 번째 단계: Pet 객체 사용 및 처리
@PostMapping("/pets/{id}/edit")
public String processSubmit(@ModelAttribute("pet") Pet pet, BindingResult result,
SessionStatus status) {
if (result.hasErrors()) {
return "petForm"; // 오류가 있을 경우 다시 폼으로 이동
}
// 성공적인 처리 후, 세션에서 "pet" 객체 제거
status.setComplete();
return "redirect:/pets"; // 목록 페이지로 리다이렉트
}
}
- @SessionAttributes("pet"): EditPetForm 컨트롤러에서 사용되는 pet이라는 이름의 모델 속성을 세션에 저장하도록 지정한다. 이를 통해 pet 객체는 여러 요청 간에 세션을 통해 유지된다.
- @ModelAttribute("pet"): 첫 번째 요청에서 새로운 Pet 객체를 생성하여 모델에 추가한다. 이 모델 속성은 @SessionAttributes에 의해 세션에 저장된다.
- SessionStatus status: processSubmit 메서드의 마지막 단계에서 세션에 저장된 pet 객체를 제거하기 위해 SessionStatus 객체를 사용한다. status.setComplete() 메서드를 호출하면 세션에 저장된 pet 객체가 삭제된다.
- BindingResult result: 데이터 바인딩 및 유효성 검사 결과를 처리하는 아규먼트이다. 폼에 오류가 있을 경우, 다시 폼 페이지로 이동하며 오류 메시지를 표시한다.
[ ▷ 세션 관리 흐름 ]
- 첫 번째 요청에서는 @ModelAttribute를 통해 Pet 객체가 생성되고, 세션에 저장된다.
- 이후 다른 요청에서 이 세션에 저장된 pet 객체를 자동으로 재사용하여 처리할 수 있다.
- 모든 처리가 완료되면 SessionStatus를 사용해 세션에서 객체를 제거합니다. 이렇게 하지 않으면 세션에 계속 유지될 수 있다.
[ ▷ Reactive 스택에서의 사용 (Spring WebFlux) ]
Spring WebFlux에서는 @SessionAttributes 어노테이션이 지원되지 않는다. 이는 WebFlux가 비동기적이고 논블로킹(non-blocking) 방식으로 동작하기 때문에, HTTP 세션을 직접적으로 다루는 구조가 아닌 다른 방식으로 상태를 관리해야 하기 때문이다.
WebFlux에서는 세션 관리를 위해 WebSession을 사용하여 세션 데이터를 다룰 수 있다. 이는 Mono나 Flux 같은 비동기 방식으로 세션 데이터를 처리한다.
▼ WebFlux 예시 코드
import org.springframework.stereotype.Controller;
import org.springframework.web.bind.annotation.PostMapping;
import org.springframework.web.server.WebSession;
import reactor.core.publisher.Mono;
@Controller
public class ReactivePetForm {
@PostMapping("/pets/edit")
public Mono<String> processSubmit(WebSession session) {
return session.getAttribute("pet")
.flatMap(pet -> {
// 처리 로직...
session.invalidate(); // 세션 데이터 제거
return Mono.just("redirect:/pets");
});
}
}
- WebSession: WebFlux에서 세션을 관리하는 방식이다. 이 예시에서는 세션에서 pet 객체를 가져와 처리하고, 작업이 완료되면 세션을 무효화(invalidate)하여 세션 데이터를 제거한다.
- session.getAttribute("pet"): 세션에서 pet 객체를 가져오는 비동기 처리 방식이다.
[ ▷ 요약 ]
- @SessionAttributes는 여러 요청 간에 세션을 통해 모델 속성을 유지할 수 있게 해주는 어노테이션이다.
- 세션에 저장된 모델 속성은 SessionStatus를 사용하여 명시적으로 제거해야 한다.
- Spring WebFlux에서는 @SessionAttributes가 지원되지 않으며, 대신 WebSession을 사용하여 비동기적으로 세션 데이터를 관리한다.
'Web on Servlet Stack' 카테고리의 다른 글
@ModelAttribute (0) | 2024.10.11 |
---|---|
Handler Method : @SessionAttribute (0) | 2024.10.11 |
Annotated Controllers[3] - @CookieValue (0) | 2024.10.11 |
@RequestHeader (0) | 2024.10.11 |
@RequestParam (0) | 2024.10.11 |