如何使用 Owin 托管存储会话数据?

Posted

技术标签:

【中文标题】如何使用 Owin 托管存储会话数据?【英文标题】:How to store session data using Owin hosting? 【发布时间】:2015-08-27 04:14:14 【问题描述】:

我在使用 Owin 托管的应用程序中创建会话时遇到问题。我试过使用RedisSession,但我不知道如何配置它,所以它给了我一个错误。 我一直在寻找解决方案,尝试了不同的方法,最后决定在这里寻求帮助。

场景:

我正在使用 HTTP POST 请求登录应用程序, 用户登录名和密码应存储在会话中, 对于需要上一个登录会话的每个下一个 GET/POST 请求是 空(登录名和密码为空)。

对象HTTPContext 为空。

我正在使用 Ninject 进行依赖注入。

我尝试过类似的方法:Can OWIN middleware use the http session?

有人知道如何在 Owin 会话中存储登录数据吗?

下面是Owin配置文件,里面的东西来自上面贴的链接。

[assembly: OwinStartup(typeof(Service.Startup))]
namespace Service

public class Startup
    
        public void Configuration(IAppBuilder appBuilder)
        
            var config = new HttpConfiguration();
            config.Routes.MapHttpRoute("DefaultApi", "api/controller/action/id", new  id = RouteParameter.Optional 
                );
            appBuilder.RequireAspNetSession();
            appBuilder.UseNinjectMiddleware(CreateKernel).UseNinjectWebApi(config);

        

        public static StandardKernel CreateKernel()
        
            var kernel = new StandardKernel(new Module());
            return kernel;
        
    
    public static class AspNetSessionExtensions
    
        public static IAppBuilder RequireAspNetSession(this IAppBuilder app)
        
            app.Use((context, next) =>
            
                // Depending on the handler the request gets mapped to, session might not be enabled. Force it on.
                HttpContextBase httpContext = context.Get<HttpContextBase>(typeof(HttpContextBase).FullName);
                httpContext.SetSessionStateBehavior(SessionStateBehavior.Required);
                return next();
            );
            // SetSessionStateBehavior must be called before AcquireState
            app.UseStageMarker(PipelineStage.MapHandler);
            return app;
        
    

【问题讨论】:

我也有类似的问题,如果你已经解决了,请分享谢谢! 【参考方案1】:

我也遇到过一些问题。

这是对我有用的解决方案:

1) 添加 NuGet Microsoft.AspNetCore.Session

2) 在您的 IServiceCollection 上调用 .AddSession。请注意,它可能需要配置。 就我而言,它是:

3) 使用您的会话。请记住,如果没有为会话设置任何值,则每个请求的 SessionID 都是不同的。 因此,您必须为会话添加一些价值。这就是它在多个请求中保持不变的方式。

这是我的会话固定中间件:

希望对你有帮助。

【讨论】:

【参考方案2】:

对于任何想要使用 ASP.net Framework 而不是 Core 的人,请继续阅读。

首先,确保已安装Owin.Extensions

接下来,将此代码添加到您的 Owin Startup.cs之前您要使用会话的中间件。

app.Use((context, next) =>

    var httpContext = context.Get<HttpContextBase>(typeof(HttpContextBase).FullName);
    httpContext.SetSessionStateBehavior(SessionStateBehavior.Required);
    return next();
).UseStageMarker(PipelineStage.MapHandler);

默认情况下,OWIN 中间件在最后一个事件 (PipelineStage.PreHandlerExecute) 处运行,此时访问会话状态为时已晚。

.UseStageMarker 告诉 OWIN 在执行管道中的哪个位置执行传递给 .Use() 的函数。

要使用会话,您需要执行在会话由 ASP.net 运行时初始化之后运行的中间件。这个中间件必须在PostAquireState阶段运行,像这样:

.Use((context, next) =>
 
     HttpContext.Current.Session["mykey"] = "myvalue";

     return next();
).UseStageMarker(PipelineStage.PostAcquireState);

【讨论】:

以上是关于如何使用 Owin 托管存储会话数据?的主要内容,如果未能解决你的问题,请参考以下文章

如何知道 OWIN cookie 何时到期?

如何在 mvc 5 中知道 OWIN cookie/用户会话即将到期

支持 https 的 Owin 自托管控制台应用程序(无 Web api,无 SignalR)

在使用 Owin 自托管的 Web API 中获取远程主机 IP

2个托管服务器之间的共享会话

如何使用Owin和Web Api 2在SignalR上配置MessagePack?