Djangoアプリケーションには、次のセッション管理要件があります。
- ユーザーがブラウザを閉じると、セッションは期限切れになります。
- 非アクティブな期間が経過すると、セッションは期限切れになります。
- 非アクティブが原因でセッションが期限切れになるタイミングを検出し、適切なメッセージをユーザーに表示します。
- 非アクティブ期間が終了する数分前にセッションの期限が切れることをユーザーに警告します。警告とともに、セッションを延長するオプションをユーザーに提供します。
- ユーザーがアプリ内でサーバーに送信されるリクエストを含まない長いビジネスアクティビティで作業している場合、セッションがタイムアウトしてはなりません。
ドキュメント、Djangoコード、およびこれに関連するいくつかのブログ投稿を読んだ後、次の実装アプローチを思いつきました。
要件1
この要件は、SESSION_EXPIRE_AT_BROWSER_CLOSEをTrueに設定することで簡単に実装できます。
要件2
セッションの有効期限を設定するためにSESSION_COOKIE_AGEを使用するいくつかの推奨事項を見ました。しかし、この方法には次のような問題があります。
ユーザーがアプリケーションをアクティブに使用している場合でも、セッションは常にSESSION_COOKIE_AGEの終了時に期限切れになります。(これは、カスタムミドルウェアを使用してすべてのリクエストでセッションの有効期限をSESSION_COOKIE_AGEに設定するか、SESSION_SAVE_EVERY_REQUESTをtrueに設定してすべてのリクエストでセッションを保存することで防ぐことができます。ただし、SESSION_COOKIE_AGEを使用するため、次の問題は避けられません。)
Cookieの動作方法により、SESSION_EXPIRE_AT_BROWSER_CLOSEとSESSION_COOKIE_AGEは相互に排他的です。つまり、Cookieはブラウザを閉じるか、指定された有効期限で期限切れになります。SESSION_COOKIE_AGEが使用され、Cookieの有効期限が切れる前にユーザーがブラウザーを閉じた場合、Cookieは保持され、ブラウザーを再度開くと、ユーザー(または他のユーザー)は再認証されずにシステムにアクセスできます。
Djangoは、存在するCookieのみに依存して、セッションがアクティブかどうかを判断します。セッションに保存されているセッションの有効期限はチェックしません。
この要件を実装し、上記の問題を回避するには、次の方法を使用できます。
- SESSION_COOKIE_AGEは設定しないでください。
- セッションの有効期限を、すべてのリクエストで「現在時刻+非アクティブ期間」に設定します。
- SessionMiddlewareでprocess_requestをオーバーライドし、セッションの有効期限を確認します。有効期限が切れている場合は、セッションを破棄してください。
要件3
(上記のカスタムSessionMiddlewareで)セッションの有効期限が切れたことを検出したら、リクエストに属性を設定してセッションの有効期限を示します。この属性は、ユーザーに適切なメッセージを表示するために使用できます。
要件4
JavaScriptを使用してユーザーの非アクティブを検出し、警告を提供し、セッションを延長するオプションも提供します。ユーザーが延長したい場合は、キープアライブパルスをサーバーに送信してセッションを延長します。
要件5
JavaScriptを使用して(長時間のビジネスオペレーション中の)ユーザーアクティビティを検出し、キープアライブパルスをサーバーに送信して、セッションが期限切れにならないようにします。
上記の実装アプローチは非常に手の込んだように見え、より簡単な方法(特に要件2の場合)があるのではないかと思っていました。
どんな洞察も高く評価されます。