1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20 package org.apache.mina.filter.keepalive;
21
22 import static org.apache.mina.filter.keepalive.KeepAliveRequestTimeoutHandler.*;
23
24 import java.net.InetSocketAddress;
25 import java.util.concurrent.atomic.AtomicBoolean;
26
27 import junit.framework.TestCase;
28
29 import org.apache.mina.core.buffer.IoBuffer;
30 import org.apache.mina.core.future.ConnectFuture;
31 import org.apache.mina.core.service.IoHandlerAdapter;
32 import org.apache.mina.core.session.IdleStatus;
33 import org.apache.mina.core.session.IoSession;
34 import org.apache.mina.transport.socket.nio.NioSocketAcceptor;
35 import org.apache.mina.transport.socket.nio.NioSocketConnector;
36
37
38
39
40
41
42
43
44 public class KeepAliveFilterTest extends TestCase {
45
46
47 private static final IoBuffer PING = IoBuffer.wrap(new byte[] { 1 });
48 private static final IoBuffer PONG = IoBuffer.wrap(new byte[] { 2 });
49 private static final int INTERVAL = 2;
50 private static final int TIMEOUT = 1;
51
52 private int port;
53 private NioSocketAcceptor acceptor;
54
55 @Override
56 protected void setUp() throws Exception {
57 super.setUp();
58
59 acceptor = new NioSocketAcceptor();
60 KeepAliveMessageFactory factory = new ServerFactory();
61 KeepAliveFilter filter = new KeepAliveFilter(factory,
62 IdleStatus.BOTH_IDLE);
63 acceptor.getFilterChain().addLast("keep-alive", filter);
64 acceptor.setHandler(new IoHandlerAdapter());
65 acceptor.setDefaultLocalAddress(new InetSocketAddress(0));
66 acceptor.bind();
67 port = acceptor.getLocalAddress().getPort();
68 }
69
70 @Override
71 protected void tearDown() throws Exception {
72 acceptor.unbind();
73 acceptor.dispose();
74 super.tearDown();
75 }
76
77 public void testKeepAliveFilterForReaderIdle() throws Exception {
78 keepAliveFilterForIdleStatus(IdleStatus.READER_IDLE);
79 }
80
81 public void testKeepAliveFilterForBothIdle() throws Exception {
82 keepAliveFilterForIdleStatus(IdleStatus.BOTH_IDLE);
83 }
84
85 public void testKeepAliveFilterForWriterIdle() throws Exception {
86 keepAliveFilterForIdleStatus(IdleStatus.WRITER_IDLE);
87 }
88
89
90
91
92
93
94
95 private void keepAliveFilterForIdleStatus(IdleStatus status)
96 throws Exception {
97 NioSocketConnector connector = new NioSocketConnector();
98 KeepAliveFilter filter = new KeepAliveFilter(new ClientFactory(),
99 status, EXCEPTION, INTERVAL, TIMEOUT);
100 filter.setForwardEvent(true);
101 connector.getFilterChain().addLast("keep-alive", filter);
102
103 final AtomicBoolean gotException = new AtomicBoolean(false);
104 connector.setHandler(new IoHandlerAdapter() {
105 @Override
106 public void exceptionCaught(IoSession session, Throwable cause)
107 throws Exception {
108
109 gotException.set(true);
110 }
111
112 @Override
113 public void sessionIdle(IoSession session, IdleStatus status)
114 throws Exception {
115
116 }
117 });
118
119 ConnectFuture future = connector.connect(
120 new InetSocketAddress("127.0.0.1", port)).awaitUninterruptibly();
121 IoSession session = future.getSession();
122 assertNotNull(session);
123
124 Thread.sleep((INTERVAL + TIMEOUT + 1) * 1000);
125
126 assertFalse("got an exception on the client", gotException.get());
127
128 session.close(true);
129 connector.dispose();
130 }
131
132 private static boolean checkRequest(IoBuffer message) {
133 IoBuffer buff = message;
134 boolean check = buff.get() == 1;
135 buff.rewind();
136 return check;
137 }
138
139 private static boolean checkResponse(IoBuffer message) {
140 IoBuffer buff = message;
141 boolean check = buff.get() == 2;
142 buff.rewind();
143 return check;
144 }
145
146
147
148 private final class ServerFactory implements KeepAliveMessageFactory {
149 public Object getRequest(IoSession session) {
150 return null;
151 }
152
153 public Object getResponse(IoSession session, Object request) {
154 return PONG.duplicate();
155 }
156
157 public boolean isRequest(IoSession session, Object message) {
158 if (message instanceof IoBuffer) {
159 return checkRequest((IoBuffer) message);
160 }
161 return false;
162 }
163
164 public boolean isResponse(IoSession session, Object message) {
165 if (message instanceof IoBuffer) {
166 return checkResponse((IoBuffer) message);
167 }
168 return false;
169 }
170 }
171
172 private final class ClientFactory implements KeepAliveMessageFactory {
173 public Object getRequest(IoSession session) {
174 return PING.duplicate();
175 }
176
177 public Object getResponse(IoSession session, Object request) {
178 return null;
179 }
180
181 public boolean isRequest(IoSession session, Object message) {
182 if (message instanceof IoBuffer) {
183 return checkRequest((IoBuffer) message);
184 }
185 return false;
186 }
187
188 public boolean isResponse(IoSession session, Object message) {
189 if (message instanceof IoBuffer) {
190 return checkResponse((IoBuffer) message);
191 }
192 return false;
193 }
194 }
195 }