2013-08-06 2 views
15

다음 코드를 사용하여 시스템에서 사용자를 로그 아웃했습니다. 이는 모든 새로운 사용자에 대해 동일한 JSESSION ID가에서 로그인하는 동안 다시 사용으로 인해로그 아웃은 브라우저에서 JSESSIONID 뒤에 있습니다. 그것을 지우는 방법?

/** 
* This function helps to set the session attribute for the present user to null and then 
* removes the attribute itself and this helps in clearing the session 
* @param request 
* @param response 
*/ 
@RequestMapping(value = AuthConstants.EXIT, method = RequestMethod.POST) 
public void exitPrime(HttpServletRequest request, HttpServletResponse response) { 
     /*Getting session and then invalidating it*/ 
     HttpSession session = request.getSession(false); 
     if(request.isRequestedSessionIdValid() && session != null) 
     { 
      session.invalidate(); 

     } 
} 

이는 동안 여전히 로그인하여 주어 성공적으로 로그 아웃하지만 JSESSION ID로 연결 브라우저에 남아 있습니다. JSESSIONID 쿠키가 현재 세션에 대해서만 유효하고 사용자가 일단 로그 아웃하면 다음 번에 수행 할 로그인에 대해 파손되거나 유효하지 않아야합니다. 다음과 같이 내 로그인 코드는 다음과 같습니다 -

/** 
* This method allows one to log into the system and generates a token for a valid employee. 
* @param authRequest 
* @param request 
* @param response 
* @return 
*/ 
@RequestMapping(value = AuthConstants.ENTRY, method = RequestMethod.POST, consumes = ApplicationConstants.APPLICATION_JSON) 
public @ResponseBody 
AuthResponse primeEntry(@RequestBody AuthRequest authRequest,HttpServletRequest request, HttpServletResponse response) { 
    AuthResponse authResponse = new AuthResponse(); 
    if(authRequest != null && authRequest.getEmployeeAuth().getEmployeeNumber() != null 
      && !authRequest.getEmployeeAuth().getEmployeeNumber().isEmpty()){ 
     /*To check whether the user is valid*/ 
     String employeeNumber = authRequest.getEmployeeAuth().getEmployeeNumber(); 
     UserBean userBean = new UserBean(); 
     userBean = userService.getUser(employeeNumber); 
     if(userBean != null) 
      { 
      HttpSession session = request.getSession(true); 
      session.setAttribute("user", userBean); 
      setAuthResponseSuccess(authResponse); 
     }else{ 
      /*If user does not exist the too throw error 500*/ 
      setAuthResponseFailure(authResponse); 
     } 
    }else{ 
     /*If input JSON is not valid then throw error 500*/ 
     setAuthResponseFailure(authResponse); 
    } 
    return authResponse; 
} 

나는 스프링 3.2를 사용하여 로그인과 로그 아웃을 수동으로하고 싶은하고있다. 도와주세요.

전체 클래스 코드만큼 이미 무효입니다 귀하의 브라우저에서 JSESSIONID의 남은 아무 문제가 없습니다

@Controller 
@RequestMapping(value = "/auth") 
public class AuthController { 
    @Autowired 
    HttpServletRequest request; 

    @Autowired 
    HttpSession session; 

    @Autowired 
    IUserService userService; 

    /** 
    * This method allows one to log into the system and generates a token for a valid employee. 
    * @param authRequest 
    * @param request 
    * @param response 
    * @return 
    */ 
    @RequestMapping(value = AuthConstants.ENTRY, method = RequestMethod.POST, consumes = ApplicationConstants.APPLICATION_JSON) 
    public @ResponseBody 
    AuthResponse primeEntry(@RequestBody AuthRequest authRequest,HttpServletRequest request, HttpServletResponse response) { 
     AuthResponse authResponse = new AuthResponse(); 
     if(authRequest != null && authRequest.getEmployeeAuth().getEmployeeNumber() != null 
       && !authRequest.getEmployeeAuth().getEmployeeNumber().isEmpty()){ 
      /*To check whether the user is valid*/ 
      String employeeNumber = authRequest.getEmployeeAuth().getEmployeeNumber(); 
      UserBean userBean = new UserBean(); 
      userBean = userService.getUser(employeeNumber); 
      if(userBean != null) 
       { 
       HttpSession session = request.getSession(true); 
       session.setAttribute("user", userBean); 
       setAuthResponseSuccess(authResponse); 
      }else{ 
       /*If user does not exist the too throw error 500*/ 
       setAuthResponseFailure(authResponse); 
      } 
     }else{ 
      /*If input JSON is not valid then throw error 500*/ 
      setAuthResponseFailure(authResponse); 
     } 
     return authResponse; 
    } 


    /** 
    * This function helps to set the session attribute for the present user to null and then 
    * removes the attribute itself and this helps in clearing the session 
    * @param request 
    * @param response 
    */ 
    @RequestMapping(value = AuthConstants.EXIT, method = RequestMethod.POST) 
    public void exitPrime(HttpServletRequest request, HttpServletResponse response) { 
      /*Getting session and then invalidating it*/ 
      HttpSession session = request.getSession(false); 
      if(request.isRequestedSessionIdValid() && session != null) 
      { 
       session.invalidate(); 

      } 
    } 

    private AuthResponse setAuthResponseFailure(AuthResponse authResponse) { 
     authResponse.setResponseCode(ApplicationConstants.INTERNAL_ERROR_CODE); 
     authResponse.setStatus(StatusType.FAILURE); 
     authResponse.setResponseMsg(ApplicationConstants.INTERNAL_ERROR_MESSAGE); 
     return authResponse; 
    } 
    private AuthResponse setAuthResponseSuccess(AuthResponse authResponse){ 
     authResponse.setResponseCode(ApplicationConstants.OK); 
     authResponse.setStatus(StatusType.SUCCESS); 
     authResponse.setResponseMsg(ApplicationConstants.LOGIN_SUCCESS); 
     return authResponse; 
    } 
} 
+0

누군가가 요격기를보고 싶다면 알려 주시기 바랍니다. –

+0

봄 보안을 사용하고 있습니까? – Santosh

+0

아니요! 나는 그것을 수동으로하고 싶다. 그게 가능한가? –

답변

7

. JSESSIONID는 실제 데이터를 포함하지 않는 임의의 문자입니다.

그러나 클래스 수준에서 @SessionAttributes 주석을 사용한 것으로 의심되어 session.invalidate()을 시도했습니다. 이전 세션이 무효화 된 후이 시나리오를 사용하면 지정된 모델 특성을 세션에 유지해야하기 때문에 스프링 의 새 세션 (JSESSIONID)을 자동으로 만듭니다.

더 나은 방법은 @SessionAttributes이없는 새 컨트롤러를 만들고 거기에서 세션을 무효화하는 것입니다.

+0

위의 전체 코드를 게시했고 클래스 수준에서 @SessionAttribute를 사용하지 않았습니다. 좀 봐주세요 그리고 거기에 뭔가 잘못 있다면 알려주십시오 :) –

+0

희망이 훨씬 명확하게 :) –

+0

나는 쿠키 권리와 만료 속성을 추가 할 수 있다고 생각하니? –

1

내가 생각할 수있는 한 가지 방법은 로그 아웃시 JSESSIONID 쿠키를 삭제하는 것입니다. 쿠키를 삭제하는 방법은 다음과 같이 나이를 0으로 설정하는 것입니다.

Cookie cookie = new Cookie(); 
cookie.setValue(null); 
cookie.setMaxAge(0); 
cookie.setPath("/"); 

여기에 루트로 경로를 추가했습니다. 올바른 경로를 찾으려면 브라우저에서 JSESSIONID 쿠키를 확인하십시오.

이이 있으면, 당신은 당신의 exitPrime() 방법이 코드를 넣을 수 있습니다 응답

response.addCookie(cookie); 

이를 추가 할 수 있습니다.

+0

쿠키 값이 null 일 수 있습니까 ?? 또는 길이가 0 일 수 있습니까? –

+0

예. 길이가 0 인 문자열을 가질 수는 있지만 'maxAge'가 0으로 설정되어 쿠키가 즉시 만료되므로 중요하지 않습니다. – Santosh

+0

다음과 같이 u가 제공 한 코드를 사용했습니다. 쿠키 쿠키 = 새 쿠키 ("JSESSION", ""); // null 일 수 있음 cookie.setValue (""); // 위와 같은 이유입니다. 나머지 코드는 동일하게 유지되었습니다. ' 이것은 문제를 해결하고 쿠키를 지우지 만, y는 서버가 무효화 된 후에도 이전 것과 동일한 sessionid를 생성한다는 것을 다른 생각으로이 끕니다 (이전의 경우?)하지만 여전히 !! !! : D –

6

비트를 실험 한 후 브라우저 쿠키 값을 유지하려면 아무 것도하지 말고 위의 코드를 사용하면 문제가 없다고 결론을 내 렸습니다. 반면에 당신은 그럼이 코드를 가지고 그것을 밖으로 시도 할 수

Set-Cookie: JSESSIONID=""; Expires=Thu, 01-Jan-1970 00:00:10 GMT; Path=/

같은 쿠키 뭔가의 출력을 원하는 경우.

private void handleLogOutResponseCookie(HttpServletResponse response) { 
     Cookie[] cookies = request.getCookies(); 
     for (Cookie cookie : cookies) { 
      cookie.setMaxAge(0); 
      cookie.setValue(null); 
      cookie.setPath("/"); 
      response.addCookie(cookie); 
     } 

이렇게하면 로그 아웃 중에 문제가 해결되고 쿠키가 삭제됩니다.

+2

요청에서 모든 쿠키를 삭제하는 것은 바람직하지 않습니다. 예를 들어로드 밸런서 쿠키 또는 웹 서버 추적 쿠키와 같이 응용 프로그램이 작성하지 않은 것이있을 수 있습니다. – asgs

1

실제 쿠키는 아직 유효하지 않지만 LogoutFilter를 확장하면 맞춤 쿠키 무효화를 비롯하여 로그 아웃시 정확한 단계를 지정할 수 있습니다.

<beans:bean id="sessionInvalidationFilter" class="org.springframework.security.web.authentication.logout.LogoutFilter"> 
    <beans:property name="filterProcessesUrl" value="/logout"/> 
    <beans:constructor-arg> 
     <beans:array> 
      <beans:bean class="org.springframework.security.web.authentication.logout.SecurityContextLogoutHandler"/> 
      <beans:bean class="org.springframework.security.web.authentication.logout.CookieClearingLogoutHandler"> 
       <beans:constructor-arg value="JSESSIONID"/> 
      </beans:bean> 
     </beans:array> 
    </beans:constructor-arg> 
</beans:bean> 
1

나를 위해 작동하지 않았다 이전에 나열된 방법,하지만 내가 일을하는 데있어 약간의 수정과 함께, 난 단지 너무 YMMV하지만 제한된 테스트를 완료했습니다.

protected void doPost(HttpServletRequest req, HttpServletResponse res) throws ServletException, IOException { 
    HttpSession session = req.getSession(false); 
    if (session != null) { 
    String sessionId = session.getId(); 
    session.invalidate(); 
    Cookie[] cookies = req.getCookies(); 
    for (Cookie cookie : cookies) { 
     if (sessionId.equalsIgnoreCase(cookie.getValue())) { 
     cookie.setMaxAge(0); 
     cookie.setValue(null); 
     cookie.setDomain(req.getServerName()); 
     cookie.setPath(req.getServletContext().getContextPath() + "/"); 
     cookie.setSecure(req.isSecure()); 
     res.addCookie(cookie); 
     break; 
     } 
    } 
    } 
} 
1

톰캣은 컨텍스트 경로 끝에 슬래시를 추가합니다. 이제 delete-cookie 속성을 설정하면 Spring은 끝에 슬래시가없는 경로의 쿠키를 찾으려고 시도합니다. 쿠키를 찾지 못하기 때문에 쿠키가 제거되지 않아 로그인 페이지 대신 세션 만료 페이지가 표시됩니다.

다음 해결 방법은 트릭을 수행합니다.

public void logout(HttpServletRequest request, HttpServletResponse response, 
        Authentication auth) { 
    Cookie cookieWithSlash = new Cookie("JSESSIONID", null); 
    //Tomcat adds extra slash at the end of context path (e.g. "/foo/") 
    cookieWithSlash.setPath(request.getContextPath() + "/"); 
    cookieWithSlash.setMaxAge(0); 

    Cookie cookieWithoutSlash = new Cookie("JSESSIONID", null); 
    //JBoss doesn't add extra slash at the end of context path (e.g. "/foo") 
    cookieWithoutSlash.setPath(request.getContextPath()); 
    cookieWithoutSlash.setMaxAge(0); 

    //Remove cookies on logout so that invalidSessionURL (session timeout) is not displayed on proper logout event 
    response.addCookie(cookieWithSlash); //For Tomcat 
    response.addCookie(cookieWithoutSlash); //For JBoss 
} 
+0

감사합니다. Grails 2.4.4 작업 –

관련 문제