JAva単純チャットネットワークプログラミング
18978 ワード
demo 1(単一スレッド単純通信)ioストリーム
サービス側
クライアント
demo 1(単一スレッド単純通信)nio
サービス側
クライアント
netty demo
サービス側構成
serverコールバック処理
サーバ側起動
クライアント
クライアントコールバック処理
サービス側
public class Server {
public static void main(String[] args) throws Exception {
//5. ServerSocket、Socket、OutputStream、InputStream
ServerSocket serverSocket = null;
boolean flag = true;
Socket socket = null;
OutputStream out = null;
InputStream in = null;
try {
//6.
serverSocket = new ServerSocket(8000);//
System.out.println(" , ...");
socket = serverSocket.accept();//
//
in = socket.getInputStream();
//7.
out = socket.getOutputStream();
System.out.println(socket.getInetAddress().getHostAddress() + "--- ");
out.write(" ".getBytes());
out.flush();
while (flag) {
byte[] b = new byte[1024];
int len = in.read(b);
System.out.println("client:" + new String(b, 0, len));
//
Scanner src = new Scanner(System.in);
String str = src.nextLine();
out.write(str.getBytes());
out.flush();
if (str.equals("bye")) {
flag = false;
}
}
} catch (IOException e) {
e.printStackTrace();
} finally {
//8. 、ServerSocket Socket
in.close();
out.close();
serverSocket.close();
socket.close();
}
}
}
クライアント
public class Client {
public static void main(String[] args) throws Exception {
//1. Socket 、OutputStream InputStream
Socket socket = null;
OutputStream out = null;
InputStream in = null;
boolean flag = true;
// IP
String serverIP = "127.0.0.1";// IP
int port = 8000;//
try {
//2.
socket = new Socket(serverIP, port);//
out = socket.getOutputStream();//
while (flag) {
//3.
byte[] b = new byte[1024];
in = socket.getInputStream();
int len = in.read(b);
String response = new String(b, 0, len);
System.out.println("server:" + response);
if ("bye".equals(response)) {
flag = false;
break;
}
//
Scanner src = new Scanner(System.in);
String str = src.nextLine();
out.write(str.getBytes());
out.flush();
}
} catch (Exception e) {
e.printStackTrace();
} finally {
//4. Socket
in.close();
out.close();
socket.close();
}
}
}
demo 1(単一スレッド単純通信)nio
サービス側
public class NIOServer {
// SocketChannel
private static Map clientMap = new HashMap();
private static ByteBuffer sBuffer = ByteBuffer.allocate(1024);
// (Selector)
private static Selector selector;
public static void main(String[] args) throws IOException {
// (Selector)
selector = Selector.open();
// ServerSocketChannel
ServerSocketChannel serverSocketChannel = ServerSocketChannel.open();
//
serverSocketChannel.configureBlocking(false);
// ServerSocketChannel ServerSocket (port)
ServerSocket serverSocket = serverSocketChannel.socket();
serverSocket.bind(new InetSocketAddress(8000));
/**
* (Channel) (Selector), selectionKey.OP_ACCEPT
* , ,selector.select() ,
* selector.select() 。
*/
serverSocketChannel.register(selector, SelectionKey.OP_ACCEPT);
System.out.println(" 。。。");
//
while (true) {
// , ,
selector.select();
//
Set selectionKeys = selector.selectedKeys();
Iterator iterator = selectionKeys.iterator();
//
while (iterator.hasNext()) {
//
SelectionKey key = iterator.next();
// ,
iterator.remove();
//
if (key.isAcceptable()) {
handleAccept(key);
} else if (key.isReadable()) {//
handleRead(key);
}
}
}
}
/**
*
*/
private static void handleAccept(SelectionKey key) throws IOException {
//
ServerSocketChannel server = (ServerSocketChannel) key.channel();
SocketChannel socketChannel = server.accept();
socketChannel.configureBlocking(false);
//
String msg = " !";
socketChannel.write(ByteBuffer.wrap(msg.getBytes()));
//
new Thread() {
@Override
public void run() {
while (true) {
try {
sBuffer.clear();
//
Scanner src = new Scanner(System.in);
String str = src.nextLine();
// System.out.println(sendText);
sBuffer.put(Charset.forName("UTF-8").encode(str));
sBuffer.flip();
socketChannel.write(sBuffer);
} catch (IOException e) {
e.printStackTrace();
}
}
}
}.start();
clientMap.put(getClientName(socketChannel), socketChannel);
// , ,
socketChannel.register(selector, SelectionKey.OP_READ);
}
/**
* ,
*/
private static void handleRead(SelectionKey key) throws IOException {
SocketChannel channel = (SocketChannel) key.channel();
//
ByteBuffer buffer = ByteBuffer.allocate(128);
channel.read(buffer);
//
byte[] data = buffer.array();
String msg = new String(data).trim();
System.out.println("client:" + channel.toString() + " " + msg);
//
// dispatch(channel, msg);
}
/**
*
*/
private static void dispatch(SocketChannel client, String info) throws IOException {
if (!clientMap.isEmpty()) {
for (Map.Entry entry : clientMap.entrySet()) {
SocketChannel temp = entry.getValue();
if (!client.equals(temp)) {
sBuffer.clear();
sBuffer.put(Charset.forName("UTF-8").encode(getClientName(client) + ":" + info));
sBuffer.flip();
temp.write(sBuffer);
}
}
}
}
/**
*
*/
private static String getClientName(SocketChannel client){
Socket socket = client.socket();
return "[" + socket.getInetAddress().toString().substring(1) + ":" + Integer.toHexString(client.hashCode()) + "]";
}
}
クライアント
public class NIOClient {
// (Selector)
private static Selector selector;
private static Charset charset = Charset.forName("UTF-8");
public static void main(String[] args) throws IOException {
// (Selector)
selector = Selector.open();
// SocketChannel
SocketChannel channel = SocketChannel.open();
//
channel.configureBlocking(false);
// , , handleConnect channel.finishConnect()
channel.connect(new InetSocketAddress("localhost", 8000));
/**
* (Channel) (Selector), selectionKey.OP_CONNECT
* , ,selector.select() ,
* selector.select() 。
*/
channel.register(selector, SelectionKey.OP_CONNECT);
//
while (true) {
/*
* I/O , selector , ,
* selector wakeup , , ,
* , api , 。
*/
selector.select();
//
Set selectionKeys = selector.selectedKeys();
Iterator iterator = selectionKeys.iterator();
//
while (iterator.hasNext()) {
//
SelectionKey key = iterator.next();
// ,
iterator.remove();
//
if (key.isConnectable()) {
handleConnect(key);
} else if (key.isReadable()) {//
handleRead(key);
}
}
}
}
/**
*
*/
private static void handleConnect(SelectionKey key) throws IOException {
//
SocketChannel channel = (SocketChannel) key.channel();
if (channel.isConnectionPending()) {
// channel.finishConnect()
channel.finishConnect();
}
channel.configureBlocking(false);
ByteBuffer sBuffer = ByteBuffer.allocate(1024);
//
String msg = "Hello Server!";
channel.write(ByteBuffer.wrap(msg.getBytes()));
//
new Thread() {
@Override
public void run() {
while (true) {
try {
sBuffer.clear();
//
Scanner src = new Scanner(System.in);
String str = src.nextLine();
// System.out.println(sendText);
sBuffer.put(charset.encode(str));
sBuffer.flip();
channel.write(sBuffer);
} catch (IOException e) {
e.printStackTrace();
}
}
}
}.start();
// ,
channel.register(selector, SelectionKey.OP_READ);
}
/**
* ,
*/
private static void handleRead(SelectionKey key) throws IOException {
SocketChannel channel = (SocketChannel) key.channel();
//
ByteBuffer buffer = ByteBuffer.allocate(128);
channel.read(buffer);
//
byte[] data = buffer.array();
String msg = new String(data).trim();
System.out.println("server:" + msg);
}
}
netty demo
サービス側構成
public class ServerChannelInitializer extends ChannelInitializer {
@Override
protected void initChannel(SocketChannel channel) {
//
// channel.pipeline().addLast(new LineBasedFrameDecoder(1024));
// String, GBK、UTF-8
channel.pipeline().addLast(new StringDecoder(Charset.forName("GBK")));
// String, GBK、UTF-8
channel.pipeline().addLast(new StringEncoder(Charset.forName("GBK")));
//
channel.pipeline().addLast(new MyServerHandler());
}
}
serverコールバック処理
public class MyServerHandler extends SimpleChannelInboundHandler {
public static HashMap channelList = new HashMap();
/**
* , 。
*/
@Override
public void channelActive(ChannelHandlerContext ctx) throws Exception {
SocketChannel channel = (SocketChannel) ctx.channel();
System.out.println(" ");
System.out.println(" : ");
System.out.println(" IP:" + channel.localAddress().getHostString());
System.out.println(" Port:" + channel.localAddress().getPort());
System.out.println(" ");
//
String str = " " + " " + new Date() + " " + channel.localAddress().getHostString() + "\r
";
ctx.writeAndFlush(str);
}
/**
* , 。
*/
@Override
public void channelInactive(ChannelHandlerContext ctx) throws Exception {
System.out.println(" " + ctx.channel().localAddress().toString());
}
@Override
public void channelRead0(ChannelHandlerContext ctx, Object msg) throws Exception {
channelList.put("1",ctx.channel());
// msg { , }
System.out.println(" client:" + msg);
// { ByteBuf, }
// String str = " :" + new Date() + " " + msg + "\r
";
// ctx.writeAndFlush(str);
}
/**
* , , , 、
*/
@Override
public void exceptionCaught(ChannelHandlerContext ctx, Throwable cause) throws Exception {
ctx.close();
System.out.println(" :\r
" + cause.getMessage());
}
}
サーバ側起動
public class NettyServer {
public static void main(String[] args) {
new NettyServer().bing(7397);
}
private void bing(int port) {
// NIO
EventLoopGroup parentGroup = new NioEventLoopGroup(); //NioEventLoopGroup extends MultithreadEventLoopGroup Math.max(1, SystemPropertyUtil.getInt("io.netty.eventLoopThreads", NettyRuntime.availableProcessors() * 2));
EventLoopGroup childGroup = new NioEventLoopGroup();
try {
ServerBootstrap b = new ServerBootstrap();
b.group(parentGroup, childGroup)
.channel(NioServerSocketChannel.class) //
.option(ChannelOption.SO_BACKLOG, 128)
.childHandler(new ServerChannelInitializer());
// , .
ChannelFuture f = b.bind(port).sync();
System.out.println("netty server start done wait conn...");
boolean flag=true;
while (flag) {
//
Scanner src = new Scanner(System.in);
String str = src.nextLine();
Channel channel= MyServerHandler.channelList.get("1");
channel.writeAndFlush(str);
if("byebye".equals(str)){
f.channel().close();
break;
}
}
//
f.channel().closeFuture().sync();
} catch (InterruptedException e) {
e.printStackTrace();
} finally {
childGroup.shutdownGracefully();
parentGroup.shutdownGracefully();
}
}
}
クライアント
public class NettyClient {
public static void main(String[] args) throws InterruptedException {
EventLoopGroup group = new NioEventLoopGroup();
// NioEventLoopGroup group = new NioEventLoopGroup();
try{
Bootstrap bootstrap = new Bootstrap();
bootstrap.group(group)
.channel(NioSocketChannel.class)
.handler(new ChannelInitializer() {
@Override
protected void initChannel(Channel ch) {
// ch.pipeline().addLast(new LineBasedFrameDecoder(1024));
ch.pipeline().addLast(new StringDecoder(Charset.forName("GBK")));
// String, GBK、UTF-8
ch.pipeline().addLast(new StringEncoder(Charset.forName("GBK")));
ch.pipeline().addLast(new ClientHandler());
}
});
ChannelFuture future = bootstrap.connect("127.0.0.1", 7397).sync();
boolean flag=true;
while (flag) {
//
Scanner src = new Scanner(System.in);
String str = src.nextLine();
future.channel().writeAndFlush(str);
if("bye".equals(str)){
future.channel().close();
break;
}
}
future.channel().closeFuture().sync();
}finally {
group.spliterator();
}
}
クライアントコールバック処理
public class ClientHandler extends SimpleChannelInboundHandler {
/**
* , 。
*/
@Override
public void channelActive(ChannelHandlerContext ctx) throws Exception {
SocketChannel channel = (SocketChannel) ctx.channel();
//
// String str = " " + " " + new Date() + " " + channel.localAddress().getHostString() + "\r
";
System.out.println(" ");
ctx.writeAndFlush("");
}
/**
* , 。
*/
@Override
public void channelInactive(ChannelHandlerContext ctx) throws Exception {
System.out.println(" " + ctx.channel().localAddress().toString());
}
@Override
public void channelRead0(ChannelHandlerContext ctx, Object msg) throws Exception {
// msg { , }
System.out.println( "server:" + msg);
// { ByteBuf, }
String str = "-- --" + "\r
";
ctx.writeAndFlush(str);
}
/**
* , , , 、
*/
@Override
public void exceptionCaught(ChannelHandlerContext ctx, Throwable cause) throws Exception {
ctx.close();
System.out.println(" :\r
" + cause.getMessage());
}
}