天天看點

基于Netty的用戶端小Demo

用戶端代碼與伺服器幾乎一緻

channelHandler類代碼如下

package com.jliangmu.client;

import org.jboss.netty.buffer.ChannelBuffer;
import org.jboss.netty.buffer.ChannelBuffers;
import org.jboss.netty.channel.ChannelHandlerContext;
import org.jboss.netty.channel.ChannelStateEvent;
import org.jboss.netty.channel.ExceptionEvent;
import org.jboss.netty.channel.MessageEvent;
import org.jboss.netty.channel.SimpleChannelHandler;

public class Clienthandler extends SimpleChannelHandler{
//關閉連接配接時調用
	public void channelClosed(ChannelHandlerContext ctx, ChannelStateEvent e)
			throws Exception {
		System.out.println("channelClosed");
		super.channelClosed(ctx, e);
	}
//成功連接配接時調用
	public void channelConnected(ChannelHandlerContext ctx, ChannelStateEvent e)
			throws Exception {
		System.out.println("channelConnected");
		super.channelConnected(ctx, e);
	}
//斷開連接配接時調用
	public void channelDisconnected(ChannelHandlerContext ctx,
			ChannelStateEvent e) throws Exception {
		System.out.println("channelDisconnected");
		super.channelDisconnected(ctx, e);
	}
/*在ServerHandler運作時發生異常調用*/
	public void exceptionCaught(ChannelHandlerContext ctx, ExceptionEvent e)
			throws Exception {
		System.out.println("exceptionCaught");
		super.exceptionCaught(ctx, e);
	}
//傳遞資訊時調用
	public void messageReceived(ChannelHandlerContext ctx, MessageEvent e)
			throws Exception {
		String s = (String) e.getMessage();
		System.out.println(s);
		super.messageReceived(ctx, e);
	}
}
           
傳遞資訊接收到消息時,直接列印到控制台上,不回寫給服務端,否則會造成互相回寫的死循環

Client類代碼如下

package com.jliangmu.client;

import java.net.InetSocketAddress;
import java.util.Scanner;
import java.util.concurrent.ExecutorService;
import java.util.concurrent.Executors;

import org.jboss.netty.bootstrap.ClientBootstrap;
import org.jboss.netty.channel.Channel;
import org.jboss.netty.channel.ChannelFuture;
import org.jboss.netty.channel.ChannelPipeline;
import org.jboss.netty.channel.ChannelPipelineFactory;
import org.jboss.netty.channel.Channels;
import org.jboss.netty.channel.socket.nio.NioClientSocketChannelFactory;
import org.jboss.netty.handler.codec.string.StringDecoder;
import org.jboss.netty.handler.codec.string.StringEncoder;

import com.jliangmu.client.Clienthandler;;

/**
 * @author Administrator
 *
 */
public class Client {

	public static void main(String[] args) {
		
		//服務類
		ClientBootstrap bootstrap = new  ClientBootstrap();
		
		//線程池
		ExecutorService boss = Executors.newCachedThreadPool();
		ExecutorService worker = Executors.newCachedThreadPool();
		
		//socket工廠
		bootstrap.setFactory(new NioClientSocketChannelFactory(boss, worker));
		
		//管道工廠
		bootstrap.setPipelineFactory(new ChannelPipelineFactory() {
			
			@Override
			public ChannelPipeline getPipeline() throws Exception {
				ChannelPipeline pipeline = Channels.pipeline();
				pipeline.addLast("decoder", new StringDecoder());
				pipeline.addLast("encoder", new StringEncoder());
				pipeline.addLast("hiHandler", new Clienthandler());
				return pipeline;
			}
		});
		
		//連接配接服務端
		ChannelFuture connect = bootstrap.connect(new InetSocketAddress("127.0.0.1", 10101));
		Channel channel = connect.getChannel();
		
		System.out.println("client start");
		
		Scanner scanner = new Scanner(System.in);
		while(true){
			System.out.println("請輸入");
			channel.write(scanner.next());
		}
	}

}
           
與服務端代碼的差別就是需要連接配接服務端,以及主動向服務端發送資料,這裡用一個死循環實作