ASP.NET の EnableSessionState の指定は無視できる?!
ASP.NET では Session を利用不可にすることが可能です。それは Page の EnableSessionState ディレクティブを False にすればよいのです。(その他、Config ファイル等でも指定可能です)
具体的には次のようにします。
<%@ Page Language="C#" CodeFile="~/useSessionState.aspx.cs" Inherits="MyTest.useSessionState" EnableSessionState="False" %> <html> <body> <p style="font-size:large;"> <% Session["test"] = "Hello"; Response.Write( Session["test"] ); %> </p> </body> </html>
コードファイルは次のとおりです。
using System; using System.Web.SessionState; namespace MyTest { public partial class useSessionState : System.Web.UI.Page { } }
このコードでは EnableSessionState を False に指定しているにもかかわらず、 Session にアクセスしているので、これを実行すると次のようなエラーが発生します。
これは、まぁ、当たり前といえば当たり前ですね。
ちなみに、このときに ASP.NET の内部で生成される一時ファイルを見てみましょう。
namespace MyTest { public partial class useSessionState { protected System.Web.Profile.DefaultProfile Profile { get { return ((System.Web.Profile.DefaultProfile)( this.Context.Profile)); } } protected System.Web.HttpApplication ApplicationInstance { get { return ((System.Web.HttpApplication)( this.Context.ApplicationInstance)); } } } }
この中では IRequiresSessionState インターフェイスのマークがなくなっています。 もともとどうなっていたかよくわからない人は、 「なぜコードビハインドクラスは partial なのか?」の getType2 クラスの定義を見直してください。
逆に言えば、EnableSessionState を True にしたときと、False にしたときの違いは、 IRequiresSessionState が含まれているか否かというところしか変わりません。
試しに、EnableSessionState を False にしたまま、コードビハインドファイルにて、次のように IRequiresSessionState を追加してみましょう。
using System; using System.Web.SessionState; namespace MyTest { public partial class useSessionState : System.Web.UI.Page, IRequiresSessionState { } }
すると、次のように問題なく実行されてしまいます。
EnableSessionState を False にしているのに、Session が使えてしまう、というところだけ考えるとバグみたいな感じですけどね...
コンパイル時に検出したほうが良いと思う
それ以上に、「Session を使わない」 と宣言しているのに Session を使っている箇所がある、ということについては、 コンパイル時に検出して欲しいですよね。
上で見たエラー時のコールスタックは以下のようになります。
[HttpException (0x80004005): Session state can only be used when
enableSessionState is set to true, either in a configuration file
or in the Page directive. Please also make sure that
System.Web.SessionStateModule or a custom session state module
is included in the <configuration>\<system.web>\<httpModules>
section in the application configuration.]
System.Web.UI.Page.get_Session() +26...
ASP.usesessionstate_aspx.__Render__control1(...)
in c:\test\useSessionState.aspx:11
System.Web.UI.Control.RenderChildrenInternal(...) +256
System.Web.UI.Control.RenderChildren(HtmlTextWriter writer) +19
System.Web.UI.Page.Render(HtmlTextWriter writer) +29
System.Web.UI.Control.RenderControlInternal(...) +27
System.Web.UI.Control.RenderControl(...) +99
System.Web.UI.Control.RenderControl(HtmlTextWriter writer) +25
System.Web.UI.Page.ProcessRequestMain(...) +1266
get_Session で SessionState を取得するコードが実行されてはじめて、IRequiresSessionState インターフェイスがマークされているかどうかチェックされ例外を投げています。 逆に言えば、コンパイルは完了して get_Session が呼び出されるまで、設定情報とコードに矛盾があることに気がつかないわけです。
できることなら、Session を無効にした段階でコンパイルができなくなり、 コードの修正箇所が見えてきたら便利なのになぁ・・・と思ったのでした。