Thrift采用了TServer來作為服務器的抽象,提供了多種類型的服務器實現。用TServerTransport作為服務器的Acceptor抽象,來監聽端口,創建客戶端Socket連接
先來看看TServerTransport。主要有兩類
1. TNonblockingServerTransport和TNonblockingServerSocket作為非阻塞IO的Acceptor,封裝了ServerSocketChannel
2. TServerSocket作為阻塞同步IO的Acceptor,封裝了ServerSocket

~~~
public class TNonblockingServerSocket extends TNonblockingServerTransport {
private ServerSocketChannel serverSocketChannel = null;
}
protected TNonblockingSocket acceptImpl() throws TTransportException {
if (serverSocket_ == null) {
throw new TTransportException(TTransportException.NOT_OPEN, "No underlying server socket.");
}
try {
SocketChannel socketChannel = serverSocketChannel.accept();
if (socketChannel == null) {
return null;
}
TNonblockingSocket tsocket = new TNonblockingSocket(socketChannel);
tsocket.setTimeout(clientTimeout_);
return tsocket;
} catch (IOException iox) {
throw new TTransportException(iox);
}
}
public void registerSelector(Selector selector) {
try {
// Register the server socket channel, indicating an interest in
// accepting new connections
serverSocketChannel.register(selector, SelectionKey.OP_ACCEPT);
} catch (ClosedChannelException e) {
// this shouldn't happen, ideally...
// TODO: decide what to do with this.
}
}
public class TServerSocket extends TServerTransport {
private ServerSocket serverSocket_ = null;
}
protected TSocket acceptImpl() throws TTransportException {
if (serverSocket_ == null) {
throw new TTransportException(TTransportException.NOT_OPEN, "No underlying server socket.");
}
try {
Socket result = serverSocket_.accept();
TSocket result2 = new TSocket(result);
result2.setTimeout(clientTimeout_);
return result2;
} catch (IOException iox) {
throw new TTransportException(iox);
}
}
~~~
再看TServer的類層次結構,主要也是兩類,非阻塞IO和同步IO
非阻塞IO的Server有:
1. TNonblockingServer是單線程的,只有一個SelectAcceptThread線程來輪詢IO就緒事件,調用就緒的channel來相應Accept, Read, Write事件,并且還是使用這個線程來同步調用實際的方法實現。
2. THsHaServer是所謂的半同步半異步的服務器。所謂半同步是說使用一個SelectAcceptThread線程來輪詢IO就緒事件,調用就緒的channel來相應Accept, Read, Write事件。所謂的半異步是說方法的調用是封裝成一個Runnable交給線程池來執行的,交給線程池立刻返回,不同步等待方法執行完畢,方法執行完畢的寫返回是有線程池中的線程來做的,實現了所謂的異步訪問的模式。
3. TThreadSelectorServer,這個服務器類比較有意思,是多線程Reactor模式的一種實現。
3.1 采用了一個AcceptorThread來專門監聽端口,處理Accept事件,然后創建SocketChannel。創建完成之后交給一個線程池來處理后續動作,將SocketChannel放到SelecotrThread的阻塞隊列acceptedQueue中
3.2 采用多個SelectorThread來處理創建好的SocketChannel。每個SelectorThread綁定一個Selector,這樣將SocketChannel分給多個Selector。同時SelectorThread又維護了一個阻塞隊列acceptedQueue,從acceptedQueue中拿新創建好的SocketChannel,來注冊讀事件
同步的TServer有TThreadPoolServer,關聯一個TServerSocket,采用同步IO的方式來Accept,然后交給一個線程池來處理后續動作

這里有一篇老外寫的文章比較各種服務器的性能,[https://github.com/m1ch1/mapkeeper/wiki/Thrift-Java-Servers-Compared](https://github.com/m1ch1/mapkeeper/wiki/Thrift-Java-Servers-Compared)
結論是TThreadSelectorServer在吞吐量和服務器響應時間的表現都是最優的