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

服务端


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

为了让服务端可以自寄宿,安装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启动。

控制台启动后的输出。

用浏览器访问

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

客户端


创建一个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里!

执行效果


执行效果如图。

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

问题


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

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

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

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

SignalR循序渐进(一)简单的聊天程序的更多相关文章

  1. Socket编程实践(3) 多连接服务器实现与简单P2P聊天程序例程

    SO_REUSEADDR选项 在上一篇文章的最后我们贴出了一个简单的C/S通信的例程.在该例程序中,使用"Ctrl+c"结束通信后,服务器是无法立即重启的,如果尝试重启服务器,将被 ...

  2. C#编写简单的聊天程序

    这是一篇基于Socket进行网络编程的入门文章,我对于网络编程的学习并不够深入,这篇文章是对于自己知识的一个巩固,同时希望能为初学的朋友提供一点参考.文章大体分为四个部分:程序的分析与设计.C#网络编 ...

  3. 简单的聊天程序,主要用到的是Socket

    服务端: import java.io.*; import java.net.*; import java.util.*; public class ChatServer { boolean stat ...

  4. Udp实现简单的聊天程序

    在<UDP通讯协议>这篇文章中,简单的说明了Udp协议特征及如何Udp协议传输数据 这里将用Udp协议技术,编写一个简单的聊天程序: //发送端: package com.shindo.j ...

  5. 使用Ajax long polling实现简单的聊天程序

    关于web实时通信,通常使用长轮询或这长连接方式进行实现. 为了能够实际体会长轮询,通过Ajax长轮询实现了一个简单的聊天程序,在此作为笔记. 长轮询 传统的轮询方式是,客户端定时(一般使用setIn ...

  6. C#编写简单的聊天程序(转)

    这是一篇基于Socket进行网络编程的入门文章,我对于网络编程的学习并不够深入,这篇文章是对于自己知识的一个巩固,同时希望能为初学的朋友提供一点参考.文章大体分为四个部分:程序的分析与设计.C#网络编 ...

  7. Java网络编程以及简单的聊天程序

    网络编程技术是互联网技术中的主流编程技术之一,懂的一些基本的操作是非常必要的.这章主要讲解网络编程,UDP和Socket编程,以及使用Socket做一个简单的聊天软件. 全部代码下载:链接 1.网络编 ...

  8. socket实例C语言:一个简单的聊天程序

    我们老师让写一个简单的聊天软件,并且实现不同机子之间的通信,我用的是SOCKET编程.不废话多说了,先附上代码: 服务器端server.c #include <stdio.h> #incl ...

  9. UDP—Socket,套接字聊天简单的聊天程序。

    思路:(发送端) 1.既然需要聊天.就应该怎么建立聊天程序,,DatagramSocket对象http://www.w3cschool.cc/manual/jdk1.6/ DatagramSocket ...

随机推荐

  1. 管道相关函数(1)-pipe

    定义: int pipe(int filedes[2]); 表头文件: #include<unistd.h> 说明: pipe()会建立管道, 并将文件描述词由参数filedes数组返回. ...

  2. 4个著名VCS的比较

    特征 CVS Git Mercurial Subversion 是否原子提交 CVS: 没有. CVS提交不是原子的 Git: 是的. 提交都是原子的 Mercurial: 是的 Subversion ...

  3. 如果本身kali就在局域网,shell在外网,怎么反弹连接呢?

    kali虚拟机使用桥接,路由器端口映射监听的端口即可.

  4. Odoo 8.0 new API 之model 装饰

    model装饰器的作用是返回一个集合列表 应用举例: 定义columns langs = fields.Selection(string="Lang",selection=&quo ...

  5. [debootstrap]制作基于arm平台的debian文件系统

    之前用过的Linux文件系统是直接busybox制作的,而当前使用的是debian的Jessie,看了一些博客后,了解到如果使用debian,那么直接使用debootstrap来构建文件系统即可 -- ...

  6. [vundle]利用vundle工具来管理vim插件

    转自:http://os.51cto.com/art/201507/484174.htm Vim是Linux上一款用途广泛的轻量级文本编辑工具.虽然对普通的Linux用户来说开始学用起来难度相当大,但 ...

  7. UCOS2系统内核讲述(四)_创建任务

    Ⅰ.写在前面 学习本文之前可以参看我前面的文章: UCOS2_STM32移植详细过程(汇总文章) UCOS2系统内核讲述(一)_总体描述 UCOS2系统内核讲述(二)_初始化调用函数 UCOS2系统内 ...

  8. 网页抓取信息(php正則表達式、php操作excel)

    1.问题描写叙述 实现对固定网页上自己须要的信息抓取,以表格形式存储. 我是拿wustoj上的一个排行榜来练习的,地址:wustoj 2.思路 网页自己就简单学习了一下php,刚好用它来做点事情吧,我 ...

  9. 用 HTML5+ payment方法支付宝支付遇到的坑

    用 HTML5+ payment方法碰到的第一个坑就是如果是支付宝的话签约那种支付方式. 因为 Dcloud的文档没有更新的原因你可以看到他们说的都是‘移动支付’,但是你去支付宝平台的时候看到的根本就 ...

  10. 滚动到指定位置js

    function mScroll(id){ $("html,body").stop(true); $(); }