如何优雅地处理Ajax调用的登录过期?

时间:2022-11-29 14:02:51

My web application is made up of a lot of Ajax calls to server side RESTful APIs. Each time a customer login my site, the login page will get a JWT (JSON Web Token) token from server and store it as a cookie on client side. (I choose to store it as cookie because it is the only way to let the browser send it automatically and it is said to be safer than HTML5 Web Storage). There's a field in the token describing the token's expiration date. For each Ajax call, the token is sent along for authentication.

我的web应用程序由许多对服务器端RESTful api的Ajax调用组成。每次客户登录我的站点时,登录页面都会从服务器获得一个JWT (JSON Web令牌)令牌,并将其作为cookie存储在客户端。(我选择将它存储为cookie,因为这是让浏览器自动发送的唯一方式,据说它比HTML5 Web Storage更安全)。标记中有一个字段描述该标记的过期日期。对于每个Ajax调用,都发送令牌进行身份验证。

If client stays on my page for long, the token can expire. And the server will detect it when client making the next HTTP request (not just REST call). I use a servlet filter to intercept all HTTP requests and check the token for expiration. If the token expired, a redirection-to-login-page response will be sent.

如果客户端长时间停留在我的页面上,则令牌可能过期。当客户机发出下一个HTTP请求(而不仅仅是REST调用)时,服务器将检测它。我使用servlet过滤器拦截所有HTTP请求并检查令牌是否过期。如果令牌过期,将发送一个重定向到登录页面的响应。

But there's a problem about the above approach: "How to gracefully handle the redirection-to-login-page response on client side?"

但是上面的方法有一个问题:“如何在客户端优雅地处理重定向到登录页面的响应?”

  • For non-Ajax originated HTTP request, I can rely on browser to handle the redirection-to-login-page response and make page jump automatically.

    对于源自非ajax的HTTP请求,我可以依赖浏览器来处理重定向到登录页面的响应,并使页面自动跳转。

  • For Ajax originated HTTP request, it seems I need to add extra logic to each ajax call's completion handler to detect the redirection-to-login-page response and imperatively make the page jump .

    对于源自Ajax的HTTP请求,似乎需要在每个Ajax调用的完成处理程序中添加额外的逻辑,以检测重定向到登录页面的响应,并紧急地进行页面跳转。

Or am I totally on a wrong way?

还是我完全走错路了?

Some refs:

一些参考文献:

JWT (JSON Web Token) automatic prolongation of expiration

JWT (JSON Web令牌)自动延长过期时间

Which authentication strategy should I use for my API?

我应该为我的API使用哪种身份验证策略?

Implicit & Explicit authentication

隐式和显式验证

ADD 1:

加1:

It seems the browser will handle the 302 redirection transparently. So maybe I can just return a 302 redirection to the login page, be it for a ajax call or a plain page visit. I will try and respond later.

看来浏览器会透明地处理302重定向。也许我可以返回302重定向到登录页面,不管是ajax调用还是普通页面访问。我稍后再回答。

From here:

从这里开始:

If the response is an HTTP redirect (status code 301, 302, 303 or 307), then it MUST be transparently followed (unless it violates security or infinite loop precautions). Any other error (including a 401) MUST cause the object to use that error page as the response.

如果响应是HTTP重定向(状态代码301、302、303或307),那么必须透明地遵循它(除非违反安全性或无限循环预防)。任何其他错误(包括401)必须导致对象使用错误页面作为响应。

Catching 302 FOUND in JavaScript

捕获JavaScript中找到的302

How to manage a redirect request after a jQuery Ajax call

如何在jQuery Ajax调用后管理重定向请求?

4 个解决方案

#1


9  

For exactly this reason, web APIs should not respond with 302 redirect, but with 401 unauthorized when the token has expired.

正是由于这个原因,web api不应该以302重定向响应,而是在令牌过期时以401未授权方式响应。

Web applications should return 302 responses as they are always meant to be consumed by browser like agents. For more information see also my answer here.

Web应用程序应该返回302个响应,因为它们总是被浏览器(如代理)使用。更多信息请参见我的答案。

#2


2  

A 302 redirect will not work for a javascript (ajax) call it will simply call the new page from within javascript and not the actual browser.

302重定向对javascript (ajax)调用不起作用,它只是从javascript内部调用新页面,而不是实际的浏览器。

The neat solution is to return a json object with an error message and either displaying that error message. or then using javascript to change the location to the login page

简洁的解决方案是返回带有错误消息的json对象,并显示该错误消息。或者使用javascript将位置更改为登录页面。

#3


2  

Yeah, I think you are right.

是的,我认为你是对的。

For non-ajax, you can handler it in the serve end using redirect.

对于非ajax,可以使用重定向在服务端处理它。

For ajax, you can switch the page depending the ajax result.

对于ajax,可以根据ajax结果切换页面。

#4


1  

You can use a Global Ajax Event Handler for handling session expiration generally.

通常可以使用全局Ajax事件处理程序来处理会话过期。

Try to catch the .ajaxError() , and then check if its a session expiry or something else, and behave accordingly.

尝试捕获. ajaxerror(),然后检查它是会话过期还是其他什么,并相应地进行操作。

I haven't try this to be honest, but it worth a shot.

说实话,我还没试过,但值得一试。

#1


9  

For exactly this reason, web APIs should not respond with 302 redirect, but with 401 unauthorized when the token has expired.

正是由于这个原因,web api不应该以302重定向响应,而是在令牌过期时以401未授权方式响应。

Web applications should return 302 responses as they are always meant to be consumed by browser like agents. For more information see also my answer here.

Web应用程序应该返回302个响应,因为它们总是被浏览器(如代理)使用。更多信息请参见我的答案。

#2


2  

A 302 redirect will not work for a javascript (ajax) call it will simply call the new page from within javascript and not the actual browser.

302重定向对javascript (ajax)调用不起作用,它只是从javascript内部调用新页面,而不是实际的浏览器。

The neat solution is to return a json object with an error message and either displaying that error message. or then using javascript to change the location to the login page

简洁的解决方案是返回带有错误消息的json对象,并显示该错误消息。或者使用javascript将位置更改为登录页面。

#3


2  

Yeah, I think you are right.

是的,我认为你是对的。

For non-ajax, you can handler it in the serve end using redirect.

对于非ajax,可以使用重定向在服务端处理它。

For ajax, you can switch the page depending the ajax result.

对于ajax,可以根据ajax结果切换页面。

#4


1  

You can use a Global Ajax Event Handler for handling session expiration generally.

通常可以使用全局Ajax事件处理程序来处理会话过期。

Try to catch the .ajaxError() , and then check if its a session expiry or something else, and behave accordingly.

尝试捕获. ajaxerror(),然后检查它是会话过期还是其他什么,并相应地进行操作。

I haven't try this to be honest, but it worth a shot.

说实话,我还没试过,但值得一试。