セッション変数を避けるべきですか?


36

以前はセッション変数に大きく依存していましたが、最近ではクエリ文字列パラメーターなどを使用して、それらの多くが不要であることがわかりました。

私の同僚がセッション変数の使用を拒否しています。これは現実的な目標であり、セッション変数は実用的な理由で避ける必要がありますか?セッション変数を完全に回避できますか(ログインを許可するセッションCookieを除く)、これにより設計が改善されますか?

私の同僚がそれらを使用しない理由は次のとおりです。

  • セッション変数の型指定されていない性質
  • セッションのタイムアウトにより状態が失われる
  • セッション変数のグローバルスコープの性質
  • セッションを失う負荷分散サーバー(.Net固有?)
  • アプリケーションプール/サーバーの再起動
  • 彼らは不要です

3
using things like query string parameters instead-この1つのケースでは、可能であれば常にクエリ文字列パラメーターを使用します。そのタイプのパラメーターにセッションを使用すると壊れやすく、ユーザーが複数のタブを開いているときに奇妙なバグが発生する可能性があります。
イズカタ

2
個人的な推奨事項-同僚が何を話しているのかはっきりとわからないので、同僚からアドバイスを受けないでください。セッションのタイムアウト?セッション期間がWebアプリによって制御されていることに気付いていませんか?
GrandmasterB

2
@GrandmasterBエヘム。彼らが何をしているのかわからないか、彼らのキャリアの過程でそれらの弾丸ポイントのそれぞれによって燃やされました(私自身はそれらの約4つを打ちました)、そして一時的な状態に対処するより適切な方法を知っています。
エドジェームズ

誰かがセッション状態と複数のタブを開くこととの関係を説明してもらえますか?新しいタブを開くと、そのタブには前のタブの状態が含まれていますか?ありがとう。
レイ

回答:


41

アプリケーションにセッション変数がある場合は、次のことを自問してください。

ブラウザの「戻る」ボタンをクリックすると、変数にどの値を設定する必要がありますか?

答えが「現在の値」である場合、セッション変数が役立つ場合があります。一例として、ショッピングカートがあります。履歴をたどるときにショッピングカートから物が削除されるとは思わないでしょう。常に現在の状態です。

答えが「以前の値」である場合、セッション変数を使用しないでください。私が見た悪い使い方には、ページ間でパラメータを渡すことが含まれます。戻るボタンをクリックしてページに戻ると、ページが必ずしも正しいパラメーターを取得するとは限りません。また、2つのタブを開いた場合、サイトはどのように動作しますか?

戻るボタンの動作を正しくすることは決して万能ではありませんが、Webサイトをステートレスアプリケーションとして考えるのに役立ちます。一般に、セッション変数の適切な使用法は、ごくわずかです。


同意する。複数のタブを使用して目的のセマンティクスを考えると、通常、セッション変数または要求パラメーターが正しい選択であるかどうかが明らかになります。
-CodesInChaos

私はセッション変数でこれらのタイプのエラーを正確に見てきましたが、確かに自分で難しい方法を学びました。
Tjaart

ユーザーが戻るボタンを押すと、セッションの有効期限が切れるまでアイテムがショッピングカート内に留まることを期待しますか?他の永続化メカニズム(データベースなど)を使用すると、単一セッションを超えた永続化が可能になり、戻るボタンはユーザーの期待どおりに機能します。
ロートンフォーグル14年

25

HTTPプロトコルはステートレスです。セッションは、HTTPリクエスト全体でクライアントの状態を保持する方法です。プラットフォームの組み込みセッション処理でそれを行うか、クエリ文字列パラメーターを使用して自分で行うかを選択できます。いずれにせよ、セッションの概念は多くのタスクに必要です。

あなたの同僚は、おそらく特定の実装を嫌うか、意図した目的のためにセッションを使用していません。HTTP要求間で特定のクライアント接続に関する情報を保持する必要がある場合は、何らかの形式のセッション永続性が必要です。

次の問題は実装固有です。

セッション変数の型指定されていない性質

セッション変数のグローバルスコープの性質

セッションを失う負荷分散サーバー

アプリケーションプール/サーバーの再起動

たとえば、私はほとんどの場合PHPで作業し、セッション情報をリレーショナルデータベースに保存します。したがって、セッション変数が入力されます。負荷分散とサーバーの再起動は、セッションの問題を引き起こしません。

これはもっと面白いです:

セッションのタイムアウトにより状態が失われる

セッションは、ほとんどの場合クッキーを介して保存されます。これらは、クライアントがいつでも削除できます。ただし、クエリ文字列パラメーターを介して保存することもできるため、クライアントでタイムアウトすることはありません。サーバーのタイムアウトはあなた次第です。したがって、この問題でさえも実装に固有です。

特定の実装が好きではないからといって、セッションの概念全体を捨てないでください。優れたWebアプリケーションフレームワークは、セッションを適切に使用してユーザーログインを保持したり、ユーザーの現在の訪問に固有のその他のものを保持したりするのに役立ちます。ユーザーのデータベースレコードは、ログイン時にユーザー固有の情報を保存するために使用できます(また、使用する必要があります)。ただし、匿名の訪問者は、最近のページの短いリストや既に見た通知を非表示にします。一般に、セッションストレージには適切な一時情報のみが適切です。


正直に言うと、.Net以外のフレームワークの経験は限られています。.Netは、セッションのタイムアウト値を強制する前に停止します。セッション変数は、型指定されていないディクショナリとしてサーバー側コードにバブルアップします。私は通常、この辞書を適切に型付けされたクラスでラップしているので、これも問題ではありません。セッション情報をデータベースに保存すると述べました。ASP .Netでは、ストレージは、.Netクライアント、データベース(自動管理)、または別のWindowsサービスのいずれかで処理されます。
Tjaart

セッションの目的の例をいくつか挙げていただけますか?
Tjaart

@Tjaart:最後の段落を少し拡張しました。お役に立てば幸いです。
マットS

14

他の人が(私は繰り返さないだろう)の良い点をたくさん作ってきたが、まだ議論されていないあなたの相棒の技術の一つの側面があります:セキュリティが

コードを見なくてもどのような脆弱性が発生するのかを知ることは不可能ですが、ここで頭に浮かんだいくつかのことを考えます。

  • セッションの固定:Cookieが適切に設定されたマシンをユーザーに使用させようとするのではなく、ユーザーがURLに必要な情報が既に含まれているリンクをクリックするだけである場合、少し簡単な強力な攻撃です。
  • SQLインジェクション(またはその他の悪意のある入力):ユーザーから送られてくるものを信頼しないでください。セッション変数にはサーバーを離れないという利点があるため、ユーザーは直接変数を変更できません。あなたがそれを置く前にデータをサニタイズする必要がありますがセッション、あなたは常にあなたが後で出て値を信頼することができます。すべてがクエリ文字列を介して渡される場合、悪意のある入力を受け入れていないことを確認するために必要な検証がたくさんあります。
  • 改ざんされた入力を使用したデータの破損:SQLインジェクションと同様に、どの程度の量のデータをやり取りしていますか?それはどれほど重要ですか?クエリ文字列の値を変更して、アプリの動作を変更できますか?値を変更してサーバー上のデータを破損できますか?サーバー上のデータが破損した場合、他のユーザーに影響しますか?(あなたの答えが「いいえ」だった場合、私の答えは「確かですか。確認する必要がある場所がたくさんあります。」)。

セッションを使用すると、これらのすべてが発生する可能性がありますが、バディが何をしているか分からない場合は、セッションを簡単に行うことができます。


2

セッション変数は、古いBasicグローバル変数にある程度似ています。ユーザーの負担は、それらの内容、その内容、範囲、およびそれらの使用方法を追跡することです。BASICの古いバージョンのように。そうは言っても、なぜプログラミングモデル(ASP、MVCなど)の不可欠かつ非常に重要な部分になるように設計されたメカニズムの使用を誰かが完全に割引かないのでしょうか?

セッション変数の使用で私が遭遇した唯一の悪い点は、それらを追跡し、それらに関連データが入力され、それらを破棄することを確認する負担をかけることです。

私たちが何らかの方法でプログラミングしているとき、私たちはそれをしませんか?


1

私は、セッション変数に関連するデバッグの問題を抱えていたいくつかの悪い経験のために、あなたの同僚のように考えていました。それは本当に私には無能でした。はい。クエリ変数、フォームの非表示フィールドなどを使用して、セッション変数を使用せずにある程度の範囲で取得できます。ただし、アプリケーションに状態を判断するための最も基本的なロジックフローを超えるものがある場合、この方法で行うのは非常に面倒です。また、クエリ文字列と非表示フィールドを介してアプリケーションの内部動作を表示することによるセキュリティ上のリスクもあります。これらはいずれも攻撃ベクトルとして機能します。

セッション変数を使用する場合、アプリケーションのロジックフローを決定するため、セッション変数が設定および設定解除されるタイミングを追跡する必要があります。Cのような言語でのメモリ管理のようなものです。

これは、フレームワークのない比較的小さなプロジェクトでPHPを使用した経験から得たものであり、他のプラットフォームでは状況が異なる可能性があることに注意してください。


2
制御フローに関係する状態にセッションを使用するときに、複数のタブセマンティクスを正しく取得するにはどうすればよいですか?セッションは、ログインやプロパティなどの設定ではうまく機能しますが、他のほとんどの用途には適切なセマンティクスがありません。
CodesInChaos

よくわかりませんが、私が投稿したのは、PHP / MySQLでデータベース駆動型Webアプリを構築した経験が明らかに制限されていることに基づいています。ブラウザの複数のタブは通常どのように処理されますか(それがあなたが参照しているものだと仮定しています)?
primehunter326

@ primehunter326ルートパラメータ、クエリ文字列、または非表示フォームフィールド。
ケーシー

0

前述のように、HTTPはステートレスであり、セッション変数はそれを破ります。ステートレスであるHTTP設計は、リソースのキャッシュに役立ちます。公開されているリソースの場合。

セッション変数なしでウェブサイトを設計することは可能ですが、より困難です。最も難しい(IMHO)は派手なログイン/ログアウトです。HTTP認証スキームは、HTMLフォームを介した認証に必要なツールを提供しません(javascriptで何かをハッキングする場合があります-XHR https:// untel:passowrd@mydomain.com)。ログアウトしてブラウザ間で互換性を保つのはさらに困難です。それについてw3メーリングリストで議論がありましたが、私が正しく覚えていれば、その考えは捨てられました。

残りについては、セッション変数なしで生きることができるはずです。データベース、ファイル、またはどこかに何らかの状態がありますが、セッション変数の使用はまれです。

ユーザーがショッピングカートを持っている場合、ユーザーがカートを共有せずに2台のコンピューター/ブラウザーで閲覧できる場合にのみ、可変セッションになります。

弊社のサイトを使用することにより、あなたは弊社のクッキーポリシーおよびプライバシーポリシーを読み、理解したものとみなされます。
Licensed under cc by-sa 3.0 with attribution required.