我们在开发完Asp.Net WebAPI程序后,可以使用WebHost寄宿方式或者SelfHost寄宿方式来部署Asp.Net WebAPI。所谓WebHost寄宿就是通过Asp.Net来实现;所谓SelfHost就是可以通过控制台、WinForm、WPF等方式寄宿。下面我们通过简单的例子来看看WebHost方式和SelfHost方式。

该Demo中包含一个类库项目、一个控制台项目以及一个空的WebForm项目。其中类库项目有一个继承自ApiController的名为HomeController的类;控制台项目实现SelfHost;WebForm项目实现WebHost:

WebAPI代码:

    public class HomeController : ApiController
{
public string Get(string fromStr)
{
return $"The request is from {fromStr}";
}
}

WebHost寄宿方式:

WebHost项目的Global文件代码:

    public class Global : System.Web.HttpApplication
{
protected void Application_Start(object sender, EventArgs e)
{
GlobalConfiguration.Configuration.Routes.MapHttpRoute(name: "default", routeTemplate: "api/{controller}/{fromStr}");
}
}

启动运行WebHost项目,浏览器输入地址http://localhost:34827/api/home/webhost:

SelfHost寄宿方式:

SelfHost项目中的Program文件代码:

        static void Main(string[] args)
{
Assembly.Load("WebAPI,Version=1.0.0.1,Culture=neutral,PublicKeyToken=null"); HttpSelfHostConfiguration configuration = new HttpSelfHostConfiguration("http://localhost:34827/");
using (HttpSelfHostServer server = new HttpSelfHostServer(configuration))
{
server.Configuration.Routes.MapHttpRoute(name: "default", routeTemplate: "api/{controller}/{fromStr}");
server.OpenAsync(); Console.Read();
}
}

启动运行SelfHost项目,浏览器输入地址http://localhost:34827/api/home/from_selfhost:

从上面的例子可以看到Asp.Net WebAPI可以有多重寄宿方式,而Asp.Net WebAPI可以实现多种寄宿方式的原因在于:Asp.Net WebAPI有一个独立于寄宿环境的抽象管道,这个抽象管道是Asp.Net WebAPI的消息处理管道。

下面正式进入今天的主题:Asp.Net WebAPI消息处理管道。Asp.Net WebAPI的消息处理管道是一组HttpMessageHandler的有序组合。在这个消息处理管道中,除了最后一个HttpMessageHandler外,其他的都是由DelegatingHandler这个类型组成的委托链,最后一个HttpMessageHandler是最终处理请求(查找Controller、执行Action)的地方。下面我们通过翻看源码来看看组成消息处理管道的这个有序组合都是哪些类型:

在了解完组成Asp.NetWebAPI消息处理管道的类型后,我们通过一个例子来看看是怎么组成的。我们改一下前面的例子,在WebAPI项目中添加两个自定义的HttpMessageHandler和自定义的HttpServer作为“龙头”:

    public class MyHttpMessageHanlder1 : DelegatingHandler
{
} public class MyHttpMessageHanlder2 : DelegatingHandler
{
} public class MyHttpServer:HttpServer
{
public MyHttpServer(HttpConfiguration configuration):base(configuration)
{ } public new void Initialize()
{
base.Initialize();
}
}

修改HomeController的代码:

    public class HomeController : ApiController
{
public Tuple<IEnumerable<string>, IEnumerable<string>> Get(string fromStr)
{
HttpConfiguration configuration = new HttpConfiguration();
configuration.MessageHandlers.Add(new MyHttpMessageHanlder1());
configuration.MessageHandlers.Add(new MyHttpMessageHanlder1()); MyHttpServer server = new MyHttpServer(configuration); IEnumerable<string> handler1 = GetHandlers(server).ToArray();
server.Initialize();
IEnumerable<string> handler2 = GetHandlers(server).ToArray(); return new Tuple<IEnumerable<string>, IEnumerable<string>>(handler1, handler2);
} private IEnumerable<string> GetHandlers(DelegatingHandler handler)
{
yield return handler.GetType().Name;
while (handler.InnerHandler != null)
{
yield return handler.InnerHandler.GetType().Name;
handler = handler.InnerHandler as DelegatingHandler;
if (handler == null)
break;
}
}
}

运行程序后输入地址http://localhost:34827/api/home/from:

由上面的例子,我们验证了HttpServer为消息处理管道的“龙头”,HttpRoutingDispatcher为管道的“龙尾”,我们自定义的委托链接点是保存在HttpConfiguration类型的MessageHanlers属性中,在HttpServer调用Initialize方法时把MessageHandlers中的委托链节点和“龙头”、“龙尾”组成一个消息处理管道委托链。

通过上面的实例我们知道了组成Asp.Net WebAPI消息处理管道的类型和验证了Asp.Net WebAPI消息处理管道的创建,下面我们继续看看作为消息处理管道的“龙头”和“龙尾”内部都做了些什么。

当请求流转到消息处理管道的最后一个节点时,通过源码,如下,我们可以看到在最后的节点中完成的动作是:根据RouteData找到对应的Controller和Action,然后执行Action,将得到的响应数据逆序流转到“龙头”HttpServer中,在有HttpServer返回给客户端。

总结:

通过前面的剖析,我们知道Asp.Net WebAPI有多种寄宿方式,是因为它有一个独立于寄宿环境的消息处理管道,然后我们也对组成Asp.Net WebAPI消息处理管道的各种类型进行了剖析,并从中发现了消息处理管道是如何创建、请求是如何在管道中流转以及各个管道的作用。

至此,我们对Asp.Net WebAPI消息处理管道进行了一个简单的剖析,由于个人能力有限,如有不对,欢迎指正。

细说Asp.Net WebAPI消息处理管道的更多相关文章

  1. WebApi学习总结系列第五篇(消息处理管道)

    引言: ASP.NET WebAPI的核心框架是一个消息处理管道,这个管道是一组HttpMessageHandler的有序组合.这是一个双工管道,请求消息从一端流入并依次经过所有HttpMessage ...

  2. ASP.NET Web API 框架研究 Self Host模式下的消息处理管道

    Self Host模式下的ASP.NET Web API与WCF非常相似,都可以寄宿在任意类型的托管应用程序中,宿主可以是Windows Form .WPF.控制台应用以及Windows Servic ...

  3. 细说Asp.Net Web API消息处理管道(二)

    在细说Asp.Net Web API消息处理管道这篇文章中,通过翻看源码和实例验证的方式,我们知道了Asp.Net Web API消息处理管道的组成类型以及Asp.Net Web API是如何创建消息 ...

  4. ASP.NET Web API 框架研究 Web Host模式下的消息处理管道

    寄宿的作用是开启一个进程为Web API提供一个运行环境以解决持续监听.请求监听和响应回复,即将接收到的请求转换成HttpRequestMessage对象传入管道,并将管道生成并经过处理后的HttpR ...

  5. ASP.NET Web API实践系列05,消息处理管道

    ASP.NET Web API的消息处理管道可以理解为请求到达Controller之前.Controller返回响应之后的处理机制.之所以需要了解消息处理管道,是因为我们可以借助它来实现对请求和响应的 ...

  6. ASP.NET Web API消息处理管道:Self Host下的消息处理管道[下篇]

    ASP.NET Web API消息处理管道:Self Host下的消息处理管道[下篇] 我们知道ASP.NET Web API借助于HttpSelfHostServer以Self Host模式寄宿于当 ...

  7. ASP.NET Web API的消息处理管道: Self Host下的消息处理管道[上篇]

    ASP.NET Web API的消息处理管道: Self Host下的消息处理管道[上篇] ASP.NET Web API服务端框架核心是一个独立于具体寄宿环境的消息处理管道,它不关心请求消息来源于何 ...

  8. ASP.NET Web API的消息处理管道: HttpRoutingDispatcher

    ASP.NET Web API的消息处理管道: HttpRoutingDispatcher 认情况下,作为消息处理管道“龙头”的HttpServer的Dispatcher属性返回一个HttpRouti ...

  9. ASP.NET Web API的消息处理管道:"龙头"HttpServer

    ASP.NET Web API的消息处理管道:"龙头"HttpServer 一般来说,对于构成ASP.NET Web API消息处理管道的所有HttpMessageHandler来 ...

随机推荐

  1. WIFI机器人网

    WIFI机器人网 WIFI智能小车机器人 外网远程控制WIFI智能小车机器人(WIFI板/703N)

  2. 理解javascript函数的重载

        javascript其实是不支持重载的,这篇文章会和java语言函数的重载对比来加深对javascript函数重载的理解.       以下我会假设读者不了解什么是重载所以会有一些很基础的概念 ...

  3. Xcode的版本问题

    1. 已经安装了Xcode6,如何再安装Xcode5,并使两者共存? 2. Xcode6升级到Xcode7 适配问题 3. XCODE6中使用iOS7 SDK的方法: 从XCODE 5的目录中: /A ...

  4. jsp 获取应用目录

    ${pageContext.request.contextPath}  //   应用名为“demo1” 则得到的是"/demo1" <script>$(documen ...

  5. PHP7新特性

    重写ZenVM,性能比PHP5.6提升300% 新特性: 1.变量类型(为PHP7.1的JIT特性做准备)function test(int $a, string $b, array $c) : in ...

  6. zepto.js 处理Touch事件

    处 理Touch事件能让你了解到用户的每一根手指的位置,在touch事件触发的时候产生,可以通过touch event handler的event对象取到,如果基于zepto.js开发,一般是通过ev ...

  7. 2.13.2. 对结果集进行筛选(Core Data 应用程序实践指南)

    Core Data通过谓词(NSPredicate)来筛选,比如限定获取的数量等.谓词基本对存储区不敏感,但也有例外,比如:matches可用在 in-memory存储区,但是不能用在SQLite存储 ...

  8. centos 安装mysql 5.5.12

    1.安装gcc-c++  gcc make cmake编译器 2.安装ncurses 3.添加用户组 groupadd mysql useradd -r -g mysql mysql 4.安装 tar ...

  9. iOS 之UICollectionView 开发步骤 之 OC

    说起来容易做起来难. 那么我就不说了,来做吧.这就是我的style. 鉴于现在的主流还是OC,那么示例程序还用OC来写,后续补写Swift程序,这里先占个坑. 废话不多说,下面开发步骤来了: 1. 创 ...

  10. Eclipse 注释

    Ctrl + / Ctri + Shift + / Ctrl + Shift + C