BeetleX之快速构建Web多房间聊天室
其实构建一个Web多房间聊天室也并不是什么困难的技术,借助于websocket就可以轻松实现多用户在线实时通讯交互;在这里主要介绍一下在BeetleX和BeetleXjs的支持下如何让这个功能实现的更简单和高效。接下来通过使用BeetleX来一步步讲解Web多房间聊天室的具体实现。
信息逻辑
既然是多房间聊天室那它具备两个主要元素,分别是用户和房间;下面通过类来描述这两个元素:
用户
public class User
{
public string Name { get; set; } public string Address { get; set; } [JsonIgnore]
public ISession Session { get; set; } [JsonIgnore]
public Room Room { get; set; } public void Send(BeetleX.FastHttpApi.WebSockets.DataFrame frame)
{
frame.Send(Session);
} public void Exit()
{
Room?.Exit(this);
}
}
信息描述比较简单主要包括信息用:名称,会话和房间;涉及的行为有发送信息和退出房间。
房间
public class Room
{ public string Name { get; set; } public List<User> Users { get; private set; } = new List<User>(); public HttpApiServer HttpServer { get; set; } public void Send(Command cmd)
{
cmd.Room = Name;
var frame = HttpServer.CreateDataFrame(cmd);
lock (Users)
{
foreach (var item in Users)
item.Send(frame);
} } public User[] GetOnlines()
{
lock (Users)
return Users.ToArray();
} public void Enter(User user)
{
if (user == null)
return;
if (user.Room != this)
{
user.Room?.Exit(user);
lock (Users)
Users.Add(user);
user.Room = this;
Command quit = new Command { Type = "enter",Message=$"enter room", User = user };
Send(quit);
}
} public void Exit(User user)
{
if (user == null)
return;
lock (Users)
Users.Remove(user);
user.Room = null;
Command quit = new Command { Type = "quit", Message = $"exit room", User = user };
Send(quit);
}
}
房间信息主要包括名称和用户信息,具体行为有进房间,出房间和向房间发送信息。
服务逻辑
有了逻辑信息那就需要把这个信息通过接口的服务方式提供给外部访问操作,接下来定义一个简单的控制器类来描述相关接口服务行为
[BeetleX.FastHttpApi.Controller]
public class Home : BeetleX.FastHttpApi.IController
{
[BeetleX.FastHttpApi.NotAction]
public void Init(HttpApiServer server, string path)
{
for (int i = ; i < ; i++)
{
string key = $"{i:00}";
mRooms[key] = new Room { Name = key, HttpServer = server };
}
server.HttpDisconnect += (o, e) =>
{
GetUser(e.Session)?.Exit();
};
}
private ConcurrentDictionary<string, Room> mRooms
= new ConcurrentDictionary<string, Room>(StringComparer.OrdinalIgnoreCase);
public object Rooms()
{
return from a in mRooms.Values orderby a.Name select new {a.Name};
}
public void Enter(string room, IHttpContext context)
{
User user = GetUser(context.Session);
mRooms.TryGetValue(room, out Room result);
result?.Enter(user);
}
public void Talk(string message, IHttpContext context)
{
if (!string.IsNullOrEmpty(message))
{
var user = GetUser(context.Session);
Command cmd = new Command { Type = "talk", Message = message, User = user };
user?.Room?.Send(cmd);
}
}
public void Login(string name, IHttpContext context)
{
User user = new User();
user.Name = name;
user.Session = context.Session;
user.Address = context.Request.RemoteIPAddress;
SetUser(context.Session, user);
}
private User GetUser(ISession session)
{
return (User)session["__user"];
} private void SetUser(ISession session, User user)
{
session["__user"] = user;
}
}
Init方法
用于初始化房间信息,并绑定连接断开事件,如果用户断开了则执行用户退出房间。
Login方法
登陆到用户中
Rooms方法
获取所有房间信息
Enter方法
用户进入房间
Talk
用户向房间内发送一条消息
启动服务
当功能逻辑写好后,接下来的工作就是让这些接口部署到websocket服务中,部署的代码比较简单:
class Program
{
static void Main(string[] args)
{
var builder = new HostBuilder()
.ConfigureServices((hostContext, services) =>
{
services.UseBeetlexHttp(o =>
{
o.LogToConsole = true;
o.ManageApiEnabled = false;
o.Port = ;
o.SetDebug();
o.LogLevel = BeetleX.EventArgs.LogType.Warring;
},
typeof(Program).Assembly);
});
builder.Build().Run();
}
}
当服务部署后就可以专心去做前端实现的工作。
Web前端
为了更方便地和Beetlex服务整合,因此也单独针对性地封装了相应的javascript组件;除了自有封装的javascript还涉及到vuejs的使用。通过以上组件整合前端的代码相比服务端来说就更简单了,详细代码如下:
<body>
<div id="page">
<page-header> </page-header>
<div class="container" style="margin-top:110px;">
<div class="row">
<ul style="list-style:none;">
<li v-for="item in messages" class="message">
<h4>
<span class="label label-success">[{{item.Room}}]</span>
<span class="label label-info">{{item.User.Name}}</span>
<span class="label label-default">{{new Date()}}</span>
</h4>
<div style="padding-left:20px;">
{{item.Message}}
</div>
</li>
</ul>
</div>
</div>
<page-footer :status="loginStatus" @login="onLogin($event)"
@talk="onTalk($event)" @select="onSelectRoom($event)" :rooms="getRooms.result">
</page-footer>
</div>
<script>
beetlex.websocket.receive = function (r) {
page.messages.push(r);
};
beetlex.websocket.disconnect = function () {
page.loginStatus = false;
};
beetlex.useWebsocket();
var login = new beetlexAction("/Login");
var getRooms = new beetlexAction('/Rooms', null, []);
var enterRoom = new beetlexAction('/Enter');
var talk = new beetlexAction('/Talk');
login.requested = function (r) {
page.loginStatus = true;
};
var model = {
getRooms: getRooms,
loginStatus: false,
login: login,
talk: talk,
enterRoom: enterRoom,
messages: [],
};
var page = new Vue({
el: '#page',
data: model,
methods: {
onSelectRoom: function (r) {
// alert(r);
this.enterRoom.post({ room: r });
},
onLogin: function (r) {
this.login.post({ name: r });
},
onTalk: function (msg) {
talk.post({ message: msg });
},
},
});
getRooms.get();
</script>
</body>
beetlex
是针对http和websocket封装的功能类,它自动兼容这两种请求;在默认情况是http请求,调用useWebsocket后所有请求都优先使用websocket;当websocket不可用的情况组会自动切回到http.
beetlexAction
用于描述一个请求,分别提供了post和get方法;当在websocket下这两个方法的处理方式一样。
运行效果

演示地址
代码地址
https://github.com/IKende/BeetleX-Samples/tree/master/WebSocket.Chat
BeetleX之快速构建Web多房间聊天室的更多相关文章
- SignalR 实现Web多人聊天室
ASP .NET SignalR 是一个ASP .NET 下的类库,可以在ASP .NET 的Web项目中实现实时通信.什么是实时通信的Web呢?就是让客户端(Web页面)和服务器端可以互相通知消 ...
- UIkit – 轻量级前端框架,帮助你快速构建 Web 界面
UIKit 是一个轻量级,模块化的前端框架,用于构建快速和强大的 Web 界面.UIKit 为您提供了 HTML,CSS 和 JavaScirpt 组件,使用简单,容易定制和扩展.UIKit 基于 L ...
- Mysql EF Core 快速构建 Web Api
(1)首先创建一个.net core web api web项目; (2)因为我们使用的是ef连接mysql数据库,通过NuGet安装MySql.Data.EntityFrameworkCore,以来 ...
- SpringBoot 快速构建微服务体系 知识点总结
可以通过http://start.spring.io/构建一个SpringBoot的脚手架项目 一.微服务 1.SpringBoot是一个可使用Java构建微服务的微框架. 2.微服务就是要倡导大家尽 ...
- ASP.NET SignalR 与LayIM配合,轻松实现网站客服聊天室(四) 添加表情、群聊功能
休息了两天,还是决定把这个尾巴给收了.本篇是最后一篇,也算是草草收尾吧.今天要加上表情功能和群聊.基本上就差不多了,其他功能,读者可以自行扩展或者优化.至于我写的代码方面,自己也没去重构.好的,我们开 ...
- websocket 多聊天室功能
websocket 类也是在网上找到的. 修改后可以用来创建多房间聊天室.可以发送图片表情,图片,及文字. 分享的代码,已经测试.可正常运行 HTML 端代码 <!DOCTYPE html> ...
- 使用轮询&长轮询实现网页聊天室
前言 如果有一个需求,让你构建一个网络的聊天室,你会怎么解决? 首先,对于HTTP请求来说,Server端总是处于被动的一方,即只能由Browser发送请求,Server才能够被动回应. 也就是说,如 ...
- 使用ASP.NET 构建 Web 应用程序快速入门-8小时的免费培训视频
- Scott Hanselman的中文博客[转载] [原文发表地址] Building Web Apps with ASP.NET Jump Start - 8 Hours of FREE Trai ...
- .net core下使用FastHttpApi构建web聊天室
一般在dotnet core下构建使用web服务应用都使用asp.net core,但通过FastHttpApi组建也可以方便地构建web服务应用,在FastHttpApi功能的支持下构建多人聊天室是 ...
随机推荐
- 算法:二叉树的层次遍历(递归实现+非递归实现,lua)
二叉树知识参考:深入学习二叉树(一) 二叉树基础 递归实现层次遍历算法参考:[面经]用递归方法对二叉树进行层次遍历 && 二叉树深度 上面第一篇基础写得不错,不了解二叉树的值得一看. ...
- 02docker核心概念
1:docker三大核心概念 核心概念 描述 镜像 Docker镜像类似于虚拟机镜像,可以将它理解为一个只读的模板. 容器 Docker容器类似于一个轻量级的沙箱,Docker利用容器来运行和隔离应用 ...
- XSS防御和绕过1
原理:对用户输入没做过滤和处理,是用户可以输入一些东西(例如js),控制输出达到一些攻击目的 1.DOM型 基于DOM的XSS有时也称为type0XSS.当用户能够通过交互修改浏览器页面中的DOM(D ...
- 5.Linux 软件安装管理
1.RPM包安装 (RPM会有依赖性,即安装这个包之前,需要安装某个包) 查询已安装的rpm 列表 rpm -qa | grep xx 安装rpm包 rpm -ivh rpm 包名 -i ...
- 理解Cookie和Session的区别及使用
资料一: Cookie和Session的区别 共同之处: cookie和session都是用来跟踪浏览器用户身份的绘画方式. 区别: cookie数据保存在客户端,session数据保存在服务端. s ...
- 日常开发用Windows 好还是 Ubuntu好?
最近打算给电脑重新装系统,纠结了很久,不知道应该是换Windows还是Ubuntu,今天通过我自身的体验,来为大家分析一下,日常开发环境到底是用Windows和Ubuntu. [系统介绍] Windo ...
- Delphi 10.3.2来了!
昨晚,官方正式发布了Delphi 10.3.2,增加对Mac 64应用的开发,支持Linux桌面开发,这个是通过集成fmxlinux实现的,同时修正400个bug,编译器,102个ide,84个fmx ...
- axios+post获取并下载后台返回的二进制流
axios+post获取并下载后台返回的二进制流 let url = $.getCookie('prefixUrl')+'/expenseword/exportWords'; let vm = thi ...
- c++中cin和cout的用法
cin和cout是c++中的标准输入输出流. 一.cin cin的一般用法: cin>>变量a>>变量b>>变量c; cin会自动辨别变量的类型,如a可以是char ...
- 【杭电多校第七场】A + B = C
原题: Given a,b,c, find an arbitrary set of x,y,z such that a*10^x+b*10^y=c*10^z and 0≤x,y,z≤10^6. 给你三 ...