您的位置:首页 > 数据库 > Redis

.Net Redis实战——使用Redis构建Web应用

2021-01-23 21:05 453 查看

示例介绍

示例1:借助Redis实现购物车功能

示例2:Redis实现网页缓存和数据缓存

 

借助Redis实现购物车功能

每个用户的购物车都是一个散列,散列存储了商品ID与商品订购数量之间的映射。订购商品时,对购物车进行更新:如果用户订购某件商品的数量大于0,那么将这件商品的ID以及用户订购该商品的数量添加到散列里面,如果用户购买的商品已经存在散列里面,那么新的订购数量会覆盖已有的订购数量;相反,如果用户订购某件商品数量不大于0,那么程序将从散列里面移除该条目。

 

由于整个示例分Controller和WebApi两部分,在不考虑封装Redis操作的情况下提取Redis连接字符串到appSetting.json中

"ConnectionStrings": {
"Redis": "localhost,abortConnect=false"
},

 

保存用户购物查数据示例代码:

[HttpGet("UpdateCart")]
public string UpdateCart(string token,string item,int count)
{
var key = $"cart:{token}";
using (var redis = ConnectionMultiplexer.Connect(redisConnectionStr))
{
var db = redis.GetDatabase();
//更新购物车数据
if (count <= 0)
{
db.HashDeleteAsync(key, item);
}
else
{
db.HashSetAsync(key, item,count);
}
}

return
56c
"更新购物车成功";
}

 

Redis实现网页缓存和数据缓存

针对不会频繁更新得动态网页或Ajax返回的数据可以缓存在Redis中,减少与数据库的交互提升系统效应效率。

该示例只是为了演示借助Reids实现页面缓存和数据缓存效果,实际使用中可通过ResponseCache特性实现缓存。

详细介绍:https://docs.microsoft.com/en-us/aspnet/core/performance/caching/response?view=aspnetcore-5.0

 

网页数据缓存

新建示例项目时为WebApi项目,修改Startup类添加Web Mvc支持。

ConfigureServices方法中修改services.AddControllers()services.AddControllersWithViews()

Configure方法中app.UseEndpoints修改为如下代码

app.UseEndpoints(endpoints =>
{
endpoints.MapControllerRoute(
name: "default",
pattern: "{controller=Home}/{action=Index}/{id?}");
});

 

定义中间件类RedisCacheMiddleware,用来缓存网页页面

public class RedisCacheMiddleware
{

private readonly RequestDelegate _next;

public IConfiguration Configuration { get; }

public RedisCacheMiddleware(RequestDelegate next, IConfiguration configuration)
{
_next = next;
Configuration = configuration;
}

public async Task InvokeAsync(HttpContext context)
{

var path = context.Request.Path.Value.ToLower();

if (path == "/home" || path == "/home/index")
{

var responseContent = "";

//Copy a pointer to the original response body stream
var originalBody
1b14
Stream = context.Response.Body;

using (var redis = ConnectionMultiplexer.Connect(Configuration.GetConnectionString("Redis")))
{
var db = redis.GetDatabase();
if (db.KeyExists(path))
{
responseContent = db.StringGet(path);
await RespondWithIndexHtml(context.Response, responseContent);
return;
}
else
{
using (var responseBody = new MemoryStream())
{
//...and use that for the temporary response body
context.Response.Body = responseBody;

//Continue down the Middleware pipeline, eventually returning to this class
await _next(context);

//Format the response from the server
responseContent = await FormatResponse(context.Response);

//Copy the contents of the new memory stream (which contains the response) to the original stream, which is then returned to the client.
await responseBody.CopyToAsync(originalBodyStream);
}

db.StringSet(path, responseContent, expiry: TimeSpan.FromSeconds(30));
}
}

}

// Call the next delegate/middleware in the pipeline
await _next(context);
}

private async Task RespondWithIndexHtml(HttpResponse response,string html)
{
response.StatusCode = 200;
response.ContentType = "text/html";

await response.WriteAsync(html, Encoding.UTF8);
}

private async Task<string> FormatResponse(HttpResponse response)
{
//We need to read the response stream from the beginning...
response.Body.Seek(0, SeekOrigin.Begin);

//...and copy it into a string
string text = await new StreamReader(response.Body).ReadToEndAsync();

//We need to reset the reader for the response so that the client can read it.
response.Body.Seek(0, SeekOrigin.Begin);

//Return the string for the response
return text;
}

}

添加中间件调用

app.UseMiddleware<RedisCacheMiddleware>();

运行效果如图:

网页上的时间会每30秒更新一次。

.Net Core提供的响应缓存中间件:https://docs.microsoft.com/zh-cn/aspnet/core/performance/caching/middleware?view=aspnetcore-5.0

Ajax数据缓存

本例只是简单的数据存储,实际使用中可编写单独的服务,让这个服务将指定的数据缓存到Redis里面,并不定期地对这些缓存进行更新。

 示例代码

[HttpGet("GetDateTime")]
public string GetDateTime()
{
var dateTime = "";
var key = "data:datetime";
using (var redis = ConnectionMultiplexer.Connect(redisConnectionStr))
{
var db = redis.GetDatabase();
if (db.KeyExists(key))
{
dateTime = db.StringGet(key);
}
else
{
dateTime = DateTimeOffset.Now.ToString("yyyy-MM-dd HH:mm:ss");
db.StringSet(key, dateTime,expiry:TimeSpan.FromSeconds(5));
}
}

return dateTime;
}

 

参考资料

Using Middleware in .NET 5.0 to Log Requests and Responses

如何在 asp.net core 的中间件中返回具体的页面

Swashbuckle.AspNetCore.ReDoc/ReDocMiddleware.cs

内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: