1. ホーム

[解決済み】セッションは本当にRESTfulnessに違反するのか?

2022-05-31 03:53:30

質問

RESTful API でセッションを使用することは、本当に RESTfulness に違反しているのでしょうか?私はどちらかの方向に向かう多くの意見を見ましたが、私はセッションが RESTless . 私の見解からすると。

  • 認証は RESTfulness のために禁止されていません (そうでなければ、RESTful サービスにはほとんど使用できません)
  • 認証はリクエストの中で認証トークンを送信することで行われ、通常はヘッダ
  • この認証トークンは何らかの方法で取得する必要があり、取り消される可能性もあるため、その場合は更新する必要があります。
  • 認証トークンは、サーバーによって検証される必要があります(そうでない場合は認証されません)。

では、セッションはどのようにこれに違反するのでしょうか?

  • クライアント側で、セッションはクッキーを使って実現される
  • クッキーは単に HTTP ヘッダーの追加です。
  • セッションクッキーはいつでも取得でき、取り消すことができます。
  • セッション・クッキーは、必要であれば無限の寿命を持つことができます。
  • セッション ID (認証トークン) はサーバーサイドで検証されます。

このように、クライアントにとってセッションクッキーは、他の HTTP ヘッダベースの認証機構とまったく同じものですが、セッションクッキーの認証には Cookie ヘッダーの代わりに Authorization などの独自のヘッダを使用していました。もし、サーバーサイドでCookieの値にセッションが付加されていなかったとしたら、なぜそのような違いが生じるのでしょうか?サーバーサイドの実装は、サーバーが が動作する限り、サーバー側の実装はクライアントに関係ありません。 RESTfulです。そのため、クッキーそれ自体では、APIをにするべきではありません。 RESTless にするべきではありませんし、セッションはクライアントにとって単なるCookieです。

私の仮定は間違っているのでしょうか?何がセッション・クッキーを RESTレス ?

どのように解決するのですか?

まず、いくつかの用語を定義しましょう。

  • RESTful。

    このセクションで説明した REST 制約に準拠するアプリケーションを、"RESTful" として特徴付けることができます。 このセクションで説明した制約に適合するアプリケーションをRESTfulと特徴付けることができます。 サービスが必要な制約のいずれかに違反している場合、それはRESTfulとは見なされません。

    によると ウィキペディア .

  • ステートレス制約です。

    次に、クライアントとサーバーの相互作用に制約を加えます。 のように、通信は本質的にステートレスでなければなりません。 3.4.3節(図5-3)のCSS(client-stateless-server)スタイルのように、通信は本質的にステートレスでなければなりません。 クライアントからサーバーへの各リクエストは、そのリクエストを理解するために必要なすべての情報を含んでいなければなりません。 そのため、クライアントからサーバへの各リクエストは、 リクエストを理解するために必要なすべての情報を含んでいなければならず サーバに保存されているコンテキストを利用することはできません。セッションの状態は そのため、セッションの状態は完全にクライアント上に保持されます。

    によると フィールディング論文 .

つまり、サーバーサイドのセッションはRESTのステートレス制約に違反するので、RESTfulnessも違反することになります。

このように、クライアントにとって、セッションクッキーは、他のHTTPヘッダーベースの認証メカニズムとまったく同じです。 他のHTTPヘッダーベースの認証メカニズムとまったく同じですが、Authorizationヘッダーの代わりにCookieヘッダーを使用する点が異なります。 ヘッダーの代わりにCookieヘッダーを使用することです。 ヘッダーの代わりに Cookie ヘッダーを使用することです。

セッションクッキーによって、クライアントの状態をサーバーに保存するため、リクエストにはコンテキストがあります。ロードバランサーと別のサービスインスタンスをシステムに追加してみましょう。この場合、サービスインスタンス間でセッションを共有しなければなりません。このようなシステムを維持・拡張するのは難しいので、ひどくスケールしてしまいます...。

私の意見では、Cookieは何も間違っていません。Cookie技術はクライアントサイドの保存メカニズムであり、保存されたデータはリクエストごとに自動的にCookieヘッダーに添付されます。このような技術で問題があるREST制約を私は知りません。つまり、技術そのものに問題はなく、問題はその使い方にあるのです。 Fieldingはサブセクションを書きました。 に、なぜHTTPクッキーが悪いと考えるかについて書いています。

<ブロッククオート

私の見解からすると

  • 認証は RESTfulness のために禁止されていません (そうでなければ、RESTful サービスにはほとんど使い道がありません)。
  • 認証は、リクエストの中で認証トークンを送信することで行われ、通常はヘッダ
  • この認証トークンは何らかの方法で取得する必要があり、取り消される可能性もあるため、その場合は更新する必要があります。
  • 認証トークンは、サーバーによって検証される必要があります(そうでない場合は認証されません)。

ご指摘の点はかなりしっかりしていました。唯一の問題は、サーバー上で認証トークンを作成するというコンセプトでした。その部分は必要ありません。必要なのは、ユーザー名とパスワードをクライアントに保存して、リクエストごとにそれを送信することです。これを行うには、HTTP Basic Authと暗号化された接続以上のものは必要ありません。

  • 図1. - 信頼できるクライアントによるステートレス認証

すべてのリクエストを認証しなければならないので、おそらく高速化するためにサーバー側でインメモリの認証キャッシュが必要でしょう。

さて、これはあなたによって書かれた信頼できるクライアントによってかなりうまくいきますが、サードパーティクライアントはどうでしょうか?ユーザー名とパスワード、そしてユーザーのすべての権限を持つことはできません。そこで、サードパーティクライアントが特定のユーザーによって持つことができる権限を個別に保存する必要があります。そこで、クライアント開発者はサードパーティークライアントを登録し、固有のAPIキーを取得することで、ユーザーはサードパーティークライアントに自分の権限の一部へのアクセスを許可することができます。例えば、名前と電子メールアドレスの読み取りや、友達のリストなどです。サードパーティークライアントを許可すると、サーバーはアクセストークンを生成します。このアクセストークンを使って、サードパーティークライアントはユーザーによって与えられたアクセス権にアクセスすることができます。

  • 図2. - サードパーティークライアントによるステートレス認証

そのため、サードパーティークライアントは、信頼できるクライアントから(またはユーザーから直接)アクセストークンを取得することができます。その後、APIキーとアクセストークンを使って有効なリクエストを送信することができます。これは最も基本的なサードパーティ認証の仕組みです。実装の詳細については、OAuth などの各サードパーティ認証システムのドキュメントを参照ください。もちろん、もっと複雑で安全な方法もあります。たとえば、サーバ側でリクエストごとに署名を行い、その署名をリクエストに添付して送信する、などなど。実際の解決策は、アプリケーションの必要性に依存します。