ASP.NET Core 6框架揭秘实例演示[35]:利用Session保留语境

2022-09-06 00:00:00 会话 请求 状态 形式 采用

客户端和服务器基于HTTP的消息交换就好比两个完全没有记忆能力的人在交流,每次单一的HTTP事务体现为一次“一问一答”的对话。单一的对话毫无意义,在在同一语境下针对某个主题进行的多次对话才会有结果。会话的目的就是在同一个客户端和服务器之间建立两者交谈的语境或者上下文,ASP.NET Core利用一个名为SessionMiddleware的中间件实现了会话。本篇提供了几个简单的实例来演示如何在一个ASP.NET Core应用中利用会话来存储用户的状态。(本文提供的示例演示已经同步到《ASP.NET Core 6框架揭秘-实例演示版》)。

[S2301]设置和提取会话状态(源代码)
[S2302]查看存储的会话状态(源代码)
[S2303] 查看Cookie(源代码)

[S2301]设置和提取会话状态

每个会话都有一个被称为Session Key的标识(但不是标识),会话状态以一个数据字典的形式将Session Key保存在服务端。当SessionMiddleware中间件在处理会话的个请求时,它会创建一个Session Key,并据此创建一个独立的数据字典来存储会话状态。这个Session Key终以Cookie的形式写入响应并返回客户端,客户端在每次发送请求时会自动附加这个Cookie,那么应用程序能够准确识别会话并成功定位存储会话状态的数据字典。下面我们利用一个简单的实例来演示会话状态的读写。ASP.NET应用在默认情况下会利用分布式缓存来存储会话状态。我们采用基于Redis数据库的分布式缓存,所以需要添加针对NuGet包“Microsoft.Extensions.Caching.Redis”的依赖。下面的演示程序调用了AddDistributedRedisCache扩展方法添加了基于DistributedRedisCache的服务注册,SessionMiddleware中间件则通过调用UseSession扩展方法进行注册。

using System.Text;

var builder = WebApplication.CreateBuilder();
builder.Services
    .AddDistributedRedisCache(options => options.Configuration = "localhost")
    .AddSession();
var app = builder.Build();
app.UseSession();
app.MapGet("/{foobar?}", ProcessAsync);
app.Run();

static async ValueTask<IResult> ProcessAsync(HttpContext context)
{
    var session = context.Session;
    await session.LoadAsync();
    string sessionStartTime;
    if (session.TryGetValue("__SessionStartTime", out var value))
    {
        sessionStartTime = Encoding.UTF8.GetString(value);
    }
    else
    {
        sessionStartTime = DateTime.Now.ToString();
        session.SetString("__SessionStartTime", sessionStartTime);
    }

    var html = $@"
<html>
    <head><title>Session Demo</title></head>
    <body>
        <ul>
            <li>Session ID:{session.Id}</li>
            <li>Session Start Time:{sessionStartTime}</li>
            <li>Current Time:{DateTime.Now}</li>
        <ul>
    </body>
</html>";
    return Results.Content(html, "text/html");
}

相关文章