01-001 HttpAbstractions 01 IApplicationBuilder
Posted on 2015-03-04 14:43 DotNet1010 阅读(278) 评论(0) 收藏 举报
本文基于 beta5 版本 github 源码链接:https://github.com/aspnet/Home/releases
asp.net5 中有个重要的 Delegate:
public delegate Task RequestDelegate(HttpContext context);
输入参数为:HttpContext 返回 Task ;
凡是需要处理HttpContext的事情(可以称作中间件:Middleware) 都可以抽象为 RequestDelegate;
比如:
1.根据请求路径访问目录的默认文件(如index.html default.htm 等),: DefaultFilesMiddleware
2.浏览文件夹中的文件 (列出文件夹中的目录和文件) :DirectoryBrowserMiddleware
3.发送(下载)静态文件:SendFileMiddleware 主要是设置文件写到流中的Feature
4.根据请求处理静态文件:StaticFileMiddleware 如:部分请求; 缓存未失效 返回304状态;只是Head请求 返回状态码 等;
5. 增加Session支持功能:SessionMiddleware
6. 增加错误处理功能:ErrorHandlerMiddleware
7. 表单验证功能:CookieAuthenticationMiddleware
8. 路由功能 :RouteMiddleware
9.跨域访问功能:CorsMiddleware
等等 这些中间件中都有个方法:
public Task Invoke(HttpContext context){}
使用这个Delegate 的一个接口是: IApplicationBuilder
在asp.net5 中 IApplicationBuilder 是一个很重要的接口
操作HttpContext的所有的中间件都要通过 Use 方法来登记使用:
此接口 有6个成员 三个属性 Server ApplicationServices Properties 三个方法 New Use Build. 源码如下:
public interface IApplicationBuilder
{
IServiceProvider ApplicationServices { get; set; }
object Server { get; }
IDictionary<string, object> Properties { get; }
IApplicationBuilder Use(Func<RequestDelegate, RequestDelegate> middleware);
IApplicationBuilder New();
RequestDelegate Build();
}
对应的默认实现类是:
public class ApplicationBuilder : IApplicationBuilder{}
IServiceProvider 这个接口 有一个成员: object GetService(Type serviceType);
这个成员来自系统创建时候赋值:
public ApplicationBuilder(IServiceProvider serviceProvider)
{
Properties = new Dictionary<string, object>();
ApplicationServices = serviceProvider;
}
New 方法 新创建一个IApplicationBuilder. 在ApplicationBuilder中实现如下:
public IApplicationBuilder New()
{
return new ApplicationBuilder(this);
}
private ApplicationBuilder(ApplicationBuilder builder)
{
Properties = builder.Properties;
}
Use 方法实现如下:
private readonly IList<Func<RequestDelegate, RequestDelegate>> _components = new List<Func<RequestDelegate, RequestDelegate>>();
public IApplicationBuilder Use(Func<RequestDelegate, RequestDelegate> middleware)
{
_components.Add(middleware);
return this;
}
Func<RequestDelegate, RequestDelegate> 举个例子: Use(nextRequestDelegate=> return currentRequestDelegate);
最后看一下Build 方法的实现:
public RequestDelegate Build()
{
RequestDelegate app = context =>
{
context.Response.StatusCode = 404;
return Task.FromResult(0);
};
foreach (var component in _components.Reverse())
{
app = component(app);
}
return app;
}
component :Func<RequestDelegate, RequestDelegate>
如果没有添加任何的 middleware (component)系统默认返回 404 状态。
如果添加了一个,比如:DefaultFilesMiddleware
即是调用了 Use(next => return new DefaultFilesMiddleware(...).Invoke );
如果再添加了一个,比如:StaticFileMiddleware
即使调用了 Use(next=>return new StaticFileMiddleware (...).Invoke);
component 可以根据需要退出 或者继续执行后面的 RequestDelegate 。最后一个是 返回404状态的 RequestDelegate.
如果有多个中间件 如 C1 C2 C3 则实现了这个的结构
返回的 DelegateRequest=C1 (C2 ( C3 (404RequestDelegate) ))
到调用的时候 C1 先调用 可以选择结束 返回 或者 继续调用C2 依次类推 ----------------
浙公网安备 33010602011771号