| 일 | 월 | 화 | 수 | 목 | 금 | 토 |
|---|---|---|---|---|---|---|
| 1 | 2 | 3 | 4 | |||
| 5 | 6 | 7 | 8 | 9 | 10 | 11 |
| 12 | 13 | 14 | 15 | 16 | 17 | 18 |
| 19 | 20 | 21 | 22 | 23 | 24 | 25 |
| 26 | 27 | 28 | 29 | 30 | 31 |
- 커뮤니티서버
- 클린아키텍처
- MVC요청플로우
- JPA
- JDBC
- model
- 공통규약
- TDD
- 전전긍긍
- DDD
- 이벤트핸들러등록
- index
- OOP
- MVC
- 디스크i/o
- springsecurity
- Transaction
- 냄새라도
- 공통기술
- AOP
- 문제선택근거
- 로그백
- 단위테스트
- Ajax
- string
- 이벤트핸들러this
- 사면초가
- SpringLegacy
- 설정세팅
- SEQUENCE
- Today
- Total
개발이군고구마
Thread와 ThreadLocal 본문
1. 개요
- 애플리케이션에서 사용되는 객체는 스프링에서 “싱글톤” 으로 만들어져서 사용됨
- 스레드가 동시에 요청되는 경우에 heap영역에 있는 싱글톤 객체가 공유되어, 각기 다른 요청에 사용될 수 있음
- 스레드 동시성의 문제를 해결해야 각 스레드별 안전성을 확보할 수 있음
2. Thread 란 무엇인가
- 실제로 작업을 수행하는 주체
- 요청당 스레드가 할당 되며, 자바의 경우엔 멀티 스레드를 지원함 (ThreadPool)
[thread와 요청을 쉽게 생각하는 방법]
- request : 주문
- thread : 점원
- WAS/브라우저 : 가게
2-1. 자바 스크립트의 싱글 스레드와 비동기
- 자바 스크립트는 실행컨텍스트를 1개만 생성할 수 있는 싱글스레드 그러나,
- 브라우저가 멀티스레드를 지원하기 때문에 동시에 여러 요청이 와도 스레드를 처리할 수 있음
- 브라우저의 이벤트 루프가 비동기도 지원하고 있음
2-2. 자바의 멀티 스레드와 동기
- thread pool에서 thread를 할당하기 때문에
- 동시에 여러 요청이 와도 처리 가능
- 자바는 동기로 스레드 처리함

3. 동시성 문제를 해결하는 ThreadLocal

JVM이 운영체제로부터 할당받은 메모리영역.

- data 영역에서, thread가 heap 영역을 공유하고 있음
- spring 싱글톤 패턴에서, 힙영역에 올라간 객체가 공유될 가능성이 있음
* 스레드 용 전용 보관소

- 각 Thread 별로 생성되는 변수
public class ThreadLocal<T> {
...
public T get() {
Thread t = Thread.currentThread();
ThreadLocalMap map = getMap(t);
if (map != null) {
ThreadLocalMap.Entry e = map.getEntry(this);
if (e != null) {
@SuppressWarnings("unchecked")
T result = (T)e.value;
return result;
}
}
return setInitialValue();
}
...
public void set(T value) {
Thread t = Thread.currentThread();
ThreadLocalMap map = getMap(t);
if (map != null) {
map.set(this, value);
} else {
createMap(t, value);
}
}
...
}
- get : 현재 스레드의 고유한 로컬 변수 조회
- set : 현재 스레드의 고유한 로컬 변수 값 저장
- Map 형태로 저장 : key (현재 thread) : value (현재 threadlocal 변수 값)
- => 해당 변수는 현재 thread에서만 사용이 가능함
4. 사용처
- 사용자 인증 정보, 트랜잭션 컨텍스트 등 스테드별로 “독립적으로” 유지해야하는 정보 저장시 활용
- 각 스레드가 사용자 별 세션 정보 유지나 현재 트랜잭션 상태를 스레드 별로 관리해야할 때
[예 - security authentication 객체 session 저장시]
public void setAuthentication(String userName){
SecurityContext context = SecurityHolder.createEmptyContext();
Authentication authentication = createAuthentication(userName);
context.setAuthentication(authentication);
SecurityHolder.setContext(context);
}
- Thread가 동시에 요청이 오는 경우, 힙 영역에 저장된 객체는 공유가 됨
- 그렇다면 SecurityHolder에 담기는 context는 중복될 가능성이 있는 거 아닐까?
[SecurityContext의 threadLocal 사용]

- SpringSecurityHolder에서 SecurityContext 클래스의 context를 조회하는 메서드를 호출
- 그때 Context는 threadlocal에 저장된 thread별 securityContext 객체를 찾아서 넘김
- 따라서, 해당 thread 별 context (authentication)이 반환되어
- 동시 thread 요청이 오더라도, 각각의 thread가 holder에 저장이 됨
5. ThreadPool
- 다중요청을 처리하는 방법
- 서블릿 컨테이너 (Tomcat) 이 부팅시에 Thread Pool을 생성함
- 유저의 요청 (HttpServletRequest) 가 들어오면 Thread Pool에서 하나씩 Thread를 할당
[앞으로 궁금점]
Context와 Strategy 라고 써져 있는 클래스들이 많이 보이는데,
이는 어떤 디자인 패턴을 따르고 있는 걸까 ?
'SERVER > Spring' 카테고리의 다른 글
| [Spring : Design Pattern] 2. Template Callback (인수 interface) (0) | 2024.10.04 |
|---|---|
| [Spring : Design Pattern] 1. Template Method (Abstract Class) (0) | 2024.10.02 |
| 데이터는 어떻게 주고 받을까? - 2. 데이터 매핑과 응답 (0) | 2024.09.15 |
| 데이터는 어떻게 주고 받을까? - 1. 데이터 전달하기 (0) | 2024.09.15 |
| DB connection 변화의 역사 (1) | 2024.09.09 |