MINA2.0 实例--TimeServer(一)

2014-11-24 10:11:59 · 作者: · 浏览: 0

MINA(Multipurpose Infrastructure for Network Applications) 是 Apache 组织一个开源Java项目,她是一个Java网络应用程序开发框架,借助她,Java开发者能够简洁的开发出发高性能和高可用的网络应用程序。她依赖于Java NIO,提供了一套便捷操作诸如TCP/IP和UDP/IP等各种传输协议的、抽象的、事件驱动的和异步的API。

Apache MINA is a network application framework which helps users develop high performance and high scalability network applications easily. It provides an abstract ·event-driven · asynchronous API over various transports such as TCP/IP and UDP/IP via Java NIO.

这个例子来自MINA的官网gettingstarted,也就是Hello级别的例子,本文在其基础上,进一步简化和修改;该实例的运行基础是MINA 2.0.7,MINA 2.*依赖于JDK1.5+,因此JDK版本也要是1.5+,其中引用的jar包有如下两个:mina-core-2.0.7.jar和slf4j-api-1.6.6.jar,mima-core是mina的核心包,她又依赖于slf4j-api,因此,两个包是程序不报错的最低最低的限度,创建一个类(通常也都是创建两个)SimpleTimeServerHandler.java,这里为了更简单,代码如下:


[java]
import java.io.IOException;
import java.net.InetSocketAddress;
import java.nio.charset.Charset;
import java.text.SimpleDateFormat;

import org.apache.mina.core.service.IoAcceptor;
import org.apache.mina.core.service.IoHandlerAdapter;
import org.apache.mina.core.session.IoSession;
import org.apache.mina.filter.codec.ProtocolCodecFilter;
import org.apache.mina.filter.codec.textline.TextLineCodecFactory;
import org.apache.mina.transport.socket.nio.NioSocketAcceptor;

public class SimpleTimeServerHandler extends IoHandlerAdapter{

@Override
public void messageReceived(IoSession session, Object message){
//服务器端打印出请求的来源
System.out.println("Request From:" + session.getRemoteAddress());
//返给客户端的消息内容:服务器系统当前时间
session.write("Server Time: "+new SimpleDateFormat("yyyy-MM-dd HH:mm:ss").format(System.currentTimeMillis()));
}

public static void main(String[] args) throws IOException{
//创建一个接收器,接收客户端请求
IoAcceptor acceptor = new NioSocketAcceptor();

//Don't know how to handle message of type 'java.lang.String'. Are you missing a protocol encoder
//编码过滤器,使得服务器可以处理string类型的消息
acceptor.getFilterChain().addLast("codec",
new ProtocolCodecFilter(new TextLineCodecFactory(Charset.forName("UTF-8"))));

//设置服务器端的处理程序
acceptor.setHandler(new SimpleTimeServerHandler());
acceptor.bind(new InetSocketAddress(60001));
}
}
直接编译执行该类,则启动了服务器,端口是60001。客户端使用最简单的,windows下使用cmd进入控制台(Windows 7默认没有开启该客户端,需要通过“控制面板->程序->程序和功能->打开或关闭Windows功能”,选择“Telnet服务器”和“Telnet客户端”来安装),通过“telnet 127.0.0.1 60001”访问服务器,然后随便输入或者不输入内容,点击回车,即可连接到服务器获取服务器端的时间,而服务器端也可以打印出监控到的客户端的地址;这里可以多开几个cmd窗口,通过telnet进行连接,可以发现不同的窗口对于服务器来说是不同的session。本例在本机和另外一台机器上各开启了一个来进行测试:
客户端的两个:

第一个本机的:

第二个另一台机器:

服务器端打印为:


可以看到服务器端是收到了来自不同的客户端的请求(本机开启两个CMD窗口也可以通过端口号来区分不同的客户端)。

简单解释:

1). 服务器端业务处理者继承IoHandlerAdapter,override其messageReceived(IoSession session, Object message)方法,来完成实际的操作,在本例中做了两家事:第一,在服务器端控制台打印出请求的来源:System.out.println("Request From:" + session.getRemoteAddress()); 第二,给请求的客户端返回系统当前时间:session.write("Server Time: "+new SimpleDateFormat("yyyy-MM-dd HH:mm:ss").format(System.currentTimeMillis()))。

2). 服务器启动Main方法做了三件事:创建一个接收器,接收客户端请求;添加编码过滤器,使得服务器可以对特定编码进行处理,本例是对String字符串进行处理,如果不设置这个编码过滤器,则会报错“Don't know how to handle message of type 'java.lang.String'. A