SecurityContextHolder 관련해서
1191
작성한 질문수 4
안녕하세요. 강의보면서 질문이 있어 문의 드립니다. (섹션 4. 실전프로젝트 - 인증 프로세스 Ajax 인증 구현)
------------------------------------------------------------------------------------------------------
SecurityConfig 구현은 http.csrf().disable(); 이렇게 설정하고 임의로
CustomUserDetails details = (CustomUserDetails) userDetailsService.loadUserByUsername("userId");
SecurityContextHolder.getContext().setAuthentication(new UsernamePasswordAuthenticationToken(details.getUserInfo(), null, details.getAuthorities()));
사용자 정보를 넣어 (디버깅으로 사용자 조회하여 데이터 들어가는것까지 확인했습니다. authorities 는 ROLE_USER)
------------------------------------------------------------------------------------------------------
사용하고자 하는 서비스에서 SecurityContextHolder.getContext().getAuthentication().getPrincipal()
호출하여 사용자 정보를 가져오려고 하는데 anonymous_user 라고 나오네요. SecurityConfig 에서 넣은 사용자 정보도 없고요.
강제로 인증되어 사용자 정보까지 가져오려면 어떻게 해야 할까요?
------------------------------------------------------------------------------------------------------
이렇게 하는 이유는 개발환경에서만 security를 풀어 SecurityContextHolder 를 사용하는 다른 곳에서 security 를 동작했을때와 같은 환경으로 사용하고자 합니다.
답변 1
0
제가 정확한 실행 환경을 모르겠으나 일단 먼저 이해하실 부분은 이렇습니다.
스프링 시큐리티의 SecurityContext 의 범위 즉 스코프는 ThreadLocal 입니다.
이 말 즉슨 서버에 접속해서 생성되는 각 스레드(사용자)는 저마다의 ThreadLocal 에 SecurityContext 를 가지고 있습니다.
만약 사용자가 인증에 성공했다면 SecurityContext 에는 UsernamePasswordAuthenticationToken 객체가 저장되어 있고 SecurityContext 는 ThreadLocal 에 저장되어 있으며 동시에 HttpSession 에도 저장되어 있습니다.
그리고 인증 이후에는 SecurityContextPersistenceFilter 가 인증 당시 HttpSession 에 저장되어 있던 SecurityContext 를 꺼내어서 SecurityContextHolder 에 담기 때문에 어플리케이션 전역적으로 참조가 가능하게 됩니다.
즉 SecurityContextHolder.getContext().getAuthentication() 로 인증객체를 얻을 수 있게 됩니다..
그런데 만약 지금 실행중인 스레드가 아닌 제 3의 스레드 혹은 실행 프로세스가 SecurityContextHolder.getContext() 를 실행하게 되면 스프링 시큐리티는 SecurityContextHolder.getContext() 를 호출한 제 3의 스레드에서 ThreadLocal 에 저장된 SecurityContext 를 찾게 되는데 해당 ThreadLocal 에는 인증 당시 저장한 SecurityContext 가 존재하지 않기 때문에 스프링 시큐리티는 SecurityContext 객체를 새롭게 생성해서 ThreadLocal 에 저장하게 되고 SecurityContextHolder 는 전략 모드에 따라 ThreadLocal 를 감싸게 됩니다.
그렇게 되면 제 3의 스레드는 Authentication 가 null 인 SecurityContext 의 상태로 스프링 시큐리티의 각 보안필터를 거치게 되는데 일반적으로 이럴 경우에는 AnonymousAuthenticationFilter 가 AnonymousAuthenticationToken 을 생성해서 principal 에는 anonymous_user 문자열 값을 저장하고 authorities 에는 ROLE_ANONYMOUS 권한을 저장해서 AnonymousAuthenticationToken 를 SecurityContext 객체에 담게 됩니다.
그래서 질의하신 내용이 여기에 해당되는지는 정확하게 모르겠으나 기억하실 점은 인증당시에 SecurityContext 에 저장한 Authentication 객체를 어떤 임의의 지점에서 다시 호출했을 때 저장된 Authentication 가 나오지 않는다면 동일한 스레드 내에서 호출한 것이 아닌 서로 다른 스레드에서 호출할 경우 그럴 수 있다는 점입니다.
다시 말씀드리면 SecurityContext 의 스코프는 ThreadLocal 이며 그렇기 때문에 각 스레드는 ThreadLocal 에 저장된 SecurityContext 를 공유하지 않는다는 점을 기억하시기 바랍니다.
혹시 소스를 올려주시면 좀 더 파악하기가 쉬울 것 같습니다.
시큐리티 공부 버전 질문
0
175
1
[해결 방법] MethodSecurityConfig.customMethodSecurityMetadataSource() 호출하지 않는 이슈
0
185
1
AbstractSecurityInterceptor.class.beforeInvocation()를 2번 실행하는 경우
0
174
1
강의 코드가 왜이렇게 뒤죽박죽인가요...
0
249
1
메인 페이지로 접속해도 login url로 리다이렉트가 되지 않습니다..
0
235
1
파라미터값이 넘어가지 않습니다 ....
0
374
1
security filterChain 설정 질문이 있습니다.
0
331
1
소스 부분 질문 드립니다.
0
208
2
섹션4 7번 강의 문제가 있는거 같네요.
0
344
2
파일이 수시로 이름이 바껴있네요 ㄷㄷ
0
304
1
HttpSessionSecurityContextRepository를 사용안하는 문제
0
555
2
error , exception 이 잘 안됩니다.
0
280
2
thymeleaf tag 질문합니다.
0
196
2
버전업하면서 deprecated된 것들이 너무많아요
0
478
1
spring security 패치 관련
0
437
1
모바일을 사용할때 토큰말고 세션
0
845
2
DB 연동한 인가 부분에 대한 질문입니다!
0
264
1
Ajax방식도 똑같이 Session방식을 사용하는건가요?
0
307
1
Config 파일 생성 시 질문이 있습니다.
0
225
1
강사님 몇일동안 구글 검색만 100개 했는데도 이유를 모르겠습니다..
1
429
2
403 에러 뜹니다.
0
813
2
login_proc의 존재에 대한 간략한 설명입니다
0
276
1
top.html에 로그인 링크를 만들어서 로그인을 해봤습니다
0
282
2
안녕하세요. DB에 저장될 때 이해 안 가는 값이 있어서 질문드립니다!
0
189
1





