InChatter系统之服务器开发(一)
服务器端是整个消息系统的中枢,类似与人类的大脑。没有他,根本无法实现客户端之间的交流,为什么呢?这也涉及到我们的系统涉及,在服务器端,每个客户端的标识数据都会在服务器端进行保存,在这种情况下,当某一个客户端请求与另外一个客户端进行交流时,我们便可以在服务器端保存的客户端列表中,找到目标客户端,并发送消息。
下面我们就一步步来实现
我们新建一个InChatter的解决方案,默认的项目可以稍后再做处理,也可是删除,我们在项目中新建一个WCF服务库(英文版本的朋友们自行参考)
在上图中,我们看到有WCF服务库、WCF服务应用程序、WCF工作流服务应用程序,我简单介绍下:
WCF服务库需要我们自己开发服务寄宿程序,而WCF服务应用程序是IIS寄宿方式的程序,是可直接运行的服务程序,.svc是服务契约文件,契约的定义和实现在.svc.cs文件中。
至于WCF工作流服务程序则是寄宿在工作流WorkFlow中的程序中的服务。
我们现在回到我们的项目中,现在我们修改实现我们的服务契约:
using InChatter.Service.Data;
using System;
using System.Collections.Generic;
using System.Linq;
using System.Runtime.Serialization;
using System.ServiceModel;
using System.Text; namespace InChatter.Service
{
[ServiceContract(SessionMode = SessionMode.Required, CallbackContract = typeof(IChatCallback), Namespace = "https://inchatter.codeplex.com/")]
public interface IChat
{
[OperationContract(IsOneWay=false,IsInitiating=true,IsTerminating=false)]
void Login(string clientId); [OperationContract(IsOneWay=true,IsInitiating=false,IsTerminating=false)]
void SendMsg(InChatterMessage message); [OperationContract(IsOneWay = true, IsInitiating = false, IsTerminating = true)]
void Logout();
} public interface IChatCallback
{
[OperationContract(IsOneWay=true)]
void ReceiveMsg(InChatterMessage message);
} }
服务契约IChat:方法的实现在服务器端,表示客户端能进行的操作,目前我们的客户端可以登录(Login)、注销(Logout)以及发送消息(SendMsg)
服务回调契约IChatCallback:方法的实现在客户端,代表服务器端能进行的操作
当客户端调用Login方法时,服务器端将初始化Session,我们这里在登录时将返回当前在线的客户端id,当客户端调用Logout时,服务器端将关闭会话,表示会话结束。而我们的消息处理就是SendMsg和ReceiveMsg。某个客户端调用SendMsg时,消息发送到服务器,服务器通过消息筛选,调用ReceiveMsg将消息发送给符合接受条件的客户端,客户端将处理接收到的消息,这个过程和SendMsg是一个完全相反的过程。那么下面我们看看我们的消息结构:
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks; namespace InChatter.Service.Data
{
public class InChatterMessage
{
/// <summary>
/// 发送消息者ID
/// </summary>
public string SenderID { set; get; }
/// <summary>
/// 发送消息者名称
/// </summary>
public string SenderName { set; get; }
/// <summary>
/// 接收消息者id
/// </summary>
public string ReceiverID { set; get; }
/// <summary>
/// 接收消息者名称
/// </summary>
public string ReceiverName { set; get; } /// <summary>
/// 消息类型:系统提醒(notice)、消息(msg)、上线提醒(logon)、下线提醒(logoff)
/// </summary>
public string Type { set; get; }
/// <summary>
/// 消息内容
/// </summary>
public string Content { set; get; }
/// <summary>
/// 消息时间
/// </summary>
public string SendTime { set; get; }
/// <summary>
/// 附加信息
/// </summary>
public string ExtendData { set; get; }
}
}
可以看到,在消息结构中,Type定义了notice、msg、logon、logoff四个消息类型,整个系统过程中的所有消息都被分为这四种形式,这是我们目前的消息结构。
现在服务端的基本框架已经有了,比较简单。下一节我们将实现IChat契约方法。
InChatter系统之服务器开发(一)的更多相关文章
- InChatter系统之服务器开发(二)
现在我们继续进行InChatter系统的服务器端的开发,今天我们将实现服务契约同时完成宿主程序的开发,今天结束之后服务器端将可以正常运行起来. 系统的开发是随着博客一起的,颇有点现场直播的感觉,所有在 ...
- C++服务器开发之笔记三
为什么需要原子性操作? 我们考虑一个例子:(1)x++这个常见的运算符在内存中是怎样操作的?从内存中读x的值到寄存器中,对寄存器加1,再把新值写回x所处的内存地址 若是有两个线程同时对同一个变量++, ...
- 全新重装win8.1系统后 配置开发及办公环境步骤
全新重装win8.1系统后 配置开发及办公环境步骤 这两天,系统因配置开发环境出错,重装了一下,为日后方便,故此记录系统配置流程,防日后重装系统计划不周. 安装前,对照步骤,准备好下列安装文件. 0. ...
- 嵌入式系统Linux内核开发工程师必须掌握的三十道题(转)
嵌入式系统Linux内核开发工程师必须掌握的三十道题 如果你能正确回答以下问题并理解相关知识点原理,那么你就可以算得上是基本合格的Linux内核开发工程师,试试看! 1) Linux中主要有哪几种内核 ...
- linux服务器开发浅谈
[开发前准备] 在进行linux服务器开发之前,必须很清楚地了解所开发的对象需要考虑的相关问题比如:功能架构:提供服务的模块体系结构稳定性:服务器的出core率,内存泄露情况性能:请求与返回的速度与正 ...
- linux下http服务器开发
linux下http服务器开发 1.mystery引入 1)超文本传输协议(HTTP)是一种应用于分布式.合作式.多媒体信息系统的应用层协议 2)工作原理 1)客户端一台客户机与服务器建立连接后,会发 ...
- NIO原理剖析与Netty初步----浅谈高性能服务器开发(一)
除特别注明外,本站所有文章均为原创,转载请注明地址 在博主不长的工作经历中,NIO用的并不多,由于使用原生的Java NIO编程的复杂性,大多数时候我们会选择Netty,mina等开源框架,但理解NI ...
- openfire:基于开源 Openfire 聊天服务器 - 开发Openfire聊天记录插件
基于开源 Openfire 聊天服务器 - 开发Openfire聊天记录插件 上一篇文章介绍到怎么在自己的Java环境中搭建openfire插件开发的环境,同时介绍到怎样一步步简单的开发openfir ...
- MOBA服务器开发第一阶段完成总结
开发历程 项目是从8月20日左右开始开发的,到今天一个月不到吧. 除了底层库和服务器架构外我们大致开发了5个服务器为: 一 ) . 战斗服务器 二 ) . 匹配服务器 三 ) . 验证服务器 四 ) ...
随机推荐
- python-----贴图 和 报错:OSError: image file is truncated (8 bytes not processed)的处理
将一张图片贴到另一张图片上,代码如下: from PIL import Image import os from PIL import ImageFile ImageFile.LOAD_TRUNCAT ...
- 洛谷P3243 [HNOI2015]菜肴制作——拓扑排序
题目:https://www.luogu.org/problemnew/show/P3243 正向按字典序拓扑排序很容易发现是不对的,因为并不是序号小的一定先做: 但若让序号大的尽可能放在后面,则不会 ...
- 《StackGAN: Text to Photo-realistic Image Synthesis with Stacked GAN》论文笔记
出处:arxiv 2016 尚未出版 Motivation 根据文字描述来合成相片级真实感的图片是一项极具挑战性的任务.现有的生成手段,往往只能合成大体的目标,而丢失了生动的细节信息.StackGAN ...
- STM32:获取复位源,软件复位
RCC CSR寄存器会存储复位标示,可通过它来知道复位原因,来源: if(RCC_GetFlagStatus(RCC_FLAG_PINRST)) printf("PINRST\r\n&quo ...
- 3winsock编程1
先看几个结构体定义 typedef struct WSAData { WORD wVersion;//版本号 通过MAKEWORD(2,2)返回该值 高位字节存储副版本号 第位字节存储主版本号 WOR ...
- Phpspy 2011继续身份验证绕过漏洞
Author: Tm3yShell7 官方目前下载已经修补上了 目前官方下载是2011.php, 文件名为2011ok.php的是带洞版本. 今天m0r5和我说phpspy2011 我都不知道2011 ...
- 你不知道的Eclipse用法:全局搜索和更替 (转载)
转自:http://blog.csdn.net/p106786860/article/details/9162537 Eclipse中全局搜索和更替 Eclipse全局搜索步骤 使用快捷键“ctrl+ ...
- Mac下Ruby升级与Rails的安装
也是醉了,网上查了半天一脸懵逼.然后自己动手试试 gem install rails瞬间命令行就没反应了,以为命令行挂了,但是一会儿报错说是没有权限. 好吧,那么来这个 sudo gem instal ...
- bzoj 2157: 旅游【树链剖分+线段树】
裸的树链剖分+线段树 但是要注意一个地方--我WA了好几次才发现取完相反数之后max值和min值是要交换的-- #include<iostream> #include<cstdio& ...
- 【笔记】对自定义异常的理解(Java)
原本,原有的异常是非手动地.自动地抛出的. 了解自定义异常时,发现其信息只是: 继承了谁,即它自己算哪种异常: 它的信息,比如一个ID,这个貌似还是可选的: 它是可被传入信息的 没有遗漏的话,就这仨了 ...