在HttpRequest管道中访问会话

Dan*_*vay 13 sitecore

我正在尝试访问查询字符串参数并将其保存到Session变量.由于我正在处理的解决方案有几个基本布局,最简单的方法是将其添加到管道处理程序.但是,我的代码失败了,因为args.Context.Session为null:

public class SaveQueryStringToSession : HttpRequestProcessor
{
    public override void Process(HttpRequestArgs args)
    {
        Assert.ArgumentNotNull((object)args, "args");
        string queryString = WebUtil.GetQueryString("parm1");
        if (queryString.Length <= 0)
            return;
        args.Context.Session["parm1"] = queryString;
    }
}
Run Code Online (Sandbox Code Playgroud)

将此方法插入HttpRequestBegin或HttpRequestEnd管道时会发生这种情况.很想知道为什么,以及在这里使用标准的变通方法或模式.(是的,我会添加一个空检查.不需要指出它.)

我在IIS 7.5(集成.Net 2.0)上运行Sitecore Sitecore.NET 6.4.1(rev.110720)

可能相关的链接:

Dan*_*vay 21

HttpRequestBegin管道连接到HttpApplication.BeginRequest事件,并且在实例化HttpSession对象之前触发此事件.使用HttpRequestEnd管道不起作用,因为在HttpApplication.EndRequest事件被触发时已经处理了HttpSession对象.

触发PostAcquireRequestState事件后会话变为可用.要拦截它,请创建一个实现IHttpModule的类,并将其添加到Web.config中的<httpModules>元素中.HttpModule代码需要检查请求是否需要会话状态,因为尝试读取静态资源请求的会话将引发异常.

这是访问Session和QueryString的HttpModule代码:

public class MyHttpModule :IHttpModule
{
   public void Init(HttpApplication context)
   {
       context.PostAcquireRequestState += RequestHandler;
   }

   public void Dispose()
   {
        //
   }

   public void RequestHandler(object sender, EventArgs e)
   {
       var app = (HttpApplication) sender;

       if (app.Context.Handler is IRequiresSessionState)
       {
           var session = app.Session;
           var queryString = app.Request.QueryString["test"];
           session["test"] = queryString;
       }
   }
}
Run Code Online (Sandbox Code Playgroud)

值得注意的是,Sitecore的HttpRequestBegin和HttpRequestEnd管道通过HttpModule连接到ASP.NET:

<add type="Sitecore.Nexus.Web.HttpModule,Sitecore.Nexus" 
name="SitecoreHttpModule" />
Run Code Online (Sandbox Code Playgroud)

由于@ddysart指着我在正确的方向,和这个答案侦听正确的事件.


小智 5

实际上,您可以使用 httpRequestProcessed 而不是 httpRequestBegin 或 HttpRequestEnd,在此期间,站点核心处理 HttpRequest 以便您可以访问会话。

您将能够使用之前提供的相同代码。

public class SaveQueryStringToSession : HttpRequestProcessor
{
   public override void Process(HttpRequestArgs args)
   {
        Assert.ArgumentNotNull((object)args, "args");
        string queryString = WebUtil.GetQueryString("parm1");
        if (queryString.Length <= 0)
            return;
        args.Context.Session["parm1"] = queryString;
    }
}
Run Code Online (Sandbox Code Playgroud)