スレッド表示 | フラット表示〕 全トピック 920 件中 268 番目 次≫ ≪前

セッションのセキュリティー

created: 2006-02-24 11:57 | modified: 2006-02-28 13:02 | reply: 9

[2957] セッションのセキュリティー

user: 江戸川 | created: 2006-02-24 11:57
毎度お世話になります。
お陰さまで、なんとなくショッピングカートの作成までたどり着いてしまいましたが、ここでまた疑問が出てきてしまいました。

仕組みとしては、先ずSSL内の?ログイン画面でユーザIDとパスワードによる認証を行い、OKならセッション変数(IDとPASS)をセットします。
次に、SSL外の?店舗のページへ行き、気に入った商品の購入ボタンを押します。
すると同じくSSL外の?ショッピングカートのページに飛んで、今選択した商品の情報をセッション変数にセットする、と言う流れです。

しかし、?でログインしていても、?でログインチェックをするとログインされていないと判定されるのです。
これは多分、SSL内と外でURLが違うからだと思うのですが、こういう問題を回避するにはどうしたら良いのでしょうか?

あるいは、セキュリティーの観点からは、そもそも?ショッピングカートはSSL内に無ければならないのでしょうか?
と言うのも、お客さんが選択した商品情報もセッション変数に代入するようにしているので(つまりクライアントのクッキーに保存される)ショッピングカートを見る度に、サーバーはそのクッキーをチェックしていますよね?そうすると、その交信を傍受されるとセッションを盗まれる事になりませんか?

まあ、実際にはそこまで気にする必要は無いのかも知れませんが、私としては選択した商品の情報が漏れるくらいは構いませんが、パスワードが漏れるとまずいです。

的外れな質問ではない事を祈りつつ、ご意見よろしくお願い致します。
reply: 2959 返信 編集 削除

[2959] http <--> https のセッション引継ぎ

user: ゆうじ | created: 2006-02-24 21:50
こんばんわ。まいどどうも。

話の順番が前後しますが先ずこれから。

・・・(つまりクライアントのクッキーに保存される)・・・

セッションに代入した値は、
サーバ内に保存されてますのでこれは違うかと。
クッキーに保存されるのは、セッションIDだけです。
クッキーから得たセッションIDを元に
セッションに代入した値の復帰が行われます。


その交信を傍受されるとセッションを盗まれる事になりませんか?

傍受されてセッションIDが盗まれることはあります。
私もお客さんが選択した商品情報をセッションに代入しますが、
個人を特定するような情報ではないので
傍受されてもかまわないと考えてます。
その観点から (1)でパスワードを保存するのはいのはいかがなものかと。

あるいは、セキュリティーの観点からは、そもそも(3)ショッピングカートはSSL内に無ければならないのでしょうか?

必須ではありませんが状況によります。
ID、パスワード、名前、住所、電話番号、など、
個人情報の送受信の際は必要と考えます。

フォームの値にしろ、セッションIDにしろ、
『傍受されて困る情報はSSL通信にする』と考えるといかがでしょう。
そして、『セッションに代入する値も選ぶ必要がある』と
念頭に置いてプログラミングすれば一応セキュリティは保たれるでしょう。



しかし、(1)でログインしていても、(3)でログインチェックをするとログインされていないと判定されるのです。
これは多分、SSL内と外でURLが違うからだと思うのですが、こういう問題を回避するにはどうしたら良いのでしょうか?

その通り、クッキーはURLが違うと別サーバと判断しますので
URLが違う場合はセッションも引き継がれません。

セッションIDの引継ぎは、
クッキー以外にも、GET・POST で渡すことができます。
http://jp.php.net/manual/ja/function.session-start.php

https と http が同じサーバなら、
下のように session_start 前に一工夫すれば、
同じセッションが復帰されるはずです。

もちろん、http <--> https 間の移動前に、
フォームなりアンカーなりにセッションIDを埋めておくのは必須です。

試してませんが参考になれば。
<?php
function sessStart()
{
if (!session_id()) {
$sess_name = session_name();
if (isset($_POST[$sess_name])) {
session_id($_POST[$sess_name]);
} elseif (isset($_GET[$sess_name]))) {
session_id($_GET[$sess_name]);
}
}
session_start();
}
?>
Parent: 2957  reply: 2964 返信 編集 削除

[2964] 毎度ありがとうございます

user: 江戸川 | created: 2006-02-27 00:26
いつもお世話になります。お返事が遅れて申し訳ありません。(なんかビジネスライクな文になってきましたが)

お蔭様で私の誤解が解けて、大分すっきりしてきました。クライアントのクッキーに保存されるのは、セッションIDだけなんですね。

今までは、SSL内のログインページでIDとPASSで認証した後、$_SESSION["ID"]と$_SESSION["PASS"]なんかをセットしていましたが(これでクライアントを判別しようという誤解のため)これは無意味だし危険なんですね。
IDとPASSが照合できて始めてセッションを確立する訳だから、言い換えればセッションを確立できたことがそのユーザが認証された証だと。

逆に$_SESSION["ID"](これはセッションIDじゃない!)や$_SESSION["PASS"]なんかのセッション変数は傍受される可能性があるので、個人を特定出来るような情報はセットしないか又はSSL内でやるって事ですね。

ただ、(本物の)セッションIDもSSL外で交信してると(認証後のショッピングページなどで)途中で傍受される事はあるんですよね?

あと、違うURLでセッションをGETやPOSTで引き渡す方法は後でやってみます。ありがとうございました。
Parent: 2959  reply: 2965 返信 編集 削除

[2965] ベターなセキュリティポリシー

user: ゆうじ | created: 2006-02-27 03:12
> IDとPASSが照合できて始めてセッションを確立する訳だから、言い換えればセッションを確立できたことがそのユーザが認証された証だと。

そのようなシステムにされているわけですね。
「セッションの確立 == ユーザ認証済」という設計だと
認証済にかかわらずセッションを使いたい時に
認証方法を見直す必要が出てきますよ。

私がショッピングカートのような
ユーザ固有のサービスを提供する場合は、
常にセッションが確立された状態にしておきます。
全てのリクエストで session_start をかけてるわけです。

認証処理で、
認証されれば $_SESSION['user_id'] にユーザIDを代入、
認証されなければ $_SESSION['user_id'] = null とします。
ログアウト時も、$_SESSION['user_id'] = null です。

$_SESSION['user_id'] が null ならば未認証時の処理を行い、
値があれば認証済と判断し $_SESSION['user_id'] をキーに
ユーザー固有のサービス提供といった感じです。
参考になれば。


> ただ、(本物の)セッションIDもSSL外で交信してると(認証後のショッピングページなどで)途中で傍受される事はあるんですよね?

おっしゃる通り。
SSL通信外だと読み取れらる可能性が高くなります。

なので、セッションにパスワードを代入するのは危険かと。

ユーザIDは、認証後もユーザを特定するため
必要なのでセッションに代入したとしても、
両方必要なのは認証処理の時だけでしょう。

セッションIDが傍受され読み取られた場合、
ユーザIDだけが漏れるのと、
ユーザIDとパスワードの両方が漏れるのとでは、
大きな違いがあります。
Parent: 2964  reply: 2966 返信 編集 削除

[2966] 普通のセキュリティーポリシー

user: 江戸川 | created: 2006-02-27 11:31
すみません。私の書き方が誤解を生じさせてしまったようなので。整理して書きます。

【今まで】
1)会員情報ページ(会員登録・ログインページ・会員情報参照/変更):SSL内。全てsession_startで開始。
※$_SESSION['user_id']と$_SESSION['user_pass']をセットし、重要ページでそれらをデータベースと照合。
2)ショッピングサイト:SSL外。session_start無し。
3)ショッピングカート:SSL内。全てsession_startで開始。セッション変数に選択した商品情報をセット。
と言うことは、2)と3)でSSL内外を行き来する必要あり煩雑。

【これから】
1)の※以降を削除。
3)で商品をショッピングカートに入れる所まではSSL外。その先、購入商品確定後のレジはSSL内にしたい。

と言うことです。それで、今気がかりなのは、3)をSSL外に移してしまった場合、セッション変数にセットされた商品情報は盗聴されても良いとして、セッションIDを傍受され、セッションそのものを乗っ取られると非常にマズイと言うことです。
それなら、session_startしなきゃ良いって話ですかね?($_SESSION['user_id']にセットしてユーザを特定しておく)でもそれだと、セッション変数そのものを参照できなくなりますよね。
Parent: 2965  reply: 2967 返信 編集 削除

[2967] 自己回答

user: 江戸川 | created: 2006-02-27 16:24
思いつきですが、ショッピング中(レジに入る前のカートに入れてる段階)の商品情報はセッションを使わずに、クッキーに直接セットしてしまえば良いのかな?
それで、レジに来て(SSL内)初めてsession_startさせて決済手続きを進めると。
そうすれば、SSL内外でセッションIDの受け渡しを行う必要もなくなりますし。
Parent: 2966  reply: 2968 返信 編集 削除

[2968] Re.自己回答

user: ゆうじ | created: 2006-02-27 21:16
この手は思いつきませんでしたね。
SSL内だけにセッションの使用限定すれば
これも有効な防衛策ですね。
私も参考になりました。
Parent: 2967  reply: 2969 2971 返信 編集 削除

[2969] Re.Re.自己回答

user: ach | created: 2006-02-27 22:03
古いですがこんな記事がありました。
クッキーの話:
http://www.itmedia.co.jp/enterprise/0308/08/epn14.html
セッションハイジャック:
http://ns1.php.gr.jp/pipermail/php-users/2003-August/017782.html

えーっと。まあ参考までに
Parent: 2968  reply: 2970 返信 編集 削除

[2970] Re3.自己回答(クッキーの話)

user: 江戸川 | created: 2006-02-28 11:57
achさん。参考リンクありがとうございます。

最初の記事に関してですが、前にも書きましたが、SSL外でクッキーを設定すると言うことは、その情報は傍受されても仕方ないと言う前提です。

例えば、何処の誰とも判らないaaa123と言うユーザがある商品をカートに入れた、と言う情報が漏れたとしても、別段誰も困らないと思うのですが、違うんですかね?その店の大体の売上がばれてしまうとか?
もっとも、客にユーザ登録をしてもらう時には、個人を特定できるようなユーザIDにしないでくださいと断っておく必要があるかも知れませんが。

例えば楽天はショップ(商品検索)は非SSLで、カートに入れるところも非SSL。で、買い物が確定して注文画面に進むところからSSL内となります。
と言うことは上記と同じ状況であって、もしそれがダメだとしたら、もうサイト全体をSSL通信にしちゃえみたいな話ですよね。

あと、session_regenerate_id()は便利かなと思いましたが、どうもうちが使ってるレンタルサーバではその設定が出来ないように見えます。(只今確認中)
Parent: 2969  返信 編集 削除

[2971] 捨てクッキー

user: 江戸川 | created: 2006-02-28 13:02
参考になったと言っていただき、大変恐縮でございます。(^^;
こんなので良いのかどうか判りませんが、自分で試してみます。
Parent: 2968  返信 編集 削除
スレッド表示 | フラット表示〕 全トピック 920 件中 268 番目 次≫ ≪前
ページの一番上へ
Googleグックマークに登録 Yahooグックマークに登録 livedoorクリップに登録 @niftyクリップに登録 はてなブックマークに登録 deliciousに登録 Buzzurlに登録 FC2ブックマークに登録
最近更新された掲示板トピックス
管理人Blog
Yahoo Search

最近更新したNote
PHPマニュアル
今日のブックマーク
PHPマニュアル関数検索
関数名を入力し検索ボタンをクリック↑