【问题标题】:.Net Remoting functionality.Net 远程处理功能
【发布时间】:2016-02-18 04:32:41
【问题描述】:

我最近开始使用 .Net 远程处理,并设法开始使用一些简单的教程,例如构建一个库 dll,该库用作客户端可以访问和使用的计算器 (https://www.youtube.com/watch?v=Ve4AQnZ-_H0)。

我希望了解的是如何访问服务器上保存的当前信息。例如,如果我在服务器上运行这个简单的部分:

int x = 0;

while (!Console.KeyAvailable)
{
x++;
System.Threading.Thread.Sleep(1000);
Console.WriteLine(x);
}

到目前为止,我发现构建的 dll 仅返回静态结果,例如使用计算器。我希望能够通过客户端在任何给定时间告诉服务器上有多少 x 。

我不知道我是否足够清楚,但如果需要,我会尝试更好地解释。

【问题讨论】:

  • .NET 远程处理只能用于处理遗留组件,任何新的开发都应该在 WCF 中完成。 (见this page顶部的粗体字)
  • @ScottChamberlain 甚至 WCF 也已被弃用,不应在新开发中使用,除非您确实需要 SOAP 或仅由 WCF 启用的某些功能。否则,请使用 WebAPI。在这种情况下,计算器可以使用服务器并请求增加 x。 x 可以是静态的,并且操作可以简单地返回全局值(尽管我不会将它用于明显的并发问题)。
  • @gretro meh,我说 WCF 和 WebAPI 共存。一种适用于某些东西,一种适用于其他东西。两者都不能替代另一个。
  • @ScottChamberlain 在功能方面,我倾向于同意你的观点。但是,WCF 没有进入 .NET Core 并非巧合。他们不希望它在那里。但你是对的。对于某些东西,我不会使用 WebAPI(但在有限的情况下)。然而,在这种情况下,WebAPI 服务将是一种更好的方法。更少的配置,更简单的方法。
  • @gretro “即使是 WCF 也已被弃用,不应该在新的开发中使用” - 苹果和橘子很好,先生

标签: c# .net .net-remoting


【解决方案1】:

在下面的服务器实现中演示了如何在调用之间保持状态。

// this gets instantiated by clients over remoting
public class Server:MarshalByRefObject
{
    // server wide state
    public static int Value;

    // state only for this instance (that can be shared with several clients
    // depending on its activation model)
    private StringBuilder buildup;

    // an instance
    public Server()
    {
        buildup = new StringBuilder();
        Console.WriteLine("server started");
    }

    // do something useful
    public int DoWork(char ch)
    {
        Console.WriteLine("server received {0}", ch);
        buildup.Append(ch);
        return Value;
    }

    // return all typed chars
    public string GetMessage()
    {
        Console.WriteLine("server GetMessage called") ;
        return buildup.ToString();
    }

    // how long should this instance live
    public override object InitializeLifetimeService()
    {
        // run forever
        return null;
    }
}

注意覆盖InitializeLifetimeService。如果您不控制这一点,您的实例将在 5 分钟后被拆除。

要使用上述类,我们使用以下代码来启动和运行侦听器,包括您的一些逻辑。不要忘记添加对程序集 System.Runtime.Remoting 的引用。

static void Main(string[] args)
{
    // which port 
    var chn = new HttpChannel(1234);
    ChannelServices.RegisterChannel(chn, false);

    // Create only ONE Server instance
    RemotingConfiguration.RegisterWellKnownServiceType(
        typeof(Server), "server", WellKnownObjectMode.Singleton);

    Server.Value = 0;
    while (!Console.KeyAvailable)
    {
        Server.Value++;
        System.Threading.Thread.Sleep(1000);
        Console.WriteLine(Server.Value);
    }
}

当此代码运行时,它应该在端口 1234 上侦听本地机器上的连接。在第一次运行时,我必须禁用防火墙,允许该端口通过本地防火墙。

使用Server 的客户端实现可能如下所示。不要忘记添加对程序集 System.Runtime.Remoting 的引用。

static void Main(string[] args)
{
    var chn = new HttpChannel();
    ChannelServices.RegisterChannel(chn, false);

    RemotingConfiguration.RegisterWellKnownClientType(
        typeof(Server),
        "http://localhost:1234/server");

    Console.WriteLine("Creating server...");
    var s = new Server();

    Console.WriteLine("type chars, press p to print, press x to stop");
    var ch = Console.ReadKey();
    while(ch.KeyChar != 'x')
    {

        switch(ch.KeyChar )
        {
            case 'p':
                Console.WriteLine("msg: {0}", s.GetMessage());
                break;
            default:
                Console.WriteLine("Got value {0} ", s.DoWork(ch.KeyChar));
                break;
        }

            ch = Console.ReadKey();
    }
    Console.WriteLine("stopped");
}

如果您编译并运行它,您的结果可能如下所示:

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2011-12-24
    • 2010-10-11
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多