Netty In Action中文版 - 第三章:Netty核心概念
在这一章我们将讨论Netty的10个核心类。清楚了解他们的结构对使用Netty非常实用。可能有一些不会再工作中用到。可是也有一些非经常常使用也非常核心,你会遇到。
- Bootstrap or ServerBootstrap
- EventLoop
- EventLoopGroup
- ChannelPipeline
- Channel
- Future or ChannelFuture
- ChannelInitializer
- ChannelHandler
本节的目的就是介绍以上这些概念。帮助你了解它们的使用方法。
3.1 Netty Crash Course
事件能够描写叙述成一个非常通用的方法,由于你能够自己定义一个handler,用来将Object转成byte[]或将byte[]转成Object;也能够定义个handler处理抛出的异常。
能够觉得应用程序的业务逻辑都是在ChannelInboundHandler中来处理的。业务罗的生命周期在ChannelInboundHandler中。
ChannelPipeline和EventLoop和EventLoopGroup密切相关,由于它们三个都和事件处理相关。所以这就是为什么它们处理IO的工作由EventLoop管理的原因。
3.2 Channels,Events and Input/Output(IO)
这样的方式不好,由于同步会影响程序的性能,Netty的设计保证程序处理事件不会有同步。
3.3 什么是Bootstrap?为什么使用它?
- Bootstrap用来连接远程主机,有1个EventLoopGroup
- ServerBootstrap用来绑定本地port,有2个EventLoopGroup
事件组(Groups)。传输(transports)和处理程序(handlers)分别在本章后面讲述,我们在这里仅仅讨论两种"引导"的差异(Bootstrap和ServerBootstrap)。第一个差异非常明显,“ServerBootstrap”监听在server监听一个port轮询client的“Bootstrap”或DatagramChannel是否连接server。通常须要调用“Bootstrap”类的connect()方法。可是也能够先调用bind()再调用connect()进行连接,之后使用的Channel包括在bind()返回的ChannelFuture中。
一个ServerBootstrap能够觉得有2个channels组。第一组包括一个单例ServerChannel,代表持有一个绑定了本地port的socket。第二组包括全部的Channel。代表server已接受了的连接。
下图形象的描写叙述了这样的情况:
3.4 Channel Handlers and Data Flow(通道处理和数据流)
Handlers自身依赖于ChannelPipeline来决定它们运行的顺序,因此不可能通过ChannelPipeline定义处理程序的某些方面,反过来不可能定义也不可能通过ChannelHandler定义ChannelPipeline的某些方面。
不是必需说我们必须定义一个自己和其它的规定。
本节将介绍ChannelHandler和ChannelPipeline在某种程度上细微的依赖。
即使你没有意思到这一点,若果你使用Netty应用将至少有一个ChannelHandler參与。换句话说,ChannelHandler对非常多事情是关键的。那么ChannelHandler到底是什么?给ChannelHandler一个定义不easy,我们能够理解为ChannelHandler是一段运行业务逻辑处理数据的代码,它们来来往往的通过ChannelPipeline。
实际上。ChannelHandler是定义一个handler的父接口,ChannelInboundHandler和ChannelOutboundHandler都实现ChannelHandler接口,例如以下图:
ChannelPipeline的作用我们能够理解为用来管理ChannelHandler的一个容器。每一个ChannelHandler处理各自的数据(比如入站数据仅仅能由ChannelInboundHandler处理),处理完毕后将转换的数据放到ChannelPipeline中交给下一个ChannelHandler继续处理,直到最后一个ChannelHandler处理完毕。
watermark/2/text/aHR0cDovL2Jsb2cuY3Nkbi5uZXQvYWJjX2tleQ==/font/5a6L5L2T/fontsize/400/fill/I0JBQkFCMA==/dissolve/70/gravity/SouthEast" alt="" />
ChannelOutboundHandler的作用和ChannelInboundHandler同样,它能够传递事件消息到下一个Handler或者自己处理消息。
不同的是ChannelOutboundHandler是从ChannelPipeline的尾部開始。而ChannelInboundHandler是从ChannelPipeline的头部開始,当处理完第一个ChannelOutboundHandler处理完毕后会出发一些操作,比方一个写操作。
每一个都提供了在ChannelPipeline中通过调用对应的方法将事件传递给下一个Handler的方法的实现。
我们能覆盖的方法就是我们须要做的处理。
也就是说Netty中发送消息有两种方法:直接写入通道或写入ChannelHandlerContext对象。
这两种方法的主要差别例如以下:
- 直接写入通道导致处理消息从ChannelPipeline的尾部開始
- 写入ChannelHandlerContext对象导致处理消息从ChannelPipeline的下一个handler開始
3.5 编码器、解码器和业务逻辑:细看Handlers
有几个适配器(adapter)同意自己定义ChannelHandler,一般自己定义ChannelHandler须要继承编码/解码适配器类中的一个。Netty有一下适配器:
- ChannelHandlerAdapter
- ChannelInboundHandlerAdapter
- ChannelOutboundHandlerAdapter
三个ChannelHandler涨,我们重点看看ecoders,decoders和SimpleChannelInboundHandler<I>。SimpleChannelInboundHandler<I>继承ChannelInboundHandlerAdapter。
3.5.1 Encoders(编码器), decoders(解码器)
这样的转换一般发生在网络程序中,由于网络上仅仅能传输字节数据。
重写的channelRead方法将调用每一个解码器的“decode”方法并通过ChannelHandlerContext.fireChannelRead(Object
msg)传递给ChannelPipeline中的下一个ChannelInboundHandler。
3.5.2 业务逻辑(Domain logic)
所以应用程序仅仅须要扩展SimpleChannelInboundHandler<I>,也就是我们自己定义一个继承SimpleChannelInboundHandler<I>的handler类,当中<I>是handler能够处理的消息类型。
通过重写父类的方法能够获得一个ChannelHandlerContext的引用,它们接受一个ChannelHandlerContext的參数,你能够在class中当一个属性存储。
幸运的是Netty提供了解决方式,我们能够在加入ChannelHandler到ChannelPipeline中时指定一个EventExecutorGroup,EventExecutorGroup会获得一个EventExecutor。EventExecutor将运行ChannelHandler的全部方法。EventExecutor将使用不同的线程来运行和释放EventLoop。
Netty In Action中文版 - 第三章:Netty核心概念的更多相关文章
- Netty In Action中文版 - 第六章:ChannelHandler
本章介绍 ChannelPipeline ChannelHandlerContext ChannelHandler Inbound vs outbound(入站和出站) 接受连接或创建他们仅仅是你的应 ...
- Netty In Action中文版 - 第五章:Buffers(缓冲)
本章介绍 ByteBuf ByteBufHolder ByteBufAllocator 使用这些接口分配缓冲和运行操作 每当你须要数据传输时,它必须包括一个缓冲区.Java NIO API自带的缓冲区 ...
- Netty In Action中文版 - 第四章:Transports(传输)
本章内容 Transports(传输) NIO(non-blocking IO,New IO), OIO(Old IO,blocking IO), Local(本地), Embedded(嵌入式) U ...
- Netty In Action中文版 - 第七章:编解码器Codec
http://blog.csdn.net/abc_key/article/details/38041143 本章介绍 Codec,编解码器 Decoder,解码器 Encoder,编码器 Netty提 ...
- Java Persistence with MyBatis 3(中文版) 第三章 使用XML配置SQL映射器
关系型数据库和SQL是经受时间考验和验证的数据存储机制.和其他的ORM 框架如Hibernate不同,MyBatis鼓励开发者可以直接使用数据库,而不是将其对开发者隐藏,因为这样可以充分发挥数据库服务 ...
- Netty 源码解析(三): Netty 的 Future 和 Promise
今天是猿灯塔“365篇原创计划”第三篇. 接下来的时间灯塔君持续更新Netty系列一共九篇 Netty 源码解析(一): 开始 Netty 源码解析(二): Netty 的 Channel 当前:Ne ...
- Netty In Action中文版 - 第一章:Netty介绍
本章介绍 Netty介绍 为什么要使用non-blocking IO(NIO) 堵塞IO(blocking IO)和非堵塞IO(non-blocking IO)对照 Java NIO的问题和在Nett ...
- Netty In Action中文版 - 第十五章:选择正确的线程模型
http://blog.csdn.net/abc_key/article/details/38419469 本章介绍 线程模型(thread-model) 事件循环(EventLoop) 并发(Con ...
- Netty In Action中国版 - 第二章:第一Netty程序
本章介绍 获得Netty4最新的版本号 设置执行环境,以构建和执行netty程序 创建一个基于Netty的server和client 拦截和处理异常 编制和执行Nettyserver和client 本 ...
随机推荐
- PHP behavior 机制简单实现
<?php class Base{ private $_m = array(); public function attachBehavior($behaviorObj){ $behaviorO ...
- Matlab 二维绘图函数(plot类)
plot 功能 绘制二维图形的最基本函数. 语法 //x为向量时,以x的元素值为纵坐标,x的序号为横坐标绘制曲线. //x为矩阵时,以其序号为横坐标,按列绘制每列元素值相对于其序号的曲线. polt( ...
- 【easyswoole】 解决安装报错
在使用swoole 创建项目时候,报错 创建命令 composer create-project easyswoole/app easyswoole 错误信息: 解决办法,切换composer 源 镜 ...
- 题目1198:a+b(高精度计算,好像有点问题)
题目链接:http://ac.jobdu.com/problem.php?pid=1198 详解链接:https://github.com/zpfbuaa/JobduInCPlusPlus 参考代码: ...
- [转]centos6 与 7 其中的一些区别
# vi /etc/ssh/sshd_config #将MaxAuthTries注释去掉 MaxAuthTries 5(登录次数) UseDNS no 默认是yes 的,把这个改为no,可以大大减 ...
- undefined类型
undefined类型 只有一个特殊的值 undefined 在使用var声明变量但未对其加以初始化,这个变量的值就是undefined 值是undefined的情况: 1.显示声明并初始化变量值 ...
- Windows Server 2008 R2之六活动目录域服务的卸载
活动目录域服务的卸载是将DC降级为独立服务器或成员服务器的过程. 在删除活动目录之前,为了防止操作失败操作系统故障,须对系统进行备份.同时,我们还必须对待删除的域控制器进行如下检查 1.是否有操作主控 ...
- yii---生产链接的方法
yii生成链接的方法: Yii::$app->urlManager->createUrl('xxx/xxx') <?= Yii::$app->urlManager->cr ...
- 爬虫之Scrapy详解
性能相关 在编写爬虫时,性能的消耗主要在IO请求中,当单进程单线程模式下请求URL时必然会引起等待,从而使得请求整体变慢. import requests def fetch_async(url): ...
- 树形DP总结,持续更新
自己做了动态规划的题目已经有了一个月,但是成效甚微,所以来总结一下动态规划,希望自己能够温故知新.这个博客是关于树形dp的,动态规划的一类题目. 首先从最简单的树形DP入手,树形DP顾名思义就是一棵树 ...