WCF开发之已知类型(KnownType)

已知类型(Known types)允许在服务契约中使用多态的行为
在服务操作中暴露基本类型
将已知类型(known types)相关到基本类型(基类类型)自身;特定操作;整个服务契约
采用属性声明或者配置的方式来实现

[KnownType]: 相关到基本类型(基类类型)自身

代码
[DataContract(Namespace ="htttp://www.cnblogs.com/Charlesliu")]
[KnownType(
typeof(GigInfo))]
[KnownType(
typeof(PhotoLink))]
[KnownType(
typeof(MP3Link))]
public class LinkItem
[DataContract(Namespace 
="htttp://www.cnblogs.com/Charlesliu")]
public class GigInfo: LinkItem
[DataContract(Namespace 
="htttp://www.cnblogs.com/Charlesliu")]
public class PhotoLink: LinkItem
[DataContract(Namespace 
="htttp://www.cnblogs.com/Charlesliu")]
public class MP3Link: LinkItem

 

[ServiceKnownType]: 相关到整个服务契约

代码
[ServiceContract(Name = "GigManagerContract", Namespace ="http://www.cnblogs.com/Charlesliu")]
[ServiceKnownType(
typeof(GigInfo))]
[ServiceKnownType(
typeof(PhotoLink))]
[ServiceKnownType(
typeof(MP3Link))]
public interface IGigManagerService
{
    [OperationContract]
    void SaveLink(LinkItem item);
    [OperationContract]
    LinkItem GetLink(
string id);
}

 

[ServiceKnownType]: 相关到特定操作

代码
[ServiceContract(Name = "GigManagerContract", Namespace ="http://www.cnblogs.com/Charlesliu")]
public interface IGigManagerService
{
    [OperationContract]
    [ServiceKnownType(
typeof(GigInfo))]
    
void SaveGig(LinkItem item);
    [OperationContract]
    [ServiceKnownType(
typeof(GigInfo))]
    LinkItem GetGig(
string id);
}

 

下面看一个具体的Demo,然后根据代码讲解:

 

ContentTypes 代码

 

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Runtime.Serialization;

namespace ContentTypes
{
    [DataContract(Namespace 
= "http://www.cnblogs.com/Charlesliu")]
    
public enum LinkItemCategories
    {
        [EnumMember]
        Gig,
        [EnumMember]
        MP3,
        [EnumMember]
        Photo
    }

    [DataContract(Name 
= "LinkItem_Contract", Namespace = "http://www.cnblogs.com/Charlesliu")]
    [KnownType(
typeof(GigInfo))]
    [KnownType(
typeof(PhotoLink))]
    [KnownType(
typeof(MP3Link))]
    
public class LinkItem
    {
        
private long m_id;
        
private string m_title;
        
private string m_description;
        
private DateTime m_dateStart;
        
private DateTime m_dateEnd;
        
private string m_url;
        
private LinkItemCategories m_category;

        [DataMember(Name 
= "Id_Contract", IsRequired = false, Order = 0)]
        
public long Id
        {
            
get { return m_id; }
            
set { m_id = value; }
        }

        [DataMember(Name 
= "Title_Contract", IsRequired = true, Order = 1)]
        
public string Title
        {
            
get { return m_title; }
            
set { m_title = value; }
        }

        [DataMember(Name 
= "Description_Contract", IsRequired = true, Order = 2)]
        
public string Description
        {
            
get { return m_description; }
            
set { m_description = value; }
        }

        [DataMember(Name 
= "DateStart_Contract", IsRequired = true, Order = 3)]
        
public DateTime DateStart
        {
            
get { return m_dateStart; }
            
set { m_dateStart = value; }
        }

        [DataMember(Name 
= "DateEnd_Contract", IsRequired = false, Order = 4)]
        
public DateTime DateEnd
        {
            
get { return m_dateEnd; }
            
set { m_dateEnd = value; }
        }

        [DataMember(Name 
= "Url_Contract", IsRequired = false, Order = 5)]
        
public string Url
        {
            
get { return m_url; }
            
set { m_url = value; }
        }

        [DataMember(Name 
= "Category_Contract", IsRequired = false, Order = 6)]
        
public LinkItemCategories Category
        {
            
get { return m_category; }
            
set { m_category = value; }
        }
    }

    [DataContract(Namespace 
= "http://www.cnblogs.com/Charlesliu")]
    
public class GigInfo : LinkItem
    {
        
public GigInfo()
        {
            
this.Category = LinkItemCategories.Gig;
        }
    }

    [DataContract(Namespace 
= "http://www.cnblogs.com/Charlesliu")]
    
public class MP3Link : LinkItem
    {
        
public MP3Link()
        {
            
this.Category = LinkItemCategories.MP3;
        }
    }

    [DataContract(Namespace 
= "http://www.cnblogs.com/Charlesliu")]
    
public class PhotoLink : LinkItem
    {
        
public PhotoLink()
        {
            
this.Category = LinkItemCategories.Photo;
        }
    }
}

 

enum类型可以用[EnumMember]标记,本例中如果不加[KnownType]的相关标记,那么在客户端是看不到子类型的。

GigManagerService 代码
using System;
using System.Collections.Generic;
using System.Linq;
using System.Runtime.Serialization;
using System.ServiceModel;
using System.Text;
using ContentTypes;

namespace WcfServiceLibraryDemo
{
    [ServiceBehavior(InstanceContextMode 
= InstanceContextMode.PerSession)]
    
public class GigManagerService : IGigManagerService
    {

        
private LinkItem m_linkItem;

        
#region IGigManager Members

        
public void SaveGig(LinkItem item)
        {
            m_linkItem 
= item;
        }

        
public LinkItem GetGig()
        {
            
return m_linkItem;
        }

        
#endregion
    }
}
IGigManagerService代码
using System;
using System.Collections.Generic;
using System.Linq;
using System.Runtime.Serialization;
using System.ServiceModel;
using System.Text;
using ContentTypes;

namespace WcfServiceLibraryDemo
{
    [ServiceContract(Name 
= "GigManagerServiceContract", Namespace = "http://www.cnblogs.com/Charlesliu", SessionMode = SessionMode.Required)]
    
public interface IGigManagerService
    {
        [OperationContract(Name 
= "SaveGig", Action = "http://www.cnblogs.com/Charlesliu/GigManagerServiceContract/SaveGig", ReplyAction = "http://www.cnblogs.com/Charlesliu/GigManagerServiceContract/SaveGigResponse")]
        
void SaveGig(LinkItem item);

        [OperationContract(Name 
= "GetGig", Action = "http://www.cnblogs.com/Charlesliu/GigManagerServiceContract/GetGig", ReplyAction = "http://www.cnblogs.com/Charlesliu/GigManagerServiceContract/GetGigResponse")]
        LinkItem GetGig();
    }
}
Form1代码
using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Linq;
using System.Text;
using System.Windows.Forms;
using WinTest.MyServiceReference;

namespace WinTest
{
    
public partial class Form1 : Form
    {
        MyServiceReference.GigManagerServiceContractClient m_proxy 
= new WinTest.MyServiceReference.GigManagerServiceContractClient();

        
public Form1()
        {
            InitializeComponent();
        }

        
private void cmdSave_Click(object sender, EventArgs e)
        {
            MP3Link item 
= new MP3Link();

            item.Id_Contract 
= int.Parse(this.txtId.Text);
            item.Title_Contract 
= this.txtTitle.Text;
            item.Description_Contract 
= this.txtDescription.Text;
            item.DateStart_Contract 
= this.dtpStart.Value;
            item.DateEnd_Contract 
= this.dtpEnd.Value;
            item.Url_Contract 
= this.txtUrl.Text;

            m_proxy.SaveGig(item);
        }

        
private void cmdGet_Click(object sender, EventArgs e)
        {
            MP3Link item 
= (MP3Link)m_proxy.GetGig();
            
if (item != null)
            {
                
this.txtId.Text = item.Id_Contract.ToString();
                
this.txtTitle.Text = item.Title_Contract;
                
this.txtDescription.Text = item.Description_Contract;

                
if (item.DateStart_Contract != DateTime.MinValue)
                    
this.dtpStart.Value = item.DateStart_Contract;
                
if (item.DateEnd_Contract != DateTime.MinValue)
                    
this.dtpEnd.Value = item.DateEnd_Contract;

                
this.txtUrl.Text = item.Url_Contract;
            }
        }
    }
}

 

看到了吗客户端用的是MP3Link这个类,通过[KnownType]实现了WCF的多态。(完)

posted @ 2010-02-02 17:06  烟鬼  阅读(6898)  评论(0编辑  收藏  举报