天天看点

Netty框架基础 - BIO

Netty框架基础 - BIO

      • 典型BIO服务器代码分析
      • BIO优缺点

Netty框架,想必很多人都听过它在江湖的传说。这款由JBOSS公司提供,异步的、基于事件驱动的网络应用程序Java开源框架,可以让我们快速开发高性能、高可靠性的网络服务器和客户端程序。我们可以在众多优秀框架或产品中看到它的身影,如Nginx,Redis,Dubbo。也正因为它如此,它也是大型互联网公司面试过程中被问得最多的一块内容。

典型BIO服务器代码分析

package com.qinghaihu.nio.qinghaihu.bio;

import java.io.IOException;
import java.io.InputStream;
import java.io.OutputStream;
import java.net.ServerSocket;
import java.net.Socket;
import java.util.concurrent.ExecutorService;
import java.util.concurrent.Executors;

/**
 * @author zhanglianzhong
 * @date 2020/11/16 11:17
 * @description BIO服务端编程
 */
public class BioServer {

    public static void main(String[] args) throws IOException {

        ExecutorService service = Executors.newCachedThreadPool();

        ServerSocket serverSocket = new ServerSocket(8090);
        while(true){
            Socket socket = serverSocket.accept();
            service.submit(new HandleIO(socket));
        }
    }
}


class HandleIO implements  Runnable{

    private Socket socket;

    public HandleIO(Socket socket){
        this.socket = socket;
    }

    @Override
    public void run() {
        InputStream inputStream = null;
        OutputStream outputStream = null;
        try {
            inputStream = socket.getInputStream();
            byte[] buffer = new byte[1024];
            inputStream.read(buffer);
            System.out.println("服务器接收到数据:"+new String(buffer));

            outputStream = socket.getOutputStream();
            outputStream.write("hello client".getBytes());
        } catch (IOException e) {
            e.printStackTrace();
        }finally {
            if(null != inputStream){
                try {
                    inputStream.close();
                } catch (IOException e) {
                    e.printStackTrace();
                }
            }

            if(null != outputStream){
                try {
                    outputStream.close();
                } catch (IOException e) {
                    e.printStackTrace();
                }
            }

            if(socket !=null){
                try {
                    socket.close();
                } catch (IOException e) {
                    e.printStackTrace();
                }
            }
        }
     }

}
           

服务端首先创建ServerSocket套接字,并绑定端口8090进行监听,调用函数accept进行网络连接。若有客户端来连接,会新建一个读取客户端数据的任务提交到线程池执行。

这里的accpt函数为阻塞式调用,也就是如果没有客户端发起Tcp连接,该函数一直不会返回。同样的,读取客户端通信数据的read()函数也是阻塞式的,即使是基于线程池,执行任务的线程也会被占用,。该编程模式极端情况下,比如一万个个客户端连接后,就是一直不发数据给服务端,这就意味着服务端要占用一万个线程才能满足这类通信要求。

BIO优缺点

优点: 编程实现简单

缺点:占用线程资源多,TPS上不去