zoukankan      html  css  js  c++  java
  • SignalR循序渐进(一)简单的聊天程序

    前阵子把玩了一下SignalR,起初以为只是个real-time的web通讯组件。研究了几天后发现,这玩意简直屌炸天,它完全就是个.net的双向异步通讯框架,用它能做很多不可思议的东西。它基于Owin,可以脱离繁重的System.Web,随意寄宿在IIS,WindowsService,或者一个控制台程序,这样它即能用于b/s的Web应用,也能用在客户端程序或者服务之间的通讯上。对它的介绍网上早已铺天盖地,这而就不再啰嗦了,先来个小例子,一个聊天室程序。

    服务端


    image

    新建一个叫SignalRDemo的工程,注意一定要选择.net Framework4.5及以上。

    image

    为了让服务端可以自寄宿,安装signalr self host组件。

    public class ChatHub : Hub
        {
            public void Send(string name, string message)
            {
                Console.WriteLine("ConnectionId:{0}, InvokeMethod:{1}", Context.ConnectionId, "Send");
                Clients.AllExcept(Context.ConnectionId).broadcast(name, message);
            }
        }

    新建一个ChatHub,创建一个行为叫Send,里面包含了一条控制台调用记录以及让所有除了发起者外的链接Hub的客户端执行客户端方法broadcast。

    [assembly: OwinStartup(typeof(Host.Startup))]
    
    namespace Host
    {
        public class Startup
        {
            public void Configuration(IAppBuilder app)
            {
                app.MapSignalR();
            }
        }
    }

    创建一个启动类,将所有的Hub映射。

    class Program
        {
            static void Main(string[] args)
            {
                var url = "localhost:10086";
                WebApp.Start<Startup>(url);
                Console.WriteLine("Server started,url is {0}", url);
                Console.ReadLine();
            }
        }

    在Main中写上url和端口,直接用WebApp启动。

    image

    控制台启动后的输出。

    image

    用浏览器访问

    好了,到这儿服务端代码就全部完成了。接下来创建客户端来调用。客户端暂时不采用website,同样用控制台程序来承载。

    客户端


    image

    创建一个Client的控制台工程,添加SignalR的Client包。

    var url = "http://localhost:10086/";
                var connection = new HubConnection(url);
                var chatHub = connection.CreateHubProxy("ChatHub");
                connection.Start().ContinueWith(t =>
                {
                    if (t.IsFaulted)
                    {
                        Console.WriteLine("Connection fault.");
                    }
                });

    在客户端的Main中创建一个HubConnection,创建ChatHub的代理,通过connection.Start启动连接。

    var broadcastHandler = chatHub.On<string, string>("broadcast", (name, message) =>
                {
                    Console.WriteLine("[{0}]{1}: {2}", DateTime.Now.ToString("HH:mm:ss"), name, message);
                });

    定义客户端方法,之前在服务端用Clients.All.broadcast的就是在这边定义的方法。

    Console.WriteLine("Please input your name:");
                var _name = Console.ReadLine();
                Console.WriteLine("Start chat!");
                while (true)
                {
                    var _message = Console.ReadLine();
                    chatHub.Invoke("Send", _name, _message).ContinueWith(t => {
                        if (t.IsFaulted)
                        {
                            Console.WriteLine("Connection error!");
                        }
                    });
                }

    最后,写上一个简单的聊天逻辑。当输入名字后,在while的循环内,每输入一行文本,hub就调用服务端的Send方法。同时服务端在执行Send的过程后又会回掉客户端方法。这种通讯方式在以前的C#代码中是很不可思议的,因为同样的客户端方法还可以写在js里!

     

    执行效果


    image

    执行效果如图。

    好了,一个基于SignalR的简单的控制台聊天程序就完成了,强大的SignalR让开发者不需要关心Socket的一堆烦人的问题。

     

    问题


    上面的那个聊天程序看似很方便很强大,但似乎哪儿有一些奇怪?

    比如说,服务端调用客户端的方法用的是dynamic的,客户端调用服务端的方法传入的都是string类型的,这样首先就不具备扩展性和进行一些规则约束。

    1. 能不能让客户端声明一个强类型的方法列表呢?这样首先不容易写错。
    2. 同样的,能不能让服务端声明一个强类型的方法列表给客户端调用呢?

    下一篇将对上面的2个问题进行思考,并给出解决方案。

  • 相关阅读:
    Oracle SQL语句大全—查看表空间
    Class to disable copy and assign constructor
    在moss上自己总结了点小经验。。高手可以飘过 转贴
    在MOSS中直接嵌入ASP.NET Page zt
    Project Web Access 2007自定义FORM验证登录实现 zt
    SharePoint Portal Server 2003 中的单一登录 zt
    vs2008 开发 MOSS 顺序工作流
    VS2008开发MOSS工作流几个需要注意的地方
    向MOSS页面中添加服务器端代码的另外一种方式 zt
    状态机工作流的 SpecialPermissions
  • 原文地址:https://www.cnblogs.com/royding/p/3733422.html
Copyright © 2011-2022 走看看