🙄

セッションを理解する

に公開

はじめに

最近はSPA+JWTの構成ばかりで、「セッションって何だっけ?」という状態になっていたので、改めて整理しました。

想定読者

Webエンジニアの初心者〜中級者

セッションとは

クライアントとサーバ間でのステートフルな通信を実現する仕組み、つまりサーバ側でステートを管理する仕組みのことです。

HTTPはステートレス(状態を保持しない)なプロトコルなので、ユーザーのログイン状態を維持するには、何らかの仕組みでステートを管理する必要があります。そこで利用されるのがセッションであり、具体的には「クッキーを使う」ことで、ステートフルな通信を実現できます。

クッキーの使い方

クッキーは「情報の保管庫」として利用されます。

  1. サーバが情報をクッキーに入れて、レスポンスと一緒にクライアントへ送信する
  2. クライアントは、次回のリクエスト時にそのクッキーをサーバに送信する
    こうすることで、サーバは次のように判断できます:

「このリクエストは、前回と同じクライアントから来ているな」

このように「クライアントを識別する」ことで、ステートフルな通信を実現します。

クッキーに入れるもの

クッキーにはセッションIDを保存します。サーバ側では次のように動作します。

  1. サーバがセッションIDを生成し、クッキーに入れてクライアントへ送信する
  2. サーバはセッション情報として、セッションIDとユーザーIDをメモリまたはデータベースに保存する
  3. クライアントがリクエストを送ると、サーバはクッキー内のセッションIDを取り出す
  4. 保存されているセッションIDと照合し、ユーザーIDを特定してデータベースからデータを取得する

こうして、サーバは「クライアントを安全に識別」できます。

なぜセッション情報にユーザーIDも保存するのか

セッションIDとあわせてユーザーIDを保存するのは、クライアントが異なるデバイスからリクエストした場合でも、同じユーザーとして識別できるようにするためです。

  • デバイスごとにセッションIDは異なる
  • そのため、セッションIDだけでは「同一ユーザー」と判断できない
  • しかし、ユーザーIDをキーとしてデータを取得すれば、同じユーザーを特定できる

この仕組みにより、「複数デバイスでも同じユーザーとして扱える」ようになります。

セッションIDを使わずユーザーIDを直接クッキーに入れればよいのでは

確かに、クッキーにユーザーIDを直接入れれば、サーバ側で簡単にユーザーを識別できます。しかし、これはセキュリティ上の重大なリスクがあります。

  • クッキーはクライアント(ブラウザ)側に保存される
  • ユーザーや攻撃者が中身を閲覧・改ざんできる
  • ユーザーIDは固定値であり推測しやすい

もしユーザーIDがそのまま入っていれば、他人のユーザーIDに書き換えて不正アクセスされる可能性があります。
一方、セッションIDもクライアント側に保存され、中身を閲覧・改ざんされる可能性はありますが、ランダムで推測困難な一時トークンです。そのため、ユーザーIDを直接扱うよりも安全です。さらに、クッキーの保護属性(Secure・HttpOnly)を組み合わせることで、「誰のリクエストかを安全に識別」できるようになります。

まとめ

  • セッションはクライアントとサーバ間でのステートフルな通信を実現する仕組みであり、サーバ側で状態を管理する仕組み
  • サーバ側で状態を管理するためにはクッキーを使う
  • サーバはクッキーにセッションIDを入れてクライアントに送信し、セッションIDとユーザーIDをサーバ側で紐付けて管理する
  • クライアントのリクエスト時に、サーバはクッキー内のセッションIDを照合し、対応するユーザー情報を取得する(=クライアントを識別する)

おわりに

冒頭で述べたように、SPA+JWTの構成ではアクセストークンを使ってリクエストを送るため、通信はステートレスです。
一方、セッションはクライアントとサーバ間でのステートフルな通信を実現する仕組みであり、サーバ側で状態を保持する際に登場する概念です。
この辺りが混同しないように整理して理解しておくことが大切です。

参考文献

[改訂新版]プロになるためのWeb技術入門

Discussion