契约操作不能使用引用对象作为参数,只允许使用基本类型或数据契约

简介: 今天看了一下wcf服务编程这本书,本来准备大致的浏览一下,但是当我看到了契约操作不能使用引用对象作为参数,只允许使用基本类型或数据契约这句话的时候,我知道契约操作只能是通过数据契约进行数据的传递,但是我也是好奇在电脑上测试了一下,结果发现这句话存在问题,可能是我对这句话的理解不够,或者说这句话隐含着什么别的意思,我没有理解透,下面我们就一起来通过这句话来构建一个测试程序来测试一下这句话的正确性。

今天看了一下wcf服务编程这本书,本来准备大致的浏览一下,但是当我看到了契约操作不能使用引用对象作为参数,只允许使用基本类型或数据契约这句话的时候,我知道契约操作只能是通过数据契约进行数据的传递,但是我也是好奇在电脑上测试了一下,结果发现这句话存在问题,可能是我对这句话的理解不够,或者说这句话隐含着什么别的意思,我没有理解透,下面我们就一起来通过这句话来构建一个测试程序来测试一下这句话的正确性。

 

 1 using System;
 2 using System.Collections.Generic;
 3 using System.Linq;
 4 using System.Text;
 5 using System.ServiceModel;
 6 using System.Runtime.Serialization;
 7 namespace Chinaer.WcfDemo.Contracts
 8 {
 9     public class BookInfo
10     {
11         public string Title { get; set; }
12 
13         public string Name { get; set; }
14     }
15 
16 
17     [ServiceContract( Namespace = "http://chinaer.com")]
18     public interface IBook
19     {
20         [OperationContract]
21         List<BookInfo> GetBooks(BookInfo info);
22 
23         [OperationContract]
24         void Check(string strMessage);
25     }
26 }

我们首先定义了一个服务契约IBook,然后定义了一个实体类BookInfo,定义了一个方法GetBooks,其中参数为BookInfo类型,我们之所以这样定义是因为契约操作不能使用引用对象作为参数,只允许使用基本类型或数据契约 这句话中不能使用引用对象,而我们使用了一个类的对象,属于引用对象的范畴。

 1 using System;
 2 using System.Collections.Generic;
 3 using System.Linq;
 4 using System.Text;
 5 using System.ServiceModel;
 6 using Chinaer.WcfDemo.Contracts;
 7 namespace Chinaer.WcfDemo.Services
 8 {
 9     [ServiceBehavior()]
10     public class BookService : IBook
11     {
12         public List<BookInfo> GetBooks(BookInfo bookInfo)
13         {
14             List<BookInfo> listBooks = new List<BookInfo>();
15             for (int i = 0; i < 100; i++)
16             {
17                 BookInfo info = new BookInfo() { Title=i.ToString(), Name="name"+i.ToString() };
18                 listBooks.Add(info);
19             }
20             return listBooks;
21         }
22 
23         public void Check(string strMessage)
24         {
25             bool flag = false;
26             if (strMessage.Equals("guozhiqi", StringComparison.OrdinalIgnoreCase))
27             {
28                 flag = true;
29             }
30         }
31     }
32 }

在服务类中我们实现了契约的方法,这其中没有什么要介绍的。

下一步就是托管代码的实现。

 1 <?xml version="1.0" encoding="utf-8" ?>
 2 <configuration>
 3   <system.serviceModel>
 4     <services>
 5       <service name="Chinaer.WcfDemo.Services.BookService">
 6         <endpoint bindingConfiguration="securityMode" 
 7                   address="http://192.168.1.106:88/bookService" 
 8                   binding="wsHttpBinding"
 9                   contract="Chinaer.WcfDemo.Contracts.IBook"></endpoint>
10       </service>
11     </services>
12 
13     <bindings>
14       <wsHttpBinding>
15         <binding name="securityMode">
16           <security mode="None"></security>
17         </binding>
18       </wsHttpBinding>
19     </bindings>
20 
21     <behaviors></behaviors>
22     
23   </system.serviceModel>
24 
25 </configuration>
 1   using (ServiceHost guoHost = new ServiceHost(typeof(BookService)))
 2             {
 3 
 4                 // Chinaer.WcfDemo.Contracts.IGuo
 5                 if (guoHost.Description.Behaviors.Find<ServiceMetadataBehavior>() == null)
 6                 {
 7                     ServiceMetadataBehavior metaDataBehavior = new ServiceMetadataBehavior();
 8                     metaDataBehavior.HttpGetEnabled = true;
 9                     metaDataBehavior.HttpGetUrl = new Uri("http://192.168.1.106:883/mex");
10                     guoHost.Description.Behaviors.Add(metaDataBehavior);
11                 }
12                 guoHost.Opened += delegate { Console.WriteLine("bookService Open"); };
13                 try
14                 {
15                     if (guoHost.State != CommunicationState.Opened || guoHost.State != CommunicationState.Opening)
16                     {
17                         guoHost.Open();
18                         int i = 0;
19                         foreach (ChannelDispatcher channelDispatcher in guoHost.ChannelDispatchers)
20                         {
21                             Console.WriteLine("{0}:{1}", ++i, channelDispatcher.Listener.Uri);
22                         }
23                         Console.Read();
24                     }
25                 }
26                 catch (CommunicationException ex)
27                 {
28                     guoHost.Abort();
29                 }
30                 catch (Exception ex)
31                 {
32                     guoHost.Abort();
33                 }

在托管程序启动以后我们就需要在客户端通过终结点访问服务,请注意我们传递的参数类型为BookInfo的实例,并不是数据契约

下面是客户端实例,其实这种过程都是老一套,只不过是更改了属性或者说是要测试特定的知识点。

 1  //ServiceReference3.BookClient client = new ServiceReference3.BookClient();
 2             //BookInfo info = new BookInfo();
 3             //BookInfo[] arrinfo = client.GetBooks(info);
 4 
 5             using (ChannelFactory<IBook> chann = new ChannelFactory<IBook>("WSHttpBinding_IBook"))
 6             {
 7                 IBook book = chann.CreateChannel();
 8                 using (book as IDisposable)
 9                 {
10                     BookInfo[] arrInfo = book.GetBooks(new BookInfo());
11                     Console.Read();
12                 }
13 
14             }

 

这就说明刚才wcf服务编程上那句话是错误的,可能是我没有真正的理解那句话的真正含义,如果你知道这句话应该如何解释,麻烦你告诉我,谢谢。

 

我又回来了,回到了技术最前线,
相关文章
|
6月前
|
JavaScript 前端开发
理解包装对象类型
理解包装对象类型
41 0
|
8月前
|
存储 编译器 程序员
【C++】类和对象①(什么是面向对象 | 类的定义 | 类的访问限定符及封装 | 类的作用域和实例化 | 类对象的存储方式 | this指针)
【C++】类和对象①(什么是面向对象 | 类的定义 | 类的访问限定符及封装 | 类的作用域和实例化 | 类对象的存储方式 | this指针)
|
8月前
|
存储 C++
c++类和对象一对象特性一成员变量和成员函数分开存储
c++类和对象一对象特性一成员变量和成员函数分开存储
59 0
|
弹性计算 JavaScript 开发工具
对象和接口-1:对象类型
本实验将介绍TypeScript中的对象类的基本语法
修饰类属性失败。请确保提案类属性已启用并设置为使用松散模式。要在规范模式下将提案类属性与修饰器一起使用,请在阶段 2 中等待下一个主要版本的装饰器。 #80
修饰类属性失败。请确保提案类属性已启用并设置为使用松散模式。要在规范模式下将提案类属性与修饰器一起使用,请在阶段 2 中等待下一个主要版本的装饰器。 #80
63 0
|
算法 Java 编译器
如何理解对象赋值给接口的操作(关键在对象!)
如何理解对象赋值给接口的操作(关键在对象!)
如何理解对象赋值给接口的操作(关键在对象!)
|
编译器 C++
C++继承中的对象模型与继承中构造和析构顺序
继承中的对象模型 问题:从父类继承过来的成员,哪些属于子类对象中? 示例: class Base { public: int m_A; protected: int m_B; private: int m_C; //私有成员只是被隐藏了,但是还是会继承下去
113 0
C++继承中的对象模型与继承中构造和析构顺序
|
存储 Java API
反模式的接口常量
在实际开发过程中,经常会需要定义一个文件,用于存储一些常量,这些常量设计为静态公共常量(使用 public static final 修饰)。这个时候就出现两种选择
165 0
|
Java
匿名内部类方式构建对象导致序列化失败
###问题描述: 以下代码为问题代码: ``` public class ItemDO implements Serializable { private static final long serialVersionUID=-463144769925355007L; ... private Map langAndTitleMap; ...
2391 0