Netty实现群聊系统
1 需求
(1) 编写一个 Netty群聊系统,实现服务器端和客户端之间的数据简单通讯(非阻塞)
(2) 实现多人群聊
(3) 服务器端:可以监测用户上线,离线,并实现消息转发功能
(4) 客户端:通过 channel可以无阻塞发送消息给其它所有用户,同时可以接受其它用
(5) 户发送的消息(有服务器转发得到)
目的:进一步理解Net非阻塞网络编程机制
2 Code
2.1 GroupChatConsts
public final class GroupChatConsts {private GroupChatConsts() {}public static final Integer port = 8888;public static final String host = "127.0.0.1";}
2.2 GroupChatServer
(1) GroupChatServerHandler
package com.rosh.netty.chat.server;import io.netty.channel.Channel;
import io.netty.channel.ChannelHandlerContext;
import io.netty.channel.SimpleChannelInboundHandler;
import io.netty.channel.group.ChannelGroup;
import io.netty.channel.group.DefaultChannelGroup;
import io.netty.util.concurrent.GlobalEventExecutor;import java.text.SimpleDateFormat;
import java.util.Date;/*** @Description:* @Author: rosh* @Date: 2020/12/29 22:59*/
public class GroupChatServerHandler extends SimpleChannelInboundHandler<String> {/*** 定义一个channel组,管理所有的channel*/private static ChannelGroup channelGroup = new DefaultChannelGroup(GlobalEventExecutor.INSTANCE);SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");/*** 当建立连接时,第一个被执行*/@Overridepublic void handlerAdded(ChannelHandlerContext ctx) throws Exception {Channel channel = ctx.channel();//通知其他客户,有人加入该聊天室channelGroup.writeAndFlush("【客户端】 " + sdf.format(new Date()) + channel.remoteAddress() + " 加入聊天 \n");//加入聊天channelGroup.add(channel);}/*** 表示channel处于一个活跃的状态*/@Overridepublic void channelActive(ChannelHandlerContext ctx) throws Exception {System.out.println("【" + ctx.channel().remoteAddress() + "】 " + sdf.format(new Date()) + " 上线了 ~");}/*** 表示channel处于不活动的状态*/@Overridepublic void channelInactive(ChannelHandlerContext ctx) throws Exception {System.out.println("【" + ctx.channel().remoteAddress() + "】 " + sdf.format(new Date()) + " 离线了 ~");}/*** channel断开连接会被触发*/@Overridepublic void handlerRemoved(ChannelHandlerContext ctx) throws Exception {Channel channel = ctx.channel();channelGroup.writeAndFlush("【客户端】 " + sdf.format(new Date()) + channel.remoteAddress() + " 离开了\n");}/*** 转发消息*/@Overrideprotected void channelRead0(ChannelHandlerContext ctx, String msg) throws Exception {Channel channel = ctx.channel();channelGroup.forEach(ch -> {if (channel != ch) {ch.writeAndFlush("【客户】" + sdf.format(new Date()) + channel.remoteAddress() + "发送了消息: " + msg + "\n");} else {ch.writeAndFlush("【自己】" + sdf.format(new Date()) + "发送了消息: " + msg + "\n");}});}/*** 发生异常时 关闭通道*/@Overridepublic void exceptionCaught(ChannelHandlerContext ctx, Throwable cause) throws Exception {ctx.close();}
}
(2) GroupChatServerChannelInitializer
public class GroupChatServerChannelInitializer extends ChannelInitializer<SocketChannel> {@Overrideprotected void initChannel(SocketChannel ch) throws Exception {ChannelPipeline pipeline = ch.pipeline();//解码器pipeline.addLast("decoder", new StringDecoder());//编码器pipeline.addLast("encoder", new StringEncoder());//加入自己业务handlerpipeline.addLast("serverHandler", new GroupChatServerHandler());}
}
(3) GroupChatServerHandler
public class GroupChatServer {public static void main(String[] args) {NioEventLoopGroup bossGroup = new NioEventLoopGroup(1);NioEventLoopGroup workerGroup = new NioEventLoopGroup();try {ServerBootstrap serverBootstrap = new ServerBootstrap();serverBootstrap.group(bossGroup, workerGroup)//nio.channel(NioServerSocketChannel.class)//bossGroup,option,服务端接受连接的队列长度,如果队列已满,客户端连接将被拒绝。.option(ChannelOption.SO_BACKLOG, 128)//workerGroup,option,是否启动心跳包活机制.childOption(ChannelOption.SO_KEEPALIVE, true).childHandler(new GroupChatServerChannelInitializer());//绑定端口ChannelFuture channelFuture = serverBootstrap.bind(GroupChatConsts.port).sync();//监听关闭事件channelFuture.channel().closeFuture().sync();} catch (InterruptedException e) {e.printStackTrace();} finally {bossGroup.shutdownGracefully();workerGroup.shutdownGracefully();}}}
2.3 GroupChatClient
(1) GroupChatClientHandler
public class GroupChatClientHandler extends SimpleChannelInboundHandler<String> {@Overrideprotected void channelRead0(ChannelHandlerContext ctx, String msg) throws Exception {System.out.println(msg.trim());}
}
(2) GroupChatClientChannelInitializetr
public class GroupChatClientChannelInitializetr extends ChannelInitializer<SocketChannel>{@Overrideprotected void initChannel(SocketChannel ch) throws Exception {ChannelPipeline pipeline = ch.pipeline();//解码器pipeline.addLast("decoder", new StringDecoder());//编码器pipeline.addLast("encoder", new StringEncoder());//自定义handlerpipeline.addLast("clientHandler", new GroupChatClientHandler());}
}
(3) GroupChatClient
public class GroupChatClient {public static void main(String[] args) {EventLoopGroup group = new NioEventLoopGroup();try {Bootstrap bootstrap = new Bootstrap();bootstrap.group(group).channel(NioSocketChannel.class).handler(new GroupChatClientChannelInitializetr());ChannelFuture channelFuture = bootstrap.connect(GroupChatConsts.host, GroupChatConsts.port).sync();//输入信息Channel channel = channelFuture.channel();Scanner scanner = new Scanner(System.in);while (scanner.hasNext()) {String msg = scanner.nextLine();channel.writeAndFlush(msg + "\n");}} catch (InterruptedException e) {e.printStackTrace();} finally {group.shutdownGracefully();}}}
3 测试
(1) 启动服务端,启动3个客户端
(2) 发送消息
Netty实现群聊系统相关推荐
- Netty基础,Netty实现群聊系统
NIO群聊系统 这里面的知识比较全面,用到了我们之前学习的三大组件,首先我先来给大家介绍本系统的功能 服务端功能 最基本的当然是注册功能,也就是将serverSocketChannel注册进Selec ...
- Netty之实现一个简单的群聊系统
要求 编写一个 Netty 群聊系统,实现服务器端和客户端之间的数据简单通讯(非阻塞) 实现多人群聊 服务器端:可以监测用户上线,离线,并实现消息转发功能 客户端:通过channel可以无阻塞发送消息 ...
- (六)Netty网络编程应用实例-群聊系统
实例要求: 编写一个NIO群聊系统,实现服务器端和客户端之间的数据简单通讯(非阻塞) 实现多人群聊 服务器端:可以监测用户上线,离线,并实现消息转发功能 客户端:通过channel可以无阻塞发送消息给 ...
- Netty学习笔记:二、NIO网络应用实例-群聊系统
实例要求: 编写一个NIO群聊系统,实现服务器端和多个客户端之间的数据简单通讯(非阻塞): 实现多人群聊: 服务器端:可以监测用户上线.离线,并实现消息转发功能: 客户端:通过channel可以无阻塞 ...
- Java基础之《netty(18)—群聊系统》
一.实例要求 1.编写一个netty群聊系统,实现服务器端和客户端之间的数据简单通讯(非阻塞) 2.实现多人群聊 3.服务器端:可以检测用户上线,离线,并实现消息转发功能 4.客户端:通过channe ...
- Netty:实现群聊系统+自定义名称+空闲检测+Protobuf
作为一个Java小白,持续学习是不可避免的,近期学习了Netty的相关知识,使用Netty实现了一个简单的群聊系统,使用Protobuf进行传输,支持空闲心跳检测,并且可以自定义群聊名称,所以写了此篇 ...
- socket通信 _ 一个简单的群聊系统
群聊系统要用到通信socket协议,在java中要用到两个类java.net.ServerSocket和 Java.net.Socket.ServerSocket用于创建服务器,而Socket用于创建 ...
- Java NIO网络编程之群聊系统
概述 对ServerSocketChannel.SocketChannel.SelectionKey有一定的理解和了解对应API. NIO非阻塞网络编程相关关系梳理: 以下概念: ServerSock ...
- Java NIO群聊系统
实例要求: 1.编写一个 NIO 群聊系统,实现服务器端和客户端之间的数据简单通讯(非阻塞) 2.实现多人群聊 3.服务器端:可以监测用户上线,离线,并实现消息转发功能 4.客户端:通过 Channe ...
- 4.基于NIO的群聊系统
[README] 1.本文总结自B站<netty-尚硅谷>,很不错: 2.文末有错误及解决方法: [1]群聊需求 1)编写一个 NIO 群聊系统,实现服务器端和客户端之间的数据简单通讯(非 ...
最新文章
- DOM(Document object madle) 文档对象模型: 元素节点 文本节点 属性节点
- python asyncio文件操作_Python asyncio文档阅读摘要
- java 控制台刷屏 dll_控制台被警告刷屏 · Issue #IXD8V · 卓源软件/JeeSite 4.2 - Gitee.com...
- 认证篇——单向散列函数
- C 结构体嵌套一级指针 二级指针 动态分配内存
- mysql 全文本检索的列_Mysql 全文本检索
- [改善Java代码]若有必要,使用变长数组
- c# 操作word中在右下角插入图片
- 时光就是一颗巨大的牛轧糖
- ThinkPhp框架:父类及表单验证
- Android OpenGL 开发
- 吉首大学第十届“新星杯”大学生程序设计大赛(暨新生网络同步赛)
- Android官方源码资料博客
- matlab钢材切割,一种基于MATLAB的钢材裂纹扩展速率试验数据处理方法
- Microsoft .Net Remoting系列专题之一:.Net Remoting基础篇
- 【综述】Deep Learning for Visual Tracking: A Comprehensive Survey-2019
- Wlan学习—无线网络安全
- ViewBinding使用时出现Could not find method viewBinding() for arguments错误
- 智能驾驶大数据是什么?传统车企如何升级?
- 电脑丢失的dll文件怎么一键修复?修复dll方法分享