none
ファイルダウンロード処理後にアプリを使い続けると、Session変数が消えてしまう RRS feed

  • 質問

  • asp.net 2.0 & visualstudio2005でWEBアプリを開発しています。

    このWEBアプリは、ユーザが選んだデータをExcelファイルに書き込み、画面上でダウンロードボタンをクリックした時点でそれをダウンロードするものです。

    問題はダウンロードした後で、同じ画面から戻る(自作の)ボタンをクリックしてメニュー画面にもどります。その後別の機能を使用するために各機能毎に設定しているボタンをクリックすると、メニュー画面自身のPage_Loadイベント時が発生し、その時点でセッション変数に格納していたユーザIDが失われてしまっています。

    この時Global.asaxでSesson_Endイベントが拾われているようですが、これはなぜなのでしょうか?

    ダウンロードはResponse.End()をし、その後Server.Transfer()でページを遷移していますが、デバッガで追っていくと、メニュー画面に戻る直前、戻るボタンで戻った直後のメニュー画面のロード時にはセッション変数は保持されていました。別機能へのボタンクリック時も、server.Transfer()で遷移していますが、Response.Redirect()もだめで、server.Transfer()で第2引数にfalseを入れたら画面が変になりした。

    (ダウンロード処理後、無理やりログアウトさせようにも、別のページに線にさせられないし、強制的にログアウトもさせられませんよね。同じページにそのボタンを作ってユーザにえらばせるのも安全ではないですし。)

     

    2007年4月2日 7:55

すべての返信

  • > この時Global.asaxでSesson_Endイベントが拾われているようですが、これはなぜなのでしょうか?

     Session.Abandon なんていう記述がどこかにありませんか?

     

    2007年4月2日 8:03
  • これは確認しました。ありません。

    メニュー画面に戻る時のページロード時には、セッション変数が保持されていることを確認済みです。

    また、別の機能を使おうとしてメニュー画面上のボタンをクリックした時のメニューページのロードイベント

    でも、セッション変数が保持されていることも確認しています。

    2007年4月2日 8:12
  • メニューページの Page_Load 時に Session に格納したページフラグ変数をチェックして、初回のアクセスなら初期化、どこかのページから飛んできた場合は初期化しなければいいだけではないでしょうか。
    2007年4月2日 10:00
  • レスありがとうございます。

    今まで書いていませんでしたが、メニューページの前にログインページがあり、そこでSession変数を格納していることもあり、

    フラグを立ててチェックというのは今回の場合難しいです。 今回の投稿をほそくしますと、

    今回「Session変数が消えてしまう」というタイトルにしたのは、まずはSession変数は何が原因で消失しているかを知りたかった

    為です。それはなぜかというと、アプリ上で必要な情報を持つSession変数が無いのでエラーとしている為、その後アプリを使えなくなるからです。

    また、今回のこの現象は、このアプリの持つ機能のうち、ファイルのダウンロード処理のみで起こるようです。

    最悪でもSession変数がなぜ消失するかがわからなくても、ファイルダウンロード処理後、エラーが出なくなればよいのですが、手が浮かびません。普通ダウンロード処理は、別のプロセスでも生成してやっているのでしょうか?私はResponse.End()等しか知りませんが、これだとダウンロード処理後(ユーザがファイルを保存した後)は、遷移もできませんよね?

     

    2007年4月2日 10:32
  • ファイルダウンロードを別ウィンドウにしてみたら?

    っていうか、一言言わせてもらうと、設計ミスだと思うけどね。

    2007年4月2日 11:21
  • 回答ありがとうございます。

     

    別ウィンドウにする、というのは、別のセッションを生成するという意味ですか?

    おがわさんはどう書くのでしょうか?

    2007年4月2日 11:28
  • マイクロソフトのダウンロードサイトを参考にすれば?
    Button の Click で JavaScript で新しい Window を開いて、その時に値を POST か GET で渡してあげて、ダウンロードさせる。
    別セッションを生成なんてしませんよ。
    2007年4月2日 12:02
  • ありがとうございます。

    ダウンロードサイトのソースは、どこがポイントなのか私には良く分かりませんが、がんばってみます。

    JavaScriptは使ったことが無いに等しいのでどうなるのか分かりませんが、

    参考になりそうなソースをみながら勉強します。

     

    2007年4月2日 14:22
  •  idaten さんからの引用

    この時Global.asaxでSesson_Endイベントが拾われているようですが、これはなぜなのでしょうか?

    ヘルプを見れば分かりますが、sessionstate の mode が インプロセス(or カスタム)の場合のみ発生するイベントですよね。インプロセスであるとしたら、アプリケーションのリスタートが発生してしまって、インプロセスで格納されてるセッション変数が失われてるんじゃないですかねぇ。

     

    パフォーマンスカウンタかなんかでリスタートしちゃってないか確認してはどうでしょうか。modeをSQLサーバやステートサーバにするとこの現象が回避されたりしない?

    2007年4月3日 1:25
  • レスありがとうございます。

    パフォーマンスカウンタは実装していません。「リスタート」にあたりそうなのは、ファイルのダウンロード処理でResponse.End()

    しているところくらいです。ただ、同画面上の「メニューに戻る」ボタンをクリックした後デバッグすると、server.transfer()でメニュー画面に戻る

    直前まではSession変数を維持していてました。

    2007年4月3日 8:59
  •  idaten さんからの引用

    パフォーマンスカウンタは実装していません。

    すみません。カスタムのパフォーマンスカウンタのことではないです。私が伝えたかったのは、パフォーマンスモニタ(管理ツール内のパフォーマンス)でASP.NETの Application Restarts や Worker Process Restarts を見てあげればリスタートが発生してないか確認できますよね、ということです。

     

    リソースを喰いすぎてWebアプリが再起動されてんじゃないか、ワーカープロセスがリサイクルされてるんじゃないか(←前レスではこれらを「リスタート」と表現しました)と予想してます。インプロセスでやるなら、これらがいつ発生してもいいように設計しないと。

     

    #Webアプリの再起動の条件って、web.configの更新・bin内の更新の他はなんだっけ・・・

     

    外してたらごめんなさいね。

    2007年4月3日 9:51
  • >#Webアプリの再起動の条件って、web.configの更新・bin内の更新の他はなんだっけ・・・

    フォルダの作成とかもです。

     

    ほかにIIS6以上だと、Application Poolの設定に依りますが、メモリ逼迫度、リクエスト回数、生存時間などがあります。

    2007年4月3日 14:22
  • そうでしたか。

    アプリケーションモニタもみてみます。ただ、今回の現象は開発機でいちいちアプリを上げ下げしているのでリソースはそんなに喰っていないのではないかと思います。Session変数は1個につき多くても20文字くらいの文字列で、全機能で十数個くらい使っています。

    タイミング的には、Excelファイルの作成&ダウンロード機能、アップロード機能を実装したところで出たので、やっぱり

    Response.End()したから位しか思いつかず、そのくせSession変数はメニューに戻る直前まで保持されているという、よくわからない状態です。

    2007年4月3日 17:43
  • デバッグ大変そうですね。

    ASP.NETに備わっている「トレース機能」をご存知でしょうか。

    リクエストごとのセッション状態などが簡単に把握できます。

    問題となる事象の絞込みに活用できると思います。

    おそらくブレイクポイントを設定して値などを確認するより作業が楽になるはずです。

     

    http://msdn.microsoft.com/library/ja/default.asp?url=/library/ja/jpdnaspnet/htm/asp01252001.asp

     

    参考にしてください。

    2007年4月6日 0:34