9

私の要件は、ユーザーがWebページでアクティビティを実行しない場合に備えて、ユーザーセッションがx秒でタイムアウトすることを通知するポップアップでユーザーに通知することです。

この要件への追加は、ポップアップで値x秒を動的にデクリメントすることです。

私が使用している環境はJavaEEです。

4

3 に答える 3

13

とを利用HttpSession#getMaxInactiveInterval()setTimeout()ます。すべてのクライアント アクティビティ (ポーリング) でタイムアウトを延期する場合を除き、この特定の目的で Ajax は必要ありません。

基本的な例:

<script>
    var secondsBeforeExpire = ${pageContext.session.maxInactiveInterval};
    var timeToDecide = 15; // Give client 15 seconds to choose.
    setTimeout(function() {
        alert('Your session is about to timeout in ' + timeToDecide + ' seconds!')
    }, (secondsBeforeExpire - timeToDecide) * 1000);
</script>

メッセージ内の時間を魔法のように減らすには、基本的な代わりに、alert()HTML DOM ツリーを介してコンテンツを制御しsetTimeout()、テキストを動的に変更するために 1 秒で別のものを使用する div を使用したオーバーレイが必要です。

JspServletEL を機能させるには、このスクリプトを から提供する必要があることに注意してください。したがって、スクリプトを JSP ページの HTML に配置する必要があり<head>ます。または、すべての JS を別のファイルに格納したい場合は、すべての要求も処理*.jsさせる必要があります。JspServlet*.js

于 2009-12-31T13:34:45.507 に答える
2

Java / Java EEは、クライアント側で(つまり、JavaScriptを使用して)処理する必要があるため、ここではあまり役に立たないと思います。私が考えることができる1つの解決策は、サーバーのタイムアウトの数分前にユーザーに通知する一種のタイマーを設定することです。

これについてグーグルで調べていると、EricPascarelloのUpdateUser's Session with AJAXブログ投稿(およびリロードされたバージョンのUpdateing User Session with Ajax-Round 2)が、そのようなソリューションを正確に説明している(そして、を使用しXMLHttpRequestてセッションを更新する)ことがわかりました。彼のAjaxセッション管理スクリプトはここから入手できます。

于 2009-12-31T13:11:41.963 に答える
0

単純なサーブレット、spring-mvc、または spring-security のいずれかである可能性があります。完全なクライアント側のロジックがなければ、自動ログアウトは不可能です。
アプリケーションが両方のタイプのリクエストを持つことを考慮する

  • AJAXと
  • フォームの送信/ページのリロード

自動ログアウトには非常に計算されたロジックが必要です。自動ログアウト機能の実装を次のように提示する

利点。


1. これを達成するために余分な呼び出し/要求は使用されません。10,000 を超えるアクティブ ユーザーと、自動ログアウトを実現するための余分な呼び出しの場合のパフォーマンスへの影響を考慮します。
2. タグを使用した 1 回線構成。
3. ユーザーが複数のタブまたは複数のウィンドウを開いても問題なく動作します。
4. セッションが無効化される 30 秒前に通知されるため、フォームに入力して送信していない場合でも、セッションを維持できます (ワンクリックでセッションを延長できます)。したがって、ユーザーが保存されていないデータを失う可能性は低くなります。

使用法


1. 以下に示すように、必要な JSP ページに自動ログアウト スクリプトを含めます。

    ....
    </body>
    <jsp:include page="../template/autologout-script.jsp"></jsp:include>
</html>

2. JSP ページ autologout-script.jsp を作成し、以下のコードを追加します。 注: 編集/構成は必要ありません

<%@taglib prefix="c" uri="http://java.sun.com/jsp/jstl/core"%>

<script>
$(document).ready(function()
{
    var timeOutTimeInSeconds = ${ timeOutTimeInSeconds }; 
    var showTimerTimeInSeconds= ${ showTimerTimeInSeconds };

    var sessionCheckIntervalId = setInterval(redirectToLoginPage, timeOutTimeInSeconds * 1000);
    var timerDisplayIntervalId = setInterval(showTimer, (timeOutTimeInSeconds - showTimerTimeInSeconds) * 1000);
    var badgeTimerId;
    window.localStorage.setItem("AjaxRequestFired", new Date());

    function redirectToLoginPage(){
        //location.href =  '<c:url value="/" />'+'${loginPageUrl}';
        window.location.reload();
    }

    $(document).ajaxComplete(function () {
        resetTimer();
    });

    $(window).bind('storage', function (e) {
         if(e.originalEvent.key == "AjaxRequestFired"){
             console.log("Request sent from another tab, hence resetting timer")
             resetTimer();
         }
    });

    function resetTimer()
    {
        showTimerTimeInSeconds= ${ showTimerTimeInSeconds };

        console.log("timeOutTimeInSeconds : "+timeOutTimeInSeconds)
        window.localStorage.setItem("AjaxRequestFired", new Date());

        window.clearInterval(sessionCheckIntervalId);
        sessionCheckIntervalId = setInterval(redirectToLoginPage, timeOutTimeInSeconds * 1000);

        window.clearInterval(timerDisplayIntervalId);
        timerDisplayIntervalId = setInterval(showTimer, (timeOutTimeInSeconds - showTimerTimeInSeconds) * 1000);

        hideTimer();
    }

    function showTimer()
    {
        $('#sessionTimeRemaining').show();
        $('#sessionTimeRemainingBadge').html(showTimerTimeInSeconds--);
        window.clearInterval(timerDisplayIntervalId);
        badgeTimerId = setInterval(function(){
            $('#sessionTimeRemainingBadge').html(showTimerTimeInSeconds--);
        }, 1000);
    }

    function hideTimer()
    {
        window.clearInterval(badgeTimerId);
        $('#sessionTimeRemaining').hide();
    }
});
</script>

3. タイムアウト設定を構成するためのセッション属性を構成します 注: これは、セッションの作成後に構成します。HttpSessionListener sessionCreated メソッドを実装し、要件に従って次の構成を設定できます。

session.setMaxInactiveInterval(300);

session.setAttribute("timeOutTimeInSeconds", 300);
session.setAttribute("showTimerTimeInSeconds", 30);

4.タイマーを表示するためのhtmlを以下に追加します。
注: CSS が得意な場合は、autologout-script テンプレート ページに移動できます。したがって、すべてのページにこれを追加することを避けることができます。
ブートストラップを含めるか、カスタム CSS を追加します。

<span class="badge badge-primary" title="click to keep session alive" id="sessionTimeRemaining" 
    onclick="ajaxSessionRefresh()" style="display:none;">
    <i class="badge badge-danger" id="sessionTimeRemainingBadge" style="float:left">30</i>
     &nbsp; 
     <small>Refresh</small>
     <i class="glyphicon glyphicon-refresh"></i>
</span>

ここに画像の説明を入力

簡単な自動ログアウトの実装については以上です。私の github リポジトリから実際の例をダウンロードできます
シンプルなサーブレットの例を使用した自動ログアウト
spring-security Java 構成例
を使用した自動ログアウト spring-security xml 構成例を使用した自動ログアウト

ロジックの説明


ケース 1: ページの読み込み時
ここでのロジックは単純です。ページの読み込み時にインターバルのタイマーを maxInactiveInterval に設定します。タイムアウト後、ログイン ページにリダイレクトされます。
ケース 2: AJAX 呼び出しを追跡
する AJAX 要求を考慮すると、jquery の .ajaxStart() または .ajaxComplete() コールバックを使用して、ajax 要求が発生した場合に間隔をリセットできます。
ケース 3: 複数のタブ/ウィンドウ アクティビティの追跡 タブ
間通信は、各タブの状態を同期するために行われます。変更イベントで localStorage を使用しました。

制限事項/必要な改善点
1. 許可される最大セッション数が 1 の場合、セッションが別のシステムから取得されると、AJAX 要求は失敗します。ログインページにリダイレクトするために処理する必要があります。
2. ajaxComplete() の代わりに ajaxStart() を使用して、サーバーとブラウザーの間で idleTime 値を正確に同期します。

要件
1.Jquery

現在の実装の代替案の比較


1. http レスポンスにRefresh ヘッダーを設定します。(AJAX リクエストでは機能しません)

response.setHeader("Refresh", "60; URL=login.jsp");
  1. HTML でのメタ リフレッシュ タグの設定(AJAX リクエストでは機能しません)
<meta http-equiv="refresh" content="60; url=login.jsp">
  1. アクティビティ チェッカーの構成 繰り返される AJAX 要求によってセッションを維持します。アイドル時間を追跡し、タイムアウト後にログアウト要求を行います。
    シンプルなロジックで良いものであることは間違いありません。しかし、私は自分の観察にインクを塗りたいだけです。
    • セッションを維持し、5 万人のアクティブ ユーザーを維持するために 1 分間に 2 つのリクエストが行われた場合のパフォーマンスへの影響。1 分あたり 10 万件のリクエスト。
    • タブ間通信2 つのタブが開いていて、一方のタブがアクティビティを受信して​​いて、もう一方のタブがアクティビティを受信して​​いない場合、そのタブはログアウト要求を起動し、他のタブにアクティビティが存在する場合でもセッションを無効にします。(でも対応可能)
    • 強制ログアウトのアプローチセッションを無効にするためにクライアントがサーバーを支配しています。
于 2019-09-11T01:40:37.267 に答える