前面的几篇文章,我们学习了怎么开发WCF应用程序与服务,也学习了如何进行WCF的配置。对于Web Service与WCF服务应用,服务端与客户端的通信是通过收发SOAP Message进行,我们如何有效而快速的获取通信信息呢?这就是本文要介绍的一个工具。

一、TcpTrace实现的基本原理

在对Web Service和WCF进行调试时,可以使用Soap Trace 工具对Soap Message进行深入捕获并进行分析。经常使用的工具有TcpTrace与Microsoft Soap Toolkit中的Soap Trace Utility。

对于希望对WCF的消息交换有一个深层次了解的开发者来说,TcpTracer绝对是一个不可多得好工具。我们将TcpTracer置于服务和服务代理之间,TcpTracer会帮助我们接获、显示和转发流经他的消息。

首先来讲讲TcpTrace实现的基本原理。说简单点,TcpTracer就是一个监听/转发器(Listening/Forwarding),就是一个路由器。当启动的时候,我们需要设置两个端口:监听端口(Listening Port)和目的主机(Destination Server)与目的端口(Destination Port),然后TcpTracer就会在本机的监听端口进行网络监听。一旦有针对该监听端口的请求抵达,他会截获整个请求的消息,并将整个消息显示到消息面板上。随后,TcpTracer会将该消息原封不动地转发给目的主机与目的端口。在另一方面,从目的主机与目的端口发送给原端口的消息,也同样被TcpTracer截获、显示和转发。 说白了就是把要发的消息先给我们查看和备份,再转发出去。

接下来我们我们通过下面的步骤演示如何通过TcpTracer在WCF中进行消息的路由。

1) 为了演示TcpTracer在WCF中的应用,还是用我们前面做的书籍查询示例的WCF服务应用(BookService),具体参见WCF学习之旅——第一个WCF示例(一)WCF学习之旅—WCF第二个示例(五)

2) 示例中的终结点的地址为:http://127.0.0.1:8888/BookService(Port为8888)。

3) 同时这个服务端的配置文件信息如下:

<?xml version="1.0" encoding="utf-8"?>
<configuration>
<configSections>
<!-- For more information on Entity Framework configuration, visit http://go.microsoft.com/fwlink/?LinkID=237468 -->
<section name="entityFramework" type="System.Data.Entity.Internal.ConfigFile.EntityFrameworkSection, EntityFramework
, Version=6.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089" requirePermission="false" /> </configSections>
<entityFramework>
<defaultConnectionFactory type="System.Data.Entity.Infrastructure.SqlConnectionFactory, EntityFramework" />
<providers>
<provider invariantName="System.Data.SqlClient" type="System.Data.Entity.SqlServer.SqlProviderServices, EntityFramework.SqlServer" />
</providers>
</entityFramework>
<system.serviceModel>
<diagnostics>
<messageLogging logEntireMessage="true" logKnownPii="false" logMalformedMessages="true"
logMessagesAtServiceLevel="true" logMessagesAtTransportLevel="true" />
<endToEndTracing propagateActivity="true" activityTracing="true" messageFlowTracing="true" />
</diagnostics>
<behaviors>
<serviceBehaviors> <behavior name="metadataBehavior">
<serviceMetadata httpGetEnabled="true" httpGetUrl="http://127.0.0.1:8888/BookService/metadata" />
<serviceDebug includeExceptionDetailInFaults="True" /> </behavior>
</serviceBehaviors>
</behaviors>
<services> <service behaviorConfiguration="metadataBehavior" name="SCF.WcfService.BookService">
<endpoint address="http://127.0.0.1:8888/BookService" binding="wsHttpBinding"
contract="SCF.Contracts.IBookService" /> </service>
</services>
</system.serviceModel>
<startup> <supportedRuntime version="v4.0" sku=".NETFramework,Version=v4.5.2" />
</startup>
<system.diagnostics>
<sources>
<source name="System.ServiceModel" switchValue="Warning" propagateActivity="true">
<listeners>
<add name="xml" />
</listeners>
</source>
</sources>
<sharedListeners>
<add name="xml" type="System.Diagnostics.XmlWriterTraceListener" initializeData="D:\wcf.svclog" />
</sharedListeners>
</system.diagnostics>
</configuration>

4) 客户端的配置信息如下:

<?xml version="1.0" encoding="utf-8" ?>
<configuration>
<startup>
<supportedRuntime version="v4.0" sku=".NETFramework,Version=v4.5.2" />
</startup>
<system.serviceModel>
<bindings>
<wsHttpBinding>
<binding name="WSHttpBinding_IBookService" />
<binding name="WSHttpBinding_IBookService1" />
</wsHttpBinding>
</bindings>
<client>
<endpoint address="http://127.0.0.1:8888/BookService" binding="wsHttpBinding"
bindingConfiguration="WSHttpBinding_IBookService" contract="SCF.Contracts.IBookService"
name="WSHttpBinding_IBookService">
<identity>
<userPrincipalName value="DEVELOPER\Administrator" /> </identity>
</endpoint>
<endpoint address="http://127.0.0.1:8888/BookService" binding="wsHttpBinding"
bindingConfiguration="WSHttpBinding_IBookService1" contract="BookServiceRef.IBookService" name="WSHttpBinding_IBookService1">
<identity>
<userPrincipalName value="DEVELOPER\Administrator" /> </identity>
</endpoint>
</client>
</system.serviceModel>
</configuration>

5)  但是通过上面的设置之后,实际上还是不能够进行数据的捕捉,如下图,无论如何在客户端调用WCF应用,TcpTrace是无法捕捉到任何数据的。

这是为什么呢?请往下看。

二、通过ClientViaBehavior实现基于TcpTracer的消息路由

在我们创建的WCF服务来说,整个服务访问只涉及到两方:服务(BookService)和服务的调用者(客户端)。从消息交换的角度来看,服务的调用者调用者将请求消息直接发送到服务端,计算结果也以回复消息的形式直接返回到服务的调用者。

现在我们需要将TcpTracer作为一个路由器引入到服务(BookService)和服务的调用者 (客户端)之间,那么我们需要解决的是:服务调用者发送的消息不能直接发送到服务端,而应该先发送给TcpTracer,再由TcpTracer转发给服务。我们可以通过ClientViaBehavior实现逻辑地址和物理地址的分离——逻辑地址指向最终的服务,而物理地址则指向 TcpTracer。

具体的原理如下图所示:我们将TcpTracer的监听端口(Listening Port)和目的端口(Destination port)设置成8080和8888(BookService地址所在的端口)。通过ClientViaBehavior将物理地址的端口设成 8080(TcpTracer监听端口)。

注:对于消息发送方来说,SOAP消息的To报头对应的地址由发送端的终结点地址(逻辑地址)决定。

基于上面的实现原理,我们需要修改客户端的配置, 在<system.serviceModel>/<behaviors>/<endpointBehaviors> 添加ClientViaBehavior,将viaUri的端口指定为8080:http://127.0.0.1:8080/BookService。并将该EndpointBehavior应用到终结点中。

1)  配置文件信息修改一下,如下面。请仔细比较一下面的客户端配置文件与上篇文章最后的客户端配置文件的区别:

<?xml version="1.0" encoding="utf-8" ?>
<configuration>
<startup>
<supportedRuntime version="v4.0" sku=".NETFramework,Version=v4.5.2" />
</startup> <system.serviceModel>
<bindings>
<wsHttpBinding>
<binding name="WSHttpBinding_IBookService" />
<binding name="WSHttpBinding_IBookService1" /> </wsHttpBinding>
</bindings>
<behaviors>
<endpointBehaviors>
<behavior name="bookServiceEndpointBehavior">
<clientVia viaUri="http://localhost:8080/BookService" /> </behavior>
</endpointBehaviors>
</behaviors>
<client>
<endpoint address="http://127.0.0.1:8888/BookService" binding="wsHttpBinding" behaviorConfiguration="bookServiceEndpointBehavior"
bindingConfiguration="WSHttpBinding_IBookService" contract="SCF.Contracts.IBookService"
name="WSHttpBinding_IBookService">
<identity>
<userPrincipalName value="DEVELOPER\Administrator" /> </identity>
</endpoint>
<endpoint address="http://127.0.0.1:8888/BookService" binding="wsHttpBinding" behaviorConfiguration="bookServiceEndpointBehavior"
bindingConfiguration="WSHttpBinding_IBookService1" contract="BookServiceRef.IBookService"
name="WSHttpBinding_IBookService1">
<identity>
<userPrincipalName value="DEVELOPER\Administrator" /> </identity>
</endpoint>
</client>
</system.serviceModel>
</configuration>

2) 经过修改保存之后,现在可以进行Soap Trace了,现在我们再次启动TcpTrace。进行如下的设置,如下图。

监听端口(Listen On Port#):可以自由设置,但是不能够与服务的端口重合,并且该端口还需要在客户端注册。在这里设置成8080

目标端口(Destination Port #):服务端口。在这里设置成8888。

3) 先运行Hosting程序,然后运行WinClient,在WinClient中发起请求,这时请求消息和回复消息将会显示到TcpTracer的消息显示面板中,如下图所示:

4)  我们还可以通过日志,把信息记录下来,记录日志的配置如下图。

5)  当关闭tcpTrace时相应的内容被记录到我们指定的Log文件中:

WCF学习之旅—TcpTrace工具(二十五)的更多相关文章

  1. WCF学习之旅—TcpTrace工具(二十六)

    止文(WCF学习之旅—TcpTrace工具(二十五))介绍了关于TcpTrance的一种使用方式,接下来介绍第二种使用方式. 三.通过ListenUri实现基于tcpTracer的消息路由 对于路由的 ...

  2. 学习Spring Boot:(二十五)使用 Redis 实现数据缓存

    前言 由于 Ehcache 存在于单个 java 程序的进程中,无法满足多个程序分布式的情况,需要将多个服务器的缓存集中起来进行管理,需要一个缓存的寄存器,这里使用的是 Redis. 正文 当应用程序 ...

  3. JavaSE 学习笔记之正则表达式(二十五)

    正则表达式:其实是用来操作字符串的一些规则. 好处:正则的出现,对字符串的复杂操作变得更为简单. 特点:将对字符串操作的代码用一些符号来表示.只要使用了指定符号,就可以调用底层的代码对字符串进行操作. ...

  4. WCF学习之旅—第三个示例之三(二十九)

    上接WCF学习之旅—第三个示例之一(二十七) WCF学习之旅—第三个示例之二(二十八) 在上一篇文章中我们创建了实体对象与接口协定,在这一篇文章中我们来学习如何创建WCF的服务端代码.具体步骤见下面. ...

  5. WCF学习之旅—WCF服务的WAS寄宿(十二)

    上接    WCF学习之旅—WCF服务部署到IIS7.5(九) WCF学习之旅—WCF服务部署到应用程序(十) WCF学习之旅—WCF服务的Windows 服务程序寄宿(十一) 八.WAS宿主 IIS ...

  6. WCF学习之旅—实现支持REST客户端应用(二十四)

    WCF学习之旅—实现REST服务(二十二) WCF学习之旅—实现支持REST服务端应用(二十三) 在上二篇文章中简单介绍了一下RestFul与WCF支持RestFul所提供的方法,及创建一个支持RES ...

  7. WCF学习之旅—HTTP双工模式(二十)

    WCF学习之旅—请求与答复模式和单向模式(十九) 四.HTTP双工模式 双工模式建立在上文所实现的两种模式的基础之上,实现客户端与服务端相互调用:前面介绍的两种方法只是在客户端调用服务端的方法,然后服 ...

  8. WCF学习之旅—第三个示例之二(二十八)

    上接WCF学习之旅—第三个示例之一(二十七) 五.在项目BookMgr.Model创建实体类数据 第一步,安装Entity Framework 1)  使用NuGet下载最新版的Entity Fram ...

  9. WCF学习之旅—第三个示例之四(三十)

           上接WCF学习之旅—第三个示例之一(二十七)               WCF学习之旅—第三个示例之二(二十八)              WCF学习之旅—第三个示例之三(二十九)   ...

随机推荐

  1. ASP.NET Core应用针对静态文件请求的处理[2]: 条件请求与区间请求

    通过调用ApplicationBuilder的扩展方法UseStaticFiles注册的StaticFileMiddleware中间件帮助我们处理针对文件的请求.对于StaticFileMiddlew ...

  2. .NET Core的日志[1]:采用统一的模式记录日志

    记录各种级别的日志是所有应用不可或缺的功能.关于日志记录的实现,我们有太多第三方框架可供选择,比如Log4Net.NLog.Loggr和Serilog 等,当然我们还可以选择微软原生的诊断框架(相关A ...

  3. Windows 常用运行库下载 (DirectX、VC++、.Net Framework等)

    经常听到有朋友抱怨他的电脑运行软件或者游戏时提示缺少什么 d3dx9_xx.dll 或 msvcp71.dll.msvcr71.dll又或者是 .Net Framework 初始化之类的错误而无法正常 ...

  4. Oracle碎碎念~2

    1. 如何查看表的列名及类型 SQL> select column_name,data_type,data_length from all_tab_columns where owner='SC ...

  5. CSS知识总结(八)

    CSS常用样式 8.变形样式 改变元素的大小,透明,旋转角度,扭曲度等. transform : none | <transform-function> <transform-fun ...

  6. VS2015在创建项目时的一些注意事项

    一.下面是在创建一个新的项目是我最常用的,现在对他们一一做一个详细的介绍: 1.Win32控制台应用程序我平时编写小的C/C++程序都用它,它应该是用的最多的. 2.名称和解决方案名称的区别:名称是项 ...

  7. Dynamics CRM 之ADFS 使用 WID 的联合服务器场

    使用 WID 的联合服务器场 默认拓扑 Active Directory 联合身份验证服务 (AD FS) 是联合服务器场,使用 Windows 内部数据库 (WID). 在这种拓扑, AD FS 使 ...

  8. NSStringCompareOptions

    typedefNS_OPTIONS(NSUInteger, NSStringCompareOptions) { NSCaseInsensitiveSearch = 1,    //不区分大小写比较 N ...

  9. JavaMail发送邮件

    发送邮件包含的内容有: from字段  --用于指明发件人 to字段      --用于指明收件人 subject字段  --用于说明邮件主题 cc字段     -- 抄送,将邮件发送给收件人的同时抄 ...

  10. Xamarin技术文档------VS多平台开发

    此技术业余时间研究,仅供大家学习参考,不涉及深入研究,有一定开发基础的人员,应该都能较快上手. 一.简介 Xamarin始创于2011年,旨在使移动开发变得难以置信地迅捷和简单.Xamarin的产品简 ...