第五节:管道中间件入门(Use、Run、Map)
一. 简介
1.中间件是一种装配到应用管道以处理请求和响应的组件,每个组件可以选择是否把请求传递到管道中的下一个组件、可在管道中的下一个组件的前后执行工作.请求管道中的每一个组件负责调用管道中的下一个组件(或者使管道短路).
经典的管道请求图:

2.当中间件短路的时候,它被称为“终端中间件”,因为它阻止中间件进一步处理请求。
3.顺序:向Startup.Configure方法中添加常用中间件组件,需要按照下面的顺序,从而保证安全性、性能、功能。
异常/错误处理→ HTTP 严格传输安全协议→HTTPS 重定向→静态文件服务器→Cookie 策略实施→身份验证→会话→MVC。
public void Configure(IApplicationBuilder app)
{
if (env.IsDevelopment())
{
app.UseDeveloperExceptionPage();
app.UseDatabaseErrorPage();
}
else
{
app.UseExceptionHandler("/Error");
app.UseHsts();
} // Use HTTPS Redirection Middleware to redirect HTTP requests to HTTPS.
app.UseHttpsRedirection(); // Return static files and end the pipeline.
app.UseStaticFiles(); // Use Cookie Policy Middleware to conform to EU General Data
// Protection Regulation (GDPR) regulations.
app.UseCookiePolicy(); // Authenticate before the user accesses secure resources.
app.UseAuthentication(); // If the app uses session state, call Session Middleware after Cookie
// Policy Middleware and before MVC Middleware.
app.UseSession(); // Add MVC to the request pipeline.
app.UseMvc();
}
4.中间件的三大核心方法,分别是:Use、Run、Map.
二. Use方法
1. 用途:Use可以将多个中间件连接在一起,实现在下一个中间件的前后执行操作,Use方法也可以使管道短路,即不调用next请求委托,此时和Run的作用一样。
2. 查看Use方法的源代码,参数为:Func<HttpContext, Func<Task>, Task> middleware,可以参考自己封装一个中间件, 如:MyMiddleware。
代码分享:
/// <summary>
/// 自定义一个中间件
/// </summary>
public class MyMiddleware
{
public Task DelegateMiddleware(HttpContext context, Func<Task> next)
{
context.Response.WriteAsync("MyOwinMiddle Start<br/>");
next.Invoke();
return context.Response.WriteAsync("MyOwinMiddle End<br/>");
}
}
public void Configure(IApplicationBuilder app, IHostingEnvironment env)
{
//1. Use用法
{
app.Use(async (context, next) =>
{
await context.Response.WriteAsync("First Start<br/>");
//调用下一个中间件
await next.Invoke();
await context.Response.WriteAsync("First End<br/>");
});
app.Use(async (context, next) =>
{
await context.Response.WriteAsync("Second Start<br/>");
//调用下一个中间件
await next.Invoke();
await context.Response.WriteAsync("Second End<br/>");
});
//调用封装后的中间件
MyMiddleware myMiddleware = new MyMiddleware();
app.Use(myMiddleware.DelegateMiddleware); //没有调用next,它在此处的作用是使管道短路
app.Use(async (context, next) =>
{
await context.Response.WriteAsync("Third Start<br/>");
await context.Response.WriteAsync("Third End<br/>");
}); }
}
运行结果及分析:执行到next.Invoke(),调用下一个中间件。

三. Run方法
1. Run是一种约定,在某些中间件的可公开的管道末尾运行Run[Middleware]方法,表示终止请求。
代码分享:
//2. Run用法
{
app.Run(async context =>
{
await context.Response.WriteAsync("First Start<br/>");
await context.Response.WriteAsync("First End<br/>");
});
//不能执行下面代码,因为第一个Run直接终止了管道
app.Run(async context =>
{
await context.Response.WriteAsync("Second Start<br/>");
await context.Response.WriteAsync("Second End<br/>");
});
}
运行结果:

四. Map和MapWhen方法
1. 当请求满足某种规则,执行某个中间件,下面分享Map和MapWhen的代码
代码分享:
//3. Map用法
{
//http://localhost:5000/map1 访问
app.Map("/map1", appBulider => appBulider.Run(async context =>
{
await context.Response.WriteAsync("This is Map1<br/>");
}));
//http://localhost:5000/map2 访问
app.Map("/map2", appBulider => appBulider.Run(async context =>
{
await context.Response.WriteAsync("This is Map2<br/>");
}));
//当没有map1和map2的时候,访问下面的中间件
app.Run(async context =>
{
await context.Response.WriteAsync("Hello from non-Map delegate. <p>");
});
} //4. MapWhen用法
{
//http://localhost:5000/?userName=ypf 访问
app.MapWhen(context => context.Request.Query.ContainsKey("userName"),
appBulider => appBulider.Run(async context =>
{
var value = context.Request.Query["userName"];
await context.Response.WriteAsync($"this value is {value}");
}));
//没有拼接的时候访问下面
app.Run(async context =>
{
await context.Response.WriteAsync("Hello from non-Map delegate. <p>");
});
}
运行结果分析:如上述代码中的描述。
!
- 作 者 : Yaopengfei(姚鹏飞)
- 博客地址 : http://www.cnblogs.com/yaopengfei/
- 声 明1 : 本人才疏学浅,用郭德纲的话说“我是一个小学生”,如有错误,欢迎讨论,请勿谩骂^_^。
- 声 明2 : 原创博客请在转载时保留原文链接或在文章开头加上本人博客地址,否则保留追究法律责任的权利。
第五节:管道中间件入门(Use、Run、Map)的更多相关文章
- Ext JS学习第十六天 事件机制event(一) DotNet进阶系列(持续更新) 第一节:.Net版基于WebSocket的聊天室样例 第十五节:深入理解async和await的作用及各种适用场景和用法 第十五节:深入理解async和await的作用及各种适用场景和用法 前端自动化准备和详细配置(NVM、NPM/CNPM、NodeJs、NRM、WebPack、Gulp/Grunt、G
code&monkey Ext JS学习第十六天 事件机制event(一) 此文用来记录学习笔记: 休息了好几天,从今天开始继续保持更新,鞭策自己学习 今天我们来说一说什么是事件,对于事件 ...
- ASP.NET Core 1.0中的管道-中间件模式
ASP.NET Core 1.0借鉴了Katana项目的管道设计(Pipeline).日志记录.用户认证.MVC等模块都以中间件(Middleware)的方式注册在管道中.显而易见这样的设计非常松耦合 ...
- Core 1.0中的管道-中间件模式
ASP.NET Core 1.0中的管道-中间件模式 SP.NET Core 1.0借鉴了Katana项目的管道设计(Pipeline).日志记录.用户认证.MVC等模块都以中间件(Middlewar ...
- 第四百零五节,centos7下搭建sentry错误日志服务器,接收python以及Django错误,
第四百零五节,centos7下搭建sentry错误日志服务器,接收python以及Django错误, 注意:版本,不然会报错 Docker >=1.11Compose >1.6.0 通过d ...
- DotNetCore学习-3.管道中间件
中间件是用于组成应用程序管道来处理请求和响应的组件.管道内的每个组件都可以选择是否将请求交给下一个组件,并在管道中调用下一个组件之前和之后执行一些操作. 请求委托被用来建立请求管道,并处理每一个HTT ...
- 第三百九十五节,Django+Xadmin打造上线标准的在线教育平台—Xadmin集成富文本框
第三百九十五节,Django+Xadmin打造上线标准的在线教育平台—Xadmin集成富文本框 首先安装DjangoUeditor3模块 Ueditor HTML编辑器是百度开源的HTML编辑器 下载 ...
- 第三百八十五节,Django+Xadmin打造上线标准的在线教育平台—登录功能实现,回填数据以及错误提示html
第三百八十五节,Django+Xadmin打造上线标准的在线教育平台—登录功能实现 1,配置登录路由 from django.conf.urls import url, include # 导入dja ...
- 第三百一十五节,Django框架,CSRF跨站请求伪造
第三百一十五节,Django框架,CSRF跨站请求伪造 全局CSRF 如果要启用防止CSRF跨站请求伪造,就需要在中间件开启CSRF #中间件 MIDDLEWARE = [ 'django.midd ...
- centos shell脚本编程1 正则 shell脚本结构 read命令 date命令的用法 shell中的逻辑判断 if 判断文件、目录属性 shell数组简单用法 $( ) 和${ } 和$(( )) 与 sh -n sh -x sh -v 第三十五节课
centos shell脚本编程1 正则 shell脚本结构 read命令 date命令的用法 shell中的逻辑判断 if 判断文件.目录属性 shell数组简单用法 $( ) 和$ ...
随机推荐
- ElasticSearch(九)e代驾使用Elasticsearch流程设计(Yii1版本)
一.控制器层的更新.添加.删除 class AddKnowledgeAction extends CAction { //add and update public function actionPo ...
- kindedit,uedit 上传跨域返回
1.kindedit 跨域上传图片的时候,a.com 上传到b.com接收图片服务器,然后返回图片地址. 2.一般如果不做任何处理是获取不到返回的信息的.原因是跨域了 3.所以一般在上传成功后,在跳转 ...
- Myapp
一.github地址:https://github.com/jianghailing/rjgcsecondwork 二.PSP表格: PSP2.1 Personal Software Process ...
- SQLServer2017自动备份数据库
本文截图来源: 地址一:https://blog.csdn.net/u010944388/article/details/86674078 地址二:https://www.cnblogs.com/ja ...
- 修改GIT已提交的用户名和邮箱
修改GIT已提交的用户名和邮箱 原文:https://help.github.com/en/github/using-git/changing-author-info 说明 要更改在现有提交中记录的名 ...
- php对接app支付宝支付出错Cannot redeclare Decrypt()
报错原因: alipaySDK中定义的Encrypt()/Decrypt()函数与Laravel中定义的Encrypt()/Decrypt()函数重名了. 解决办法: 修改alipaySDK中定义的函 ...
- Python实现感知器的逻辑电路(与门、与非门、或门、异或门)
在神经网络入门回顾(感知器.多层感知器)中整理了关于感知器和多层感知器的理论,这里实现关于与门.与非门.或门.异或门的代码,以便对感知器有更好的感觉. 此外,我们使用 pytest 框架进行测试. p ...
- websocket 的基本用法
项目当中使用到了websocket,以前的项目当中使用到了另外一个类似的socket.io,两者的区别和联系在另外一篇文章当中有提及,这里就简单的写下websocket的用法 下面的例子是阮一峰的We ...
- 通过开启子进程的方式实现套接字服务端可以并发的处理多个链接以及通讯循环(用到了subprocess模块,解决粘包问题)
今日作业:通过开启子进程的方式实现套接字服务端可以并发的处理多个链接以及通讯循环(用到了subprocess模块,解决粘包问题) server(服务端) import socket from mult ...
- python中列表(list)函数及使用
序列是Python中最基本的数据结构.序列中的每个元素都分配一个数字 - 它的位置,或索引,第一个索引是0,第二个索引是1,依此类推. Python有6个序列的内置类型,但最常见的是列表和元组. 序列 ...