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;
}
}
}
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 { get; set; }
/// <summary>
/// Criteria对象序列化后的数据
/// </summary>
[DataMember]
public byte[] CriteriaData { get; set; }
/// <summary>
/// principal对象序列化后的数据
/// </summary>
[DataMember]
public byte[] Principal { get; set; }
/// <summary>
/// 全局上下文对象序列化后的数据
/// </summary>
[DataMember]
public byte[] GlobalContext { get; set; }
/// <summary>
/// 客户端上下文对象序列化后的数据
/// </summary>
[DataMember]
public byte[] ClientContext { get; set; }
/// <summary>
///
/// </summary>
/// <value>Client Culture.</value>
[DataMember]
public string ClientCulture { get; set; }
/// <summary>
///
/// </summary>
/// <value>Client UI Culture.</value>
[DataMember]
public string ClientUICulture { get; set; }
}
/// 要发送到WcfDataPortal服务器的消息
/// </summary>
[DataContract]
public class CriteriaRequest
{
/// <summary>
/// 业务对象类型(Assembly qualified name)
/// </summary>
[DataMember]
public string TypeName { get; set; }
/// <summary>
/// Criteria对象序列化后的数据
/// </summary>
[DataMember]
public byte[] CriteriaData { get; set; }
/// <summary>
/// principal对象序列化后的数据
/// </summary>
[DataMember]
public byte[] Principal { get; set; }
/// <summary>
/// 全局上下文对象序列化后的数据
/// </summary>
[DataMember]
public byte[] GlobalContext { get; set; }
/// <summary>
/// 客户端上下文对象序列化后的数据
/// </summary>
[DataMember]
public byte[] ClientContext { get; set; }
/// <summary>
///
/// </summary>
/// <value>Client Culture.</value>
[DataMember]
public string ClientCulture { get; set; }
/// <summary>
///
/// </summary>
/// <value>Client UI Culture.</value>
[DataMember]
public string ClientUICulture { get; set; }
}
/// <summary>
/// 要发送到WcfDataPortal上的消息
/// </summary>
[DataContract]
public class UpdateRequest
{
/// <summary>
/// 序列化后的业务对象数据
/// </summary>
[DataMember]
public byte[] ObjectData { get; set; }
/// <summary>
/// 序列化后的Principal对象数据
/// </summary>
[DataMember]
public byte[] Principal { get; set; }
/// <summary>
/// 序列化后的全局上下文对象数据
/// </summary>
[DataMember]
public byte[] GlobalContext { get; set; }
/// <summary>
/// 序列化后的客户端上下文对象数据
/// </summary>
[DataMember]
public byte[] ClientContext { get; set; }
/// <summary>
///
/// </summary>
/// <value>Client Culture.</value>
[DataMember]
public string ClientCulture { get; set; }
/// <summary>
///
/// </summary>
/// <value>Client UI Culture.</value>
[DataMember]
public string ClientUICulture { get; set; }
}
/// 要发送到WcfDataPortal上的消息
/// </summary>
[DataContract]
public class UpdateRequest
{
/// <summary>
/// 序列化后的业务对象数据
/// </summary>
[DataMember]
public byte[] ObjectData { get; set; }
/// <summary>
/// 序列化后的Principal对象数据
/// </summary>
[DataMember]
public byte[] Principal { get; set; }
/// <summary>
/// 序列化后的全局上下文对象数据
/// </summary>
[DataMember]
public byte[] GlobalContext { get; set; }
/// <summary>
/// 序列化后的客户端上下文对象数据
/// </summary>
[DataMember]
public byte[] ClientContext { get; set; }
/// <summary>
///
/// </summary>
/// <value>Client Culture.</value>
[DataMember]
public string ClientCulture { get; set; }
/// <summary>
///
/// </summary>
/// <value>Client UI Culture.</value>
[DataMember]
public string ClientUICulture { get; set; }
}
[DataContract]
public class WcfResponse
{
/// <summary>
/// 序列化业务对象数据
/// </summary>
[DataMember]
public byte[] ObjectData { get; set; }
/// <summary>
/// 序列化错误数据
/// </summary>
[DataMember]
public byte[] Error { get; set; }
/// <summary>
/// 序列化全局上下文数据
/// </summary>
[DataMember]
public byte[] GlobalContext { get; set; }
/// <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() { }
}
public class WcfResponse
{
/// <summary>
/// 序列化业务对象数据
/// </summary>
[DataMember]
public byte[] ObjectData { get; set; }
/// <summary>
/// 序列化错误数据
/// </summary>
[DataMember]
public byte[] Error { get; set; }
/// <summary>
/// 序列化全局上下文数据
/// </summary>
[DataMember]
public byte[] GlobalContext { get; set; }
/// <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>
<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>
<client>
<endpoint address="http://localhost:1670/BFService.svc" binding="basicHttpBinding" contract="ITLead.CslaExtend.Server.Hosts.IExtendWcfPortal" name="BFWcfDataPortal" />
</client>
</system.serviceModel>
记住,还应该将我们编译的DataPortal扩展复制到应用程序的bin目录。
现在,我们已经完成DataPortal的扩展
 
                    
                     
                    
                 
                    
                 
 
         
                
            
         浙公网安备 33010602011771号
浙公网安备 33010602011771号