.net core 2.0学习笔记(六):Remoting核心类库RealProxy迁移

    在学习.net core的过程中,我们已经明确被告知,Remoting将不会被支持。官方的解释是,.net framework 类型包含了太多的Runtime的内容,是一个非常重量级的服务实现,已被确定为一项有问题的体系结构。说白了就是迁移的难度很大,.net core中直接不提供了。微软的建议是,如果是进程内或跨进程通讯,建议我们使用 Pipes或者内存映射文件(Memory Mapped Files)。如果是机器间的调用,建议我们采用网络通讯的方案,比如HTTP、WCF等。

    好吧,既然微软官方不支持, 我们只能自己想办法搞定了。

    OK,说迁移方案前,我们先看看.net Framework中,使用Remoting的代码:

    通过Remoting封装后的服务调用方法,我们可以直接得到一个服务接口的实现,通过调用次接口的本地代理实现执行远程调用。

static void Main(string[] args)
{
             IUserService service = InvokeSerice.Proxy<IUserService>();
             string uName = service.GetCurrentUserName();

            Console.WriteLine($"当前用户名:{uName}");
             Console.ReadLine();
}

    IUserService接口的声明如下:

public interface IUserService
{
         string GetCurrentUserName();
}

    InvokeService方法的核心实现逻辑如下:

//远程调用服务提供类

public class InvokeService
{

        //获取一个服务的本地调用代理对象
         public static T Proxy<T>()
         {
             var proxy = new InvokeProxy<T>();
             return (T)proxy.GetTransparentProxy();
         }
}

 

//服务本地代理对象实现类

public class InvokeProxy<T> : RealProxy
{
         private Type type = null;
         public InvokeProxy() : this(typeof(T))
         {
             type = typeof(T);
         }

        protected InvokeProxy(Type classToProxy) : base(classToProxy)
         {
         }

        //接收本地调用请求,然后转发远程访问

        public override IMessage Invoke(IMessage msg)
         {
             Console.WriteLine("Invoke 远程服务调用!");
             ReturnMessage message = new System.Runtime.Remoting.Messaging.ReturnMessage("Test",null,0,null,(IMethodCallMessage)msg);

            return (IMessage)message;
         }
}

    通过.NET Portability Analyzer分析这个工程,我们会得到系统不支持的结果。

Image

    既然,.net core 已经不支持RealProxy,那么就只能另起炉灶了。通过翻阅.net core的代码,终于发现了一个程序集:System.Reflection.DispatchProxy。此程序中,有一个类型DispatchProxy。(灵感还是来自于WCF。WCF是.net 中重量级的API,微软不可能不支持,通过翻阅其中的实现逻辑,终于到了RealProxy的替代方案。)

Image

     好吧,通过DispatchProxy提供的功能,很容易可以替代RealProxyP,Remoting的问题终于比较完美的解决了。下面就贴一下替换后的服务实现代码吧。

public class InvokeSerice
{
         public static T Proxy<T>()
         {
             return DispatchProxy.Create<T, InvokeProxy<T>>();
         }
}

public class InvokeProxy<T> : DispatchProxy
{
         private Type type = null;
         public InvokeProxy()
         {
             type = typeof(T);
         }

        protected override object Invoke(MethodInfo targetMethod, object[] args)
         {
             Console.WriteLine("Invoke 远程服务调用!");

            return "Test";
         }
}

posted @ 2017-08-28 08:58  凌晨三点半  阅读(8101)  评论(6编辑  收藏  举报