跨应用程序域边界传输对象副本 ----继承某类的对象可以跨越应用程序域边界被引用,甚至被远程引用--.NET Remoting

           当一个对象需要长途跋涉到另一个环境中时,需要将其marshal成一个可以传输的形态(比如在.NET Remoting中对象将被打包成一个serializable的ObjRef实例——这个ByRef就是指ObjRef这种形态);同理,当打包以后传输到目标地点,还要执行unmarshal的操作将其还原为内存中的对象

你实际上只拥有对这个对象的一个远程引用,虽然你可以调用它的方法,但实际上这些操作都是发生在远程的(就是前面讲过的过程)

 

NET Remoting分布式开发是在2003年,那时候是Framework1.0初次亮相之时,Remoting分布式开发是Framework1.0其中一个亮点。经过多年的发展,在2005年,WCF随着Framework2.0首先亮相。WCF是结合Remoting,Web服务,TCP/IP套接字,MSMQ信息,P2P,WSE等多方通讯的混合体。随着WCF的出现是否意昧着Remoting即将没落,答案是否定的。因为Remoting有其独到之处,在通讯效率,信息交换,安全性等多方面都有其特点,所以在企业内部系统的信息化交换层的开发当中,很多时候会使用Remoting进行开发

    

一、基础概念

Remoting是采用分布式进行编程的一种技术,主要用于管理跨应用程序域的同步和异步RPC 会话。在默认情况下,Remoting可从使用 HTTP 或 TCP 协议进行信息通讯,并使用 XML 编码的 SOAP 或二进制消息格式进行数据交换。.NET Remoting 提供了非常灵活和可扩展的编程框架,并且可以管理对象的状态。Remoting跟Web服务不同,它并不依赖于IIS,用户可以自己开发(Development)并部署(Dispose)宿主服务器,只需要服务器支持Framework。

二、Remoting的特点

Remoting可以灵活的定义其所基于的协议,比如http,tcp等。在使用TCP/IP的时候,Remoting能发挥更高的效率,其性能接近于DCOM。

Remoting一般需要通过一个应用程序或是Windows服务来承载,也可以使用iis部署。

Remoting必须要在一个支持Framework的开发环境下进行开发,无论客户端跟服务器端都必须支持Framework。

Remoting 支持许多状态管理选项,并且可能与来自同一个用户的多个调用相关或不相关,这取决于您选择的对象生命周期架构。

三、废话不多说直接上示例代码

1. 建立一个Model类库,注意因为对象要进行序列化转化,必须对其加上Serializable特性!

代码

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

namespace Model
{ [Serializable] public class Person { public int ID { get; set;} public String Name {get;set;} public int Age {get;set;} } }

2.建立一个可远程调用的对象,注意远程对象必须继承MarshalByRefObject,继承它才可以实现微软封装的远程调用类

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Runtime.Serialization.Formatters.Binary;
using System.IO;
using Model;
namespace Manager
{    //类必须继承了MarshalByRefObject,才能进行远程调用
public class PersonManager:MarshalByRefObject   
 {     
   public List<Person> GetList()      
   {
List<Person> personList = new List<Person>();
     personList.Add(new Person() { Age=18,ID=1,Name="张三"});
     personList.Add(new Person() { Age = 18, ID = 2, Name = "李四" });
     return personList;
   }   
 }
}

 

核心重点:

在一个应用程序中加载服务器端,服务器端的配置有两种试,一是直接写在代码里面。首先建立服务传送方式,可以选择用TcpServerChannel,也可使用HttpChannel,前者有着更高的效率。然后在ChannelService注册此传输通道,最后通过RemotingConfiguration的RegisterWellKnownServiceType方法注册远程对象。

注意WellKonwnObjectMode可选择为SingleTon或者SingleCall,前者使用单体模式,每个客户端进行访问都会使用同一个远程对象。后者会为每个请求建立一个远程对象。在这个例子里面我们使用SingleTon单体模式。

using System;
using System.Runtime.Remoting;
using System.Runtime.Remoting.Channels;
using System.Runtime.Remoting.Channels.Tcp;
using Model;
using Manager;

namespace RemotingServer
{
class Program
{
static void Main(string[] args)
{
//建立服务传输方式,可选择TCP或者HTTP,前者更能发挥高效性
TcpServerChannel channel =new TcpServerChannel(8089);
//注册通道
ChannelServices.RegisterChannel(channel, false);
//添加可调用的远程对象,WellKonwnObjectMode可选择为SingleTon或者SingleCall
RemotingConfiguration.RegisterWellKnownServiceType(typeof(PersonManager), "PersonTcp", WellKnownObjectMode.Singleton);
Console.ReadKey();
}
}
}

第二,可以在config文件里面实现服务器的配置,其效果与代码实现的相同

<?xml version="1.0" encoding="utf-8" ?>
<configuration>
<system.runtime.remoting>
<application name="Server">
<service>
//定义传送模式,远程对象类,Uri路径
<wellknown mode="Singleton" type="Manager.PersonManager,Manager" objectUri="PersonUri"/>
</service>
<channels>
//定义传送通道,传送方式和接口
<channel ref="tcp" port="8089"/>
</channels>
</application>
</system.runtime.remoting>
</configuration>

最后  在客户端对远程对象进行调用

 1 using System.Runtime.Remoting.Channels;
 2 using System.Runtime.Remoting.Channels.Tcp;
 3 using Model;
 4 using Manager;
 5 
 6 namespace RemotingClient
 7 {
 8 class Program
 9 {
10 staticvoid Main(string[] args)
11 {
12 //确立通道传送方式
13 ChannelServices.RegisterChannel(new TcpClientChannel(),false);
14 //使用Activator.GetObject()或者Activator.CreateInstance()方法建立透明代理,控制远程对象
15 PersonManager personManager = (PersonManager)Activator.GetObject(typeof(PersonManager), "tcp://localhost:8089/PersonUri");
16 //获取远程数据
17 List<Person> personList = personManager.GetList();
18 Console.Write(personList.Count);
19 Console.ReadKey();
20 }
21 }
22 }

 代码

posted @ 2022-12-01 08:41  BK小鬼  阅读(36)  评论(0编辑  收藏  举报