本文在上篇的基础上独立而来,可以看作是VpnService中TCPServer的简单实现,也可以单独出来看作Java NIO的一个Demo。
写在前面
- Java NIO深入理解SocketChannel
- 目的是初步了解Java NIO;最终目标是实现Android手机无Root下Host解析;现有目标是实现一个TCPServer,在NATManager提供的信息下(假设已经实现),连接远程服务器,搭建客户端和服务器的桥梁。
思考
- 现在的思路如下:
- 假设收到本地的连接请求事件ACCEPT,根据请求的端口,从NATManager获取远程信息,建立连接远程,并分别为本地、远程Socket注册READ。
为了便于管理,新建TwinsChannel保存本地、远程Socket信息,并作为附件传递。 - 假设收到本地的可读事件READ,读取内容,往远程Socket写入;
- 假设收到远程的可读事件READ,读取内容,往本地Socket写入;
- 假设收到本地的连接请求事件ACCEPT,根据请求的端口,从NATManager获取远程信息,建立连接远程,并分别为本地、远程Socket注册READ。
要注意的地方
- SocketChannel在注册时,可以传入附件,很方便。
sc.register(selector, SelectionKey.OP_READ, attaches);
- SocketChannel打开后并不意味着就已经建立连接了,还需要进一步操作:
remoteSc = SocketChannel.open(); remoteSc.configureBlocking(false);
if (!twins.remoteSc.isConnected()) { // 如果正在连接,则完成连接 twins.remoteSc.finishConnect(); twins.remoteSc.configureBlocking(false); }