nonepassby

导航

CSLA.NET快速入门系列——实现DataPortal扩展(三)

在第二篇中我们介绍了IDataPortalProxy的实现,本篇主要介绍Wcf服务的实现和配置以启用扩展的DataPortal

Wcf服务主要实现接收IDataPortalProxy传递过来的参数,并进行反序列化(因为Proxy是序列化过的参数),然后将参数重新组装成Csla.Server.DataPortal相应方法的参数,并调用相应的方法,接收返回参数并将返回参数序列化组装成Wcf方法的返回参数返回给调用方。

代码如下:

 

using System;
using Csla.Server.Hosts;
using System.ServiceModel;
using System.ServiceModel.Activation;
using Csla.Serialization;
using System.IO;
using System.Security.Principal;
using Csla.Core;
using Csla.Server;

namespace ITLead.CslaExtend.Server.Hosts
{
    /// <summary>
    
/// 二进制业务对象序列化WcfDataPortal
    
/// </summary>
    [ServiceBehavior(InstanceContextMode = InstanceContextMode.PerCall)]
    [AspNetCompatibilityRequirements(RequirementsMode = AspNetCompatibilityRequirementsMode.Allowed)]
    public class BFWcfPortal : IExtendWcfPortal
    {
        #region IExtendWcfPortal Members

        /// <summary>
        
/// 创建业务对象,Create
        
/// </summary>
        
/// <param name="request"></param>
        [OperationBehavior(Impersonation = ImpersonationOption.Allowed)]
        public WcfResponse Create(CriteriaRequest request)
        {
            Csla.Server.DataPortal portal = new Csla.Server.DataPortal();
            Exception error = null;
            DataPortalResult result = null;
            WcfResponse response = null;
            ISerializationFormatter formatter = SerializationFormatterFactory.GetFormatter();
            try
            {
                request = ConvertRequest(request);
                DataPortalContext context = new DataPortalContext(
                    formatter.Deserialize(request.Principal) as IPrincipal,
                    true,
                    request.ClientCulture,
                    request.ClientUICulture,
                    formatter.Deserialize(request.ClientContext) as ContextDictionary,
                    formatter.Deserialize(request.GlobalContext) as ContextDictionary);
                result = portal.Create(Type.GetType(request.TypeName), formatter.Deserialize(request.CriteriaData), context);
                response = new WcfResponse(
                    formatter.Serialize(result.ReturnObject),
                    formatter.Serialize(error),
                    formatter.Serialize(Csla.ApplicationContext.GlobalContext));
            }
            catch (Exception ex)
            {
                error = ex;
                response = new WcfResponse(
                   null,
                   formatter.Serialize(error),
                   formatter.Serialize(Csla.ApplicationContext.GlobalContext));
            }
            return ConvertResponse(response);
        }

        /// <summary>
        
/// 获取业务对象.
        
/// </summary>
        
/// <param name="request"></param>
        [OperationBehavior(Impersonation = ImpersonationOption.Allowed)]
        public WcfResponse Fetch(CriteriaRequest request)
        {
            Csla.Server.DataPortal portal = new Csla.Server.DataPortal();
            Exception error = null;
            DataPortalResult result = null;
            WcfResponse response = null;
            ISerializationFormatter formatter = SerializationFormatterFactory.GetFormatter();
            try
            {
                request = ConvertRequest(request);
                DataPortalContext context = new DataPortalContext(
                    formatter.Deserialize(request.Principal) as IPrincipal,
                    true,
                    request.ClientCulture,
                    request.ClientUICulture,
                    formatter.Deserialize(request.ClientContext) as ContextDictionary,
                    formatter.Deserialize(request.GlobalContext) as ContextDictionary);
                result = portal.Fetch(Type.GetType(request.TypeName), formatter.Deserialize(request.CriteriaData), context);
                response = new WcfResponse(
                    formatter.Serialize(result.ReturnObject),
                    formatter.Serialize(error),
                    formatter.Serialize(Csla.ApplicationContext.GlobalContext));
            }
            catch (Exception ex)
            {
                error = ex;
                response = new WcfResponse(
                   null,
                   formatter.Serialize(error),
                   formatter.Serialize(Csla.ApplicationContext.GlobalContext));
            }
            return ConvertResponse(response);
        }

        /// <summary>
        
/// 更新业务对象
        
/// </summary>
        
/// <param name="request"></param>
        [OperationBehavior(Impersonation = ImpersonationOption.Allowed)]
        public WcfResponse Update(UpdateRequest request)
        {
            Csla.Server.DataPortal portal = new Csla.Server.DataPortal();
            Exception error = null;
            DataPortalResult result = null;
            WcfResponse response = null;
            ISerializationFormatter formatter = SerializationFormatterFactory.GetFormatter();
            try
            {
                request = ConvertRequest(request);
                DataPortalContext context = new DataPortalContext(
                    formatter.Deserialize(request.Principal) as IPrincipal,
                    true,
                    request.ClientCulture,
                    request.ClientUICulture,
                    formatter.Deserialize(request.ClientContext) as ContextDictionary,
                    formatter.Deserialize(request.GlobalContext) as ContextDictionary);
                result = portal.Update(formatter.Deserialize(request.ObjectData), context);
                response = new WcfResponse(
                    formatter.Serialize(result.ReturnObject),
                    formatter.Serialize(error),
                    formatter.Serialize(Csla.ApplicationContext.GlobalContext));
            }
            catch (Exception ex)
            {
                error = ex;
                response = new WcfResponse(
                   null,
                   formatter.Serialize(error),
                   formatter.Serialize(Csla.ApplicationContext.GlobalContext));
            }
            return ConvertResponse(response);
        }

        /// <summary>
        
/// 删除业务对象
        
/// </summary>
        
/// <param name="request"></param>
        [OperationBehavior(Impersonation = ImpersonationOption.Allowed)]
        public WcfResponse Delete(CriteriaRequest request)
        {
            Csla.Server.DataPortal portal = new Csla.Server.DataPortal();
            Exception error = null;
            DataPortalResult result = null;
            WcfResponse response = null;
            ISerializationFormatter formatter = SerializationFormatterFactory.GetFormatter();
            try
            {
                request = ConvertRequest(request);
                DataPortalContext context = new DataPortalContext(
                    formatter.Deserialize(request.Principal) as IPrincipal,
                    true,
                    request.ClientCulture,
                    request.ClientUICulture,
                    formatter.Deserialize(request.ClientContext) as ContextDictionary,
                    formatter.Deserialize(request.GlobalContext) as ContextDictionary);
                result = portal.Delete(Type.GetType(request.TypeName), formatter.Deserialize(request.CriteriaData), context);
                response = new WcfResponse(
                    formatter.Serialize(result.ReturnObject),
                    formatter.Serialize(error),
                    formatter.Serialize(Csla.ApplicationContext.GlobalContext));
            }
            catch (Exception ex)
            {
                error = ex;
                response = new WcfResponse(
                    null,
                    formatter.Serialize(error),
                    formatter.Serialize(Csla.ApplicationContext.GlobalContext));
            }
            return ConvertResponse(response);
        }

        #endregion


        /// <summary>
        
/// 转换响应结果
        
/// </summary>
        
/// <param name="response"></param>
        
/// <returns></returns>
        protected virtual WcfResponse ConvertResponse(WcfResponse response)
        {
            return response;
        }

        /// <summary>
        
/// 转换Criteria请求
        
/// </summary>
        
/// <param name="request"></param>
        
/// <returns></returns>
        protected virtual CriteriaRequest ConvertRequest(CriteriaRequest request)
        {
            return request;
        }
        /// <summary>
        
/// 转换Update请求
        
/// </summary>
        
/// <param name="request"></param>
        
/// <returns></returns>
        protected virtual UpdateRequest ConvertRequest(UpdateRequest request)
        {
            return request;
        }
    }
}

 

服务参数类:

 

/// <summary>
    
/// 要发送到WcfDataPortal服务器的消息
    
/// </summary>
    [DataContract]
    public class CriteriaRequest
    {
        /// <summary>
        
/// 业务对象类型(Assembly qualified name)
        
/// </summary>
        [DataMember]
        public string TypeName { getset; }

        /// <summary>
        
/// Criteria对象序列化后的数据
        
/// </summary>
        [DataMember]
        public byte[] CriteriaData { getset; }

        /// <summary>
        
/// principal对象序列化后的数据
        
/// </summary>
        [DataMember]
        public byte[] Principal { getset; }

        /// <summary>
        
/// 全局上下文对象序列化后的数据
        
/// </summary>
        [DataMember]
        public byte[] GlobalContext { getset; }

        /// <summary>
        
/// 客户端上下文对象序列化后的数据
        
/// </summary>
        [DataMember]
        public byte[] ClientContext { getset; }

        /// <summary>
        
/// 
        
/// </summary>
        
/// <value>Client Culture.</value>
        [DataMember]
        public string ClientCulture { getset; }

        /// <summary>
        
/// 
        
/// </summary>
        
/// <value>Client UI Culture.</value>
        [DataMember]
        public string ClientUICulture { getset; }

    }

 

/// <summary>
    
/// 要发送到WcfDataPortal上的消息
    
/// </summary>
    [DataContract]
    public class UpdateRequest
    {
        /// <summary>
        
/// 序列化后的业务对象数据
        
/// </summary>
        [DataMember]
        public byte[] ObjectData { getset; }

        /// <summary>
        
/// 序列化后的Principal对象数据
        
/// </summary>
        [DataMember]
        public byte[] Principal { getset; }

        /// <summary>
        
/// 序列化后的全局上下文对象数据
        
/// </summary>
        [DataMember]
        public byte[] GlobalContext { getset; }

        /// <summary>
        
/// 序列化后的客户端上下文对象数据
        
/// </summary>
        [DataMember]
        public byte[] ClientContext { getset; }

        /// <summary>
        
/// 
        
/// </summary>
        
/// <value>Client Culture.</value>
        [DataMember]
        public string ClientCulture { getset; }

        /// <summary>
        
/// 
        
/// </summary>
        
/// <value>Client UI Culture.</value>
        [DataMember]
        public string ClientUICulture { getset; }

    }

 

[DataContract]
  public class WcfResponse
  {
    /// <summary>
    
/// 序列化业务对象数据
    
/// </summary>
    [DataMember]
    public byte[] ObjectData { getset; }
    /// <summary>
    
/// 序列化错误数据
    
/// </summary>
    [DataMember]
    public byte[] Error { getset; }
    /// <summary>
    
/// 序列化全局上下文数据
    
/// </summary>
    [DataMember]
    public byte[] GlobalContext { getset; }

      /// <summary>
      
/// 构造方法
      
/// </summary>
      
/// <param name="objectData"></param>
      
/// <param name="error"></param>
      
/// <param name="globalContext"></param>
    public WcfResponse(byte[] objectData, byte[] error, byte[] globalContext)
    {
      ObjectData = objectData;
      Error = error;
      GlobalContext = globalContext;
    }
    public WcfResponse() { }
  }

 

最后,就是怎么将我们的DataPortal扩展应用到我们的系统中

如果你熟悉WcfPortal的配置,应用此DataPortal扩展其实非常简单,和配置WcfPortal完全一样,只是将相应的类型配置为我们刚刚开发的类型即可:

在服务器上配置:

1、发布DataPortal服务(如BFService.SVC),在里面添加代码:

<%@ ServiceHost Service="ITLead.CslaExtend.Server.Hosts.BFWcfPortal" %>

 

2、修改配置文件web.config,添加:

 <services>
                  <service name="ITLead.CslaExtend.Server.Hosts.BFWcfPortal" behaviorConfiguration="WcfDataPortalHost.Service1Behavior">
              <!-- Service Endpoints -->
              <endpoint binding="basicHttpBinding" contract="ITLead.CslaExtend.Server.Hosts.IExtendWcfPortal" >
              </endpoint>
          </service>
</services>

 

客户端配置:

 <system.serviceModel>
               <client>
                        <endpoint address="http://localhost:1670/BFService.svc" binding="basicHttpBinding"  contract="ITLead.CslaExtend.Server.Hosts.IExtendWcfPortal" name="BFWcfDataPortal" />
                    </client>
    </system.serviceModel>

 

记住,还应该将我们编译的DataPortal扩展复制到应用程序的bin目录。

 

现在,我们已经完成DataPortal的扩展

posted on 2012-09-06 20:16  jack  阅读(500)  评论(0)    收藏  举报