【Win 10应用开发】手动调用WCF服务
调用服务最简单的方法就是,直接在VS里面添加服务引用,输入服务的地址即可,无论是普通Web服务,还是WCF服务均可。VS会根据获取到的元数据,自动生成客户端代码。
如果服务的调用量很大,应用广泛,可以放在IIS上作为一种Web资源使用。但WCF不限于此,它可以在一个进程中运行,或者可以放到Windows服务进程上运行,实则是一种Windows平台的万能通信技术。
为了装逼,今天老周将演示如何手动调用WCF,仅通过Channel(通道)就可以调用。其实,在某些时候,手动也有手动的好处,手动调用的话,代码量不多,也比较灵活。
当然,这个演示仅供参考。
为了顺利完成装逼演示,首先得弄个服务示例,以往常用的是做一个执行加减乘除的服务来测试,今天既然要装逼,就装得有创意一点,就来一个计算N次方的吧,比如2的3次方为8。
不知各位是否记得建立WCF的步骤,这么小的程序,就不用IIS来运行了,直接用一个控制台应用程序可以了,简单大方美观有层次。
首先要声明服务协定。
[ServiceContract(Name = "pow_service", Namespace = "http://my")]
interface IService
{
[OperationContract(Name = "pow", Action = "PowAction", ReplyAction = "PowReply")]
double Pow(double x, double y);
}
协定只是个接口,在服务器端要实现它,但在客户端不需要知道实现这接口的代码,只要在客户端也定义一个这样的接口,就可以了。当然,如果你不想重复定义协定,你可以把这个接口定义到一个共享的类库中,最好用可移植的库,这样保证平台万能性。
在服务器和客户端中分别定义协定接口有一个好处就是可以两边不必保持一致,接口名、接口的方法都可以不同,参数名也可以不同,只要参数 的顺序、类型、数量,以及返回值的类型相同就可以。
重点是附加在接口上的ServiceContractAttribute,和附加到方法上的OperationContractAttribute特性。服务器和客户端的接口名字可以不同,只要附加的这些特性的属性值相同即可。
所以,在Win10 App客户端,我可以自己声明这样的接口:
[ServiceContract(Name = "pow_service", Namespace = "http://my")]
interface IPowService
{
[OperationContract(Name = "pow", Action = "PowAction", ReplyAction = "PowReply")]
Task<double> PowAsync(double x, double y);
}
你不妨看一下,接口名字和接口成员名字不同,但标注的协定特性是相同的。所谓的协定者,就是服务器和客户端之间必须有一点“默契”,协定接口就是一种规范,不然,客户端不知道服务有哪些操作方法,就无法调用了。
协定完成后,在服务器端要实现协定接口,进行具体的操作。
class PowService : IService
{
public double Pow(double x, double y)
{
double res = Math.Pow(x, y);
return res;
}
}
承载在进程上的WCF比较好处理,不用太复杂的配置,几行代码就可以启动服务主机。
using (ServiceHost host = new ServiceHost(typeof(PowService)))
{
NetTcpBinding binding = new NetTcpBinding(SecurityMode.None); // 直接添加终结点
host.AddServiceEndpoint(typeof(IService), binding, "net.tcp://localhost:1700/pow"); host.Opened += (h, ea) => Console.WriteLine("服务已打开。");
// 打开服务
try
{
host.Open();
}
catch (Exception ex) { Console.WriteLine(ex.Message); } Console.ReadKey();
}
其实很Easy,ServiceHost负责运行服务,可解释为服务主机。因为是手动访问服务,基址可以省略。然后你直接将服务协定相应地作为终结点添加到服务主机中即可。在添加终结点时,需要指明协定的Type,一个Binding,当然还要包含地址。
这里我选用TCP协议来通信,就用NetTcpBinding类,NET TCP的地址要以“net.tcp:”开头。
之后,直接Open就可以运行服务了。
注意这个服务只能手动调用,不能用服务引用生成代码,因为没有公开元数据,生成代码时会找不到WSDL。
=========================================================
然后在Windows App客户端中就可以直接调用了。
// 终结点地址
EndpointAddress ep = new EndpointAddress("net.tcp://localhost:1700/pow");
// TCP绑定
NetTcpBinding binding = new NetTcpBinding(SecurityMode.None); // 创建通道
ChannelFactory<WCFSVContracts.IPowService> factory = new ChannelFactory<WCFSVContracts.IPowService>(binding, ep);
WCFSVContracts.IPowService channel = factory.CreateChannel(); // 调用服务
double x = double.Parse(txt1.Text);
double y = double.Parse(txt2.Text);
double r = await channel.PowAsync(x, y);
tbres.Text = $"计算结果:{r:G}";
WCFSVContracts.IPowService就是在客户端上重新定义的服务协定,但协定的特性要与服务相同,接口名字可以不同。这个上面贴过代码,下面我再贴一段完整的。
using System;
using System.ServiceModel;
using System.Threading.Tasks; namespace WCFSVContracts
{
[ServiceContract(Name = "pow_service", Namespace = "http://my")]
interface IPowService
{
[OperationContract(Name = "pow", Action = "PowAction", ReplyAction = "PowReply")]
Task<double> PowAsync(double x, double y);
}
}
与服务器上的定义有些不同的是,在客户端中,我将操作方法声明为支持异步等待,即返回Task<TResult>,这个是允许的,大家不必怀疑。
你会看到,在客户端上调用也是挺简单的,首先用一个EndpointAddress表示终结点的地址,这个地址必须和服务器上添加的终结点的地址一致,否则找不到服务。
然后实例化一个NetTcpBinding对象,Binding的类型与属性值必须与服务器上的Binding一致。服务器上的NetTcpBinding的安全模式设置为None,客户端上的也要设置为None。因为也不是什么见不得人的数据,就禁用安全模式。
最后,用一个ChannelFactory<TChannel>就可以完成服务调用。TChannel的类型就是协定接口,随着当调用CreateChannel方法时,它所创建的通道就以协定接口为基础返回,它返回的实际类型是一个动态类型,但它可以以协定接口为基础来调用。
运行结果如下图。

【Win 10应用开发】手动调用WCF服务的更多相关文章
- 学习调用WCF服务的各种方法
1.开发工具调用WCF 这中方法很方便也很简单,很多工作VS就帮我们完成了.相信大家也不会对这种方法陌生.这里简单提一下.打开VS,在项目中添加服务引用: 在config中自动声明了有关服务的节点信息 ...
- [转]学习 WCF (6)--学习调用WCF服务的各种方法
转自:http://www.cnblogs.com/gaoweipeng/archive/2009/07/26/1528263.html 作者这篇博文写得很全面. 根据不同的情况,我们可以用不同的方法 ...
- 学习之路十四:客户端调用WCF服务的几种方法小议
最近项目中接触了一点WCF的知识,也就是怎么调用WCF服务,上网查了一些资料,很快就搞出来,可是不符合头的要求,主要有以下几个方面: ①WCF的地址会变动,地址虽变,但是里面的逻辑不变! ②不要引用W ...
- C# 调用WCF服务的两种方法
项目简介 之前领导布置一个做单点登录的功能给我,实际上就是医院想做一个统一的平台来实现在这个统一的平台登录后不需要在His.Emr.Lis等系统一个个登录,直接可以登录到对应的系统,然后进行相应的操作 ...
- SharePoint 2013 调用WCF服务简单示例
内容比较简单,主要记录自己使用SharePoint 2013WCF服务遇到的小问题和小经验,分享给大家,希望能够给需要的人有所帮助.好吧,进入正题! 第一部分 SharePoint 2013调用自带W ...
- WCF分布式开发步步为赢(3)WCF服务元数据交换、配置及编程开发
今天我们继续WCF分布式开发步步为赢(3)WCF服务元数据交换.配置及编程开发的学习.经过前面两节的学习,我们了解WCF分布式开发的相关的基本的概念和自定义宿主托管服务的完整的开发和配置过程.今天我们 ...
- Silverlight客户端调用WCF服务难题解疑
一:解决办法 Silverlight客户端调用WCF服务在实际使用中经常会出现的问题就是无法直接应用类文件和配置文件.微软针对这一情况已经给出了解决办法.WCF开发框架可以帮助我们实现可靠性较高的跨平 ...
- WCF技术剖析之二十九:换种不同的方式调用WCF服务[提供源代码下载]
原文:WCF技术剖析之二十九:换种不同的方式调用WCF服务[提供源代码下载] 我们有两种典型的WCF调用方式:通过SvcUtil.exe(或者添加Web引用)导入发布的服务元数据生成服务代理相关的代码 ...
- WCF技术剖析之十:调用WCF服务的客户端应该如何进行异常处理
原文:WCF技术剖析之十:调用WCF服务的客户端应该如何进行异常处理 在前面一片文章(服务代理不能得到及时关闭会有什么后果?)中,我们谈到及时关闭服务代理(Service Proxy)在一个高并发环境 ...
随机推荐
- 在.NET Core 里使用 BouncyCastle 的DES加密算法
.NET Core上面的DES等加密算法要等到1.2 才支持,我们可是急需这个算法的支持,文章<使用 JavaScriptService 在.NET Core 里实现DES加密算法>需要用 ...
- node中的Stream-Readable和Writeable解读
在node中,只要涉及到文件IO的场景一般都会涉及到一个类-Stream.Stream是对IO设备的抽象表示,其在JAVA中也有涉及,主要体现在四个类-InputStream.Reader.Outpu ...
- winform异步加载数据到界面
做一个学习记录. 有两个需求: 1.点击按钮,异步加载数据,不卡顿UI. 2.把获取的数据加载到gridview上面. 对于需求1,2,代码如下: public delegate void ShowD ...
- 自己来实现一个简易的OCR
来做个简易的字符识别 ,既然是简易的 那么我们就不能用任何的第三方库 .啥谷歌的 tesseract-ocr, opencv 之类的 那些玩意是叼 至少图像处理 机器视觉这类课题对我这种高中没毕业的人 ...
- C# 索引器,实现IEnumerable接口的GetEnumerator()方法
当自定义类需要实现索引时,可以在类中实现索引器. 用Table作为例子,Table由多个Row组成,Row由多个Cell组成, 我们需要实现自定义的table[0],row[0] 索引器定义格式为 [ ...
- MSYS2——Windows平台下模拟linux环境的搭建
最近从MSYS1.0迁移到了MSYS2.0,简单讲,MSYS2.0功能更强大,其环境模拟更加符合linux.虽然本身来自cygwin,但其集成了pacman软件管理工具,很有linux范,并且可以直接 ...
- java中的内部类
/** * 内部类 ?? * 定义在一个内部的类,被称为内部类. * 内部类里有类体,方法体 * 内部类所在的类,被称为外部类. * --------------------------------- ...
- 【干货分享】流程DEMO-补打卡
流程名: 补打卡申请 业务描述: 当员工在该出勤的工作日出勤但漏打卡时,于一周内填写补打卡申请. 流程相关文件: 流程包.xml 流程说明: 直接导入流程包文件,即可使用本流程 表单: 流程: 图片 ...
- DevExpress - 使用 GaugeControl 标尺组件制作抽奖程序 附源码
前不久,公司举办了15周年庆,其中添加了一个抽奖环节,要从在读学员中随机抽取幸运学员,当然,这个任务就分到了我这里. 最后的效果如下,启动有个欢迎页面,数据是来自Excel的,点击开始则上面的学号及姓 ...
- openfire的组件(Component)开发
在之前的文章<Openfire阶段实践总结>中提到过一种openfire的扩展模式Compoent.本文将主要探讨对这种模式的应用与开发方法. 内部与外部组件介绍 在openfire中的许 ...