Migrate transport to junit5 (#11431) (#11432)

Motivation:

We should update to use junit5 in all modules.

Modifications:

Adjust transport tests to use junit5

Result:

Part of https://github.com/netty/netty/issues/10757
This commit is contained in:
Norman Maurer 2021-06-30 16:17:57 +02:00 committed by GitHub
parent 94a4880358
commit 8d76f402b1
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
8 changed files with 201 additions and 165 deletions

View File

@ -25,12 +25,13 @@ import io.netty.util.concurrent.EventExecutor;
import io.netty.util.concurrent.GlobalEventExecutor; import io.netty.util.concurrent.GlobalEventExecutor;
import io.netty.util.concurrent.Promise; import io.netty.util.concurrent.Promise;
import io.netty.util.concurrent.SingleThreadEventExecutor; import io.netty.util.concurrent.SingleThreadEventExecutor;
import org.junit.Test; import org.junit.jupiter.api.Test;
import java.lang.reflect.Field; import java.lang.reflect.Field;
import java.util.concurrent.TimeUnit; import java.util.concurrent.TimeUnit;
import static org.junit.Assert.*; import static org.junit.jupiter.api.Assertions.assertNull;
import static org.junit.jupiter.api.Assertions.assertTrue;
public class ThreadPerChannelEventLoopGroupTest { public class ThreadPerChannelEventLoopGroupTest {

View File

@ -30,24 +30,30 @@ import io.netty.util.ReferenceCountUtil;
import io.netty.util.concurrent.DefaultEventExecutorGroup; import io.netty.util.concurrent.DefaultEventExecutorGroup;
import io.netty.util.concurrent.DefaultThreadFactory; import io.netty.util.concurrent.DefaultThreadFactory;
import io.netty.util.concurrent.EventExecutorGroup; import io.netty.util.concurrent.EventExecutorGroup;
import org.junit.AfterClass; import org.junit.jupiter.api.AfterAll;
import org.junit.Assert; import org.junit.jupiter.api.BeforeAll;
import org.junit.BeforeClass; import org.junit.jupiter.api.Disabled;
import org.junit.Ignore; import org.junit.jupiter.api.Test;
import org.junit.Test; import org.junit.jupiter.api.Timeout;
import java.util.HashSet; import java.util.HashSet;
import java.util.Queue; import java.util.Queue;
import java.util.Set; import java.util.Set;
import java.util.concurrent.ConcurrentLinkedQueue; import java.util.concurrent.ConcurrentLinkedQueue;
import java.util.concurrent.TimeUnit;
import java.util.concurrent.atomic.AtomicReference; import java.util.concurrent.atomic.AtomicReference;
import static org.junit.jupiter.api.Assertions.assertEquals;
import static org.junit.jupiter.api.Assertions.assertFalse;
import static org.junit.jupiter.api.Assertions.assertSame;
import static org.junit.jupiter.api.Assertions.assertTrue;
public class LocalTransportThreadModelTest { public class LocalTransportThreadModelTest {
private static EventLoopGroup group; private static EventLoopGroup group;
private static LocalAddress localAddr; private static LocalAddress localAddr;
@BeforeClass @BeforeAll
public static void init() { public static void init() {
// Configure a test server // Configure a test server
group = new DefaultEventLoopGroup(); group = new DefaultEventLoopGroup();
@ -70,20 +76,22 @@ public class LocalTransportThreadModelTest {
localAddr = (LocalAddress) sb.bind(LocalAddress.ANY).syncUninterruptibly().channel().localAddress(); localAddr = (LocalAddress) sb.bind(LocalAddress.ANY).syncUninterruptibly().channel().localAddress();
} }
@AfterClass @AfterAll
public static void destroy() throws Exception { public static void destroy() throws Exception {
group.shutdownGracefully().sync(); group.shutdownGracefully().sync();
} }
@Test(timeout = 30000) @Test
@Ignore("regression test") @Timeout(value = 30000, unit = TimeUnit.MILLISECONDS)
@Disabled("regression test")
public void testStagedExecutionMultiple() throws Throwable { public void testStagedExecutionMultiple() throws Throwable {
for (int i = 0; i < 10; i ++) { for (int i = 0; i < 10; i ++) {
testStagedExecution(); testStagedExecution();
} }
} }
@Test(timeout = 5000) @Test
@Timeout(value = 5000, unit = TimeUnit.MILLISECONDS)
public void testStagedExecution() throws Throwable { public void testStagedExecution() throws Throwable {
EventLoopGroup l = new DefaultEventLoopGroup(4, new DefaultThreadFactory("l")); EventLoopGroup l = new DefaultEventLoopGroup(4, new DefaultThreadFactory("l"));
EventExecutorGroup e1 = new DefaultEventExecutorGroup(4, new DefaultThreadFactory("e1")); EventExecutorGroup e1 = new DefaultEventExecutorGroup(4, new DefaultThreadFactory("e1"));
@ -135,43 +143,43 @@ public class LocalTransportThreadModelTest {
try { try {
// Events should never be handled from the current thread. // Events should never be handled from the current thread.
Assert.assertFalse(h1.inboundThreadNames.contains(currentName)); assertFalse(h1.inboundThreadNames.contains(currentName));
Assert.assertFalse(h2.inboundThreadNames.contains(currentName)); assertFalse(h2.inboundThreadNames.contains(currentName));
Assert.assertFalse(h3.inboundThreadNames.contains(currentName)); assertFalse(h3.inboundThreadNames.contains(currentName));
Assert.assertFalse(h1.outboundThreadNames.contains(currentName)); assertFalse(h1.outboundThreadNames.contains(currentName));
Assert.assertFalse(h2.outboundThreadNames.contains(currentName)); assertFalse(h2.outboundThreadNames.contains(currentName));
Assert.assertFalse(h3.outboundThreadNames.contains(currentName)); assertFalse(h3.outboundThreadNames.contains(currentName));
Assert.assertFalse(h1.removalThreadNames.contains(currentName)); assertFalse(h1.removalThreadNames.contains(currentName));
Assert.assertFalse(h2.removalThreadNames.contains(currentName)); assertFalse(h2.removalThreadNames.contains(currentName));
Assert.assertFalse(h3.removalThreadNames.contains(currentName)); assertFalse(h3.removalThreadNames.contains(currentName));
// Assert that events were handled by the correct executor. // Assert that events were handled by the correct executor.
for (String name: h1.inboundThreadNames) { for (String name: h1.inboundThreadNames) {
Assert.assertTrue(name.startsWith("l-")); assertTrue(name.startsWith("l-"));
} }
for (String name: h2.inboundThreadNames) { for (String name: h2.inboundThreadNames) {
Assert.assertTrue(name.startsWith("e1-")); assertTrue(name.startsWith("e1-"));
} }
for (String name: h3.inboundThreadNames) { for (String name: h3.inboundThreadNames) {
Assert.assertTrue(name.startsWith("e2-")); assertTrue(name.startsWith("e2-"));
} }
for (String name: h1.outboundThreadNames) { for (String name: h1.outboundThreadNames) {
Assert.assertTrue(name.startsWith("l-")); assertTrue(name.startsWith("l-"));
} }
for (String name: h2.outboundThreadNames) { for (String name: h2.outboundThreadNames) {
Assert.assertTrue(name.startsWith("e1-")); assertTrue(name.startsWith("e1-"));
} }
for (String name: h3.outboundThreadNames) { for (String name: h3.outboundThreadNames) {
Assert.assertTrue(name.startsWith("e2-")); assertTrue(name.startsWith("e2-"));
} }
for (String name: h1.removalThreadNames) { for (String name: h1.removalThreadNames) {
Assert.assertTrue(name.startsWith("l-")); assertTrue(name.startsWith("l-"));
} }
for (String name: h2.removalThreadNames) { for (String name: h2.removalThreadNames) {
Assert.assertTrue(name.startsWith("e1-")); assertTrue(name.startsWith("e1-"));
} }
for (String name: h3.removalThreadNames) { for (String name: h3.removalThreadNames) {
Assert.assertTrue(name.startsWith("e2-")); assertTrue(name.startsWith("e2-"));
} }
// Assert that the events for the same handler were handled by the same thread. // Assert that the events for the same handler were handled by the same thread.
@ -179,30 +187,30 @@ public class LocalTransportThreadModelTest {
names.addAll(h1.inboundThreadNames); names.addAll(h1.inboundThreadNames);
names.addAll(h1.outboundThreadNames); names.addAll(h1.outboundThreadNames);
names.addAll(h1.removalThreadNames); names.addAll(h1.removalThreadNames);
Assert.assertEquals(1, names.size()); assertEquals(1, names.size());
names.clear(); names.clear();
names.addAll(h2.inboundThreadNames); names.addAll(h2.inboundThreadNames);
names.addAll(h2.outboundThreadNames); names.addAll(h2.outboundThreadNames);
names.addAll(h2.removalThreadNames); names.addAll(h2.removalThreadNames);
Assert.assertEquals(1, names.size()); assertEquals(1, names.size());
names.clear(); names.clear();
names.addAll(h3.inboundThreadNames); names.addAll(h3.inboundThreadNames);
names.addAll(h3.outboundThreadNames); names.addAll(h3.outboundThreadNames);
names.addAll(h3.removalThreadNames); names.addAll(h3.removalThreadNames);
Assert.assertEquals(1, names.size()); assertEquals(1, names.size());
// Count the number of events // Count the number of events
Assert.assertEquals(1, h1.inboundThreadNames.size()); assertEquals(1, h1.inboundThreadNames.size());
Assert.assertEquals(2, h2.inboundThreadNames.size()); assertEquals(2, h2.inboundThreadNames.size());
Assert.assertEquals(3, h3.inboundThreadNames.size()); assertEquals(3, h3.inboundThreadNames.size());
Assert.assertEquals(3, h1.outboundThreadNames.size()); assertEquals(3, h1.outboundThreadNames.size());
Assert.assertEquals(2, h2.outboundThreadNames.size()); assertEquals(2, h2.outboundThreadNames.size());
Assert.assertEquals(1, h3.outboundThreadNames.size()); assertEquals(1, h3.outboundThreadNames.size());
Assert.assertEquals(1, h1.removalThreadNames.size()); assertEquals(1, h1.removalThreadNames.size());
Assert.assertEquals(1, h2.removalThreadNames.size()); assertEquals(1, h2.removalThreadNames.size());
Assert.assertEquals(1, h3.removalThreadNames.size()); assertEquals(1, h3.removalThreadNames.size());
} catch (AssertionError e) { } catch (AssertionError e) {
System.out.println("H1I: " + h1.inboundThreadNames); System.out.println("H1I: " + h1.inboundThreadNames);
System.out.println("H2I: " + h2.inboundThreadNames); System.out.println("H2I: " + h2.inboundThreadNames);
@ -225,8 +233,9 @@ public class LocalTransportThreadModelTest {
} }
} }
@Test(timeout = 30000) @Test
@Ignore @Timeout(value = 30000, unit = TimeUnit.MILLISECONDS)
@Disabled
public void testConcurrentMessageBufferAccess() throws Throwable { public void testConcurrentMessageBufferAccess() throws Throwable {
EventLoopGroup l = new DefaultEventLoopGroup(4, new DefaultThreadFactory("l")); EventLoopGroup l = new DefaultEventLoopGroup(4, new DefaultThreadFactory("l"));
EventExecutorGroup e1 = new DefaultEventExecutorGroup(4, new DefaultThreadFactory("e1")); EventExecutorGroup e1 = new DefaultEventExecutorGroup(4, new DefaultThreadFactory("e1"));
@ -415,13 +424,13 @@ public class LocalTransportThreadModelTest {
if (t == null) { if (t == null) {
this.t = Thread.currentThread(); this.t = Thread.currentThread();
} else { } else {
Assert.assertSame(t, Thread.currentThread()); assertSame(t, Thread.currentThread());
} }
ByteBuf out = ctx.alloc().buffer(4); ByteBuf out = ctx.alloc().buffer(4);
int m = ((Integer) msg).intValue(); int m = ((Integer) msg).intValue();
int expected = inCnt ++; int expected = inCnt ++;
Assert.assertEquals(expected, m); assertEquals(expected, m);
out.writeInt(m); out.writeInt(m);
ctx.fireChannelRead(out); ctx.fireChannelRead(out);
@ -429,7 +438,7 @@ public class LocalTransportThreadModelTest {
@Override @Override
public void write(ChannelHandlerContext ctx, Object msg, ChannelPromise promise) throws Exception { public void write(ChannelHandlerContext ctx, Object msg, ChannelPromise promise) throws Exception {
Assert.assertSame(t, Thread.currentThread()); assertSame(t, Thread.currentThread());
// Don't let the write request go to the server-side channel - just swallow. // Don't let the write request go to the server-side channel - just swallow.
boolean swallow = this == ctx.pipeline().first(); boolean swallow = this == ctx.pipeline().first();
@ -439,7 +448,7 @@ public class LocalTransportThreadModelTest {
for (int j = 0; j < count; j ++) { for (int j = 0; j < count; j ++) {
int actual = m.readInt(); int actual = m.readInt();
int expected = outCnt ++; int expected = outCnt ++;
Assert.assertEquals(expected, actual); assertEquals(expected, actual);
if (!swallow) { if (!swallow) {
ctx.write(actual); ctx.write(actual);
} }
@ -473,7 +482,7 @@ public class LocalTransportThreadModelTest {
if (t == null) { if (t == null) {
this.t = Thread.currentThread(); this.t = Thread.currentThread();
} else { } else {
Assert.assertSame(t, Thread.currentThread()); assertSame(t, Thread.currentThread());
} }
ByteBuf m = (ByteBuf) msg; ByteBuf m = (ByteBuf) msg;
@ -481,7 +490,7 @@ public class LocalTransportThreadModelTest {
for (int j = 0; j < count; j ++) { for (int j = 0; j < count; j ++) {
int actual = m.readInt(); int actual = m.readInt();
int expected = inCnt ++; int expected = inCnt ++;
Assert.assertEquals(expected, actual); assertEquals(expected, actual);
ctx.fireChannelRead(actual); ctx.fireChannelRead(actual);
} }
m.release(); m.release();
@ -489,12 +498,12 @@ public class LocalTransportThreadModelTest {
@Override @Override
public void write(ChannelHandlerContext ctx, Object msg, ChannelPromise promise) throws Exception { public void write(ChannelHandlerContext ctx, Object msg, ChannelPromise promise) throws Exception {
Assert.assertSame(t, Thread.currentThread()); assertSame(t, Thread.currentThread());
ByteBuf out = ctx.alloc().buffer(4); ByteBuf out = ctx.alloc().buffer(4);
int m = (Integer) msg; int m = (Integer) msg;
int expected = outCnt ++; int expected = outCnt ++;
Assert.assertEquals(expected, m); assertEquals(expected, m);
out.writeInt(m); out.writeInt(m);
ctx.write(out, promise); ctx.write(out, promise);
@ -525,23 +534,23 @@ public class LocalTransportThreadModelTest {
if (t == null) { if (t == null) {
this.t = Thread.currentThread(); this.t = Thread.currentThread();
} else { } else {
Assert.assertSame(t, Thread.currentThread()); assertSame(t, Thread.currentThread());
} }
int actual = (Integer) msg; int actual = (Integer) msg;
int expected = inCnt ++; int expected = inCnt ++;
Assert.assertEquals(expected, actual); assertEquals(expected, actual);
ctx.fireChannelRead(msg); ctx.fireChannelRead(msg);
} }
@Override @Override
public void write(ChannelHandlerContext ctx, Object msg, ChannelPromise promise) throws Exception { public void write(ChannelHandlerContext ctx, Object msg, ChannelPromise promise) throws Exception {
Assert.assertSame(t, Thread.currentThread()); assertSame(t, Thread.currentThread());
int actual = (Integer) msg; int actual = (Integer) msg;
int expected = outCnt ++; int expected = outCnt ++;
Assert.assertEquals(expected, actual); assertEquals(expected, actual);
ctx.write(msg, promise); ctx.write(msg, promise);
} }
@ -571,22 +580,22 @@ public class LocalTransportThreadModelTest {
if (t == null) { if (t == null) {
this.t = Thread.currentThread(); this.t = Thread.currentThread();
} else { } else {
Assert.assertSame(t, Thread.currentThread()); assertSame(t, Thread.currentThread());
} }
int actual = (Integer) msg; int actual = (Integer) msg;
int expected = inCnt ++; int expected = inCnt ++;
Assert.assertEquals(expected, actual); assertEquals(expected, actual);
} }
@Override @Override
public void write( public void write(
ChannelHandlerContext ctx, Object msg, ChannelPromise promise) throws Exception { ChannelHandlerContext ctx, Object msg, ChannelPromise promise) throws Exception {
Assert.assertSame(t, Thread.currentThread()); assertSame(t, Thread.currentThread());
int actual = (Integer) msg; int actual = (Integer) msg;
int expected = outCnt ++; int expected = outCnt ++;
Assert.assertEquals(expected, actual); assertEquals(expected, actual);
ctx.write(msg, promise); ctx.write(msg, promise);
} }

View File

@ -29,11 +29,11 @@ import io.netty.util.ReferenceCountUtil;
import io.netty.util.concurrent.DefaultEventExecutorGroup; import io.netty.util.concurrent.DefaultEventExecutorGroup;
import io.netty.util.concurrent.DefaultThreadFactory; import io.netty.util.concurrent.DefaultThreadFactory;
import io.netty.util.concurrent.EventExecutorGroup; import io.netty.util.concurrent.EventExecutorGroup;
import org.junit.AfterClass; import org.junit.jupiter.api.AfterAll;
import org.junit.Assert; import org.junit.jupiter.api.BeforeAll;
import org.junit.BeforeClass; import org.junit.jupiter.api.Disabled;
import org.junit.Ignore; import org.junit.jupiter.api.Test;
import org.junit.Test; import org.junit.jupiter.api.Timeout;
import java.util.Deque; import java.util.Deque;
import java.util.LinkedList; import java.util.LinkedList;
@ -41,6 +41,10 @@ import java.util.Queue;
import java.util.Random; import java.util.Random;
import java.util.UUID; import java.util.UUID;
import java.util.concurrent.ConcurrentLinkedDeque; import java.util.concurrent.ConcurrentLinkedDeque;
import java.util.concurrent.TimeUnit;
import static org.junit.jupiter.api.Assertions.assertEquals;
import static org.junit.jupiter.api.Assertions.assertTrue;
public class LocalTransportThreadModelTest3 { public class LocalTransportThreadModelTest3 {
@ -60,7 +64,7 @@ public class LocalTransportThreadModelTest3 {
private static EventLoopGroup group; private static EventLoopGroup group;
private static LocalAddress localAddr; private static LocalAddress localAddr;
@BeforeClass @BeforeAll
public static void init() { public static void init() {
// Configure a test server // Configure a test server
group = new DefaultEventLoopGroup(); group = new DefaultEventLoopGroup();
@ -83,35 +87,39 @@ public class LocalTransportThreadModelTest3 {
localAddr = (LocalAddress) sb.bind(LocalAddress.ANY).syncUninterruptibly().channel().localAddress(); localAddr = (LocalAddress) sb.bind(LocalAddress.ANY).syncUninterruptibly().channel().localAddress();
} }
@AfterClass @AfterAll
public static void destroy() throws Exception { public static void destroy() throws Exception {
group.shutdownGracefully().sync(); group.shutdownGracefully().sync();
} }
@Test(timeout = 60000) @Test
@Ignore("regression test") @Timeout(value = 60000, unit = TimeUnit.MILLISECONDS)
@Disabled("regression test")
public void testConcurrentAddRemoveInboundEventsMultiple() throws Throwable { public void testConcurrentAddRemoveInboundEventsMultiple() throws Throwable {
for (int i = 0; i < 50; i ++) { for (int i = 0; i < 50; i ++) {
testConcurrentAddRemoveInboundEvents(); testConcurrentAddRemoveInboundEvents();
} }
} }
@Test(timeout = 60000) @Test
@Ignore("regression test") @Timeout(value = 60000, unit = TimeUnit.MILLISECONDS)
@Disabled("regression test")
public void testConcurrentAddRemoveOutboundEventsMultiple() throws Throwable { public void testConcurrentAddRemoveOutboundEventsMultiple() throws Throwable {
for (int i = 0; i < 50; i ++) { for (int i = 0; i < 50; i ++) {
testConcurrentAddRemoveOutboundEvents(); testConcurrentAddRemoveOutboundEvents();
} }
} }
@Test(timeout = 30000) @Test
@Ignore("needs a fix") @Timeout(value = 30000, unit = TimeUnit.MILLISECONDS)
@Disabled("needs a fix")
public void testConcurrentAddRemoveInboundEvents() throws Throwable { public void testConcurrentAddRemoveInboundEvents() throws Throwable {
testConcurrentAddRemove(true); testConcurrentAddRemove(true);
} }
@Test(timeout = 30000) @Test
@Ignore("needs a fix") @Timeout(value = 30000, unit = TimeUnit.MILLISECONDS)
@Disabled("needs a fix")
public void testConcurrentAddRemoveOutboundEvents() throws Throwable { public void testConcurrentAddRemoveOutboundEvents() throws Throwable {
testConcurrentAddRemove(false); testConcurrentAddRemove(false);
} }
@ -211,10 +219,10 @@ public class LocalTransportThreadModelTest3 {
for (;;) { for (;;) {
EventType event = events.poll(); EventType event = events.poll();
if (event == null) { if (event == null) {
Assert.assertTrue("Missing events:" + expectedEvents, expectedEvents.isEmpty()); assertTrue(expectedEvents.isEmpty(), "Missing events:" + expectedEvents);
break; break;
} }
Assert.assertEquals(event, expectedEvents.poll()); assertEquals(event, expectedEvents.poll());
} }
} finally { } finally {
l.shutdownGracefully(); l.shutdownGracefully();

View File

@ -26,13 +26,15 @@ import io.netty.channel.EventLoopGroup;
import io.netty.channel.socket.oio.OioServerSocketChannel; import io.netty.channel.socket.oio.OioServerSocketChannel;
import io.netty.channel.socket.oio.OioSocketChannel; import io.netty.channel.socket.oio.OioSocketChannel;
import io.netty.util.NetUtil; import io.netty.util.NetUtil;
import org.junit.Test; import org.junit.jupiter.api.Test;
import java.net.InetSocketAddress; import java.net.InetSocketAddress;
import java.net.Socket; import java.net.Socket;
import java.util.concurrent.CountDownLatch; import java.util.concurrent.CountDownLatch;
import static org.hamcrest.CoreMatchers.*; import static org.hamcrest.CoreMatchers.containsString;
import static org.hamcrest.CoreMatchers.instanceOf;
import static org.hamcrest.CoreMatchers.is;
import static org.hamcrest.MatcherAssert.assertThat; import static org.hamcrest.MatcherAssert.assertThat;
public class OioEventLoopTest { public class OioEventLoopTest {

View File

@ -26,19 +26,22 @@ import io.netty.util.concurrent.EventExecutor;
import io.netty.util.concurrent.Future; import io.netty.util.concurrent.Future;
import io.netty.util.concurrent.GenericFutureListener; import io.netty.util.concurrent.GenericFutureListener;
import io.netty.util.concurrent.Promise; import io.netty.util.concurrent.Promise;
import org.junit.Test; import org.junit.jupiter.api.Test;
import org.junit.jupiter.api.function.Executable;
import java.net.ConnectException; import java.net.ConnectException;
import java.util.concurrent.TimeUnit; import java.util.concurrent.TimeUnit;
import static io.netty.channel.pool.ChannelPoolTestUtils.getLocalAddrId; import static io.netty.channel.pool.ChannelPoolTestUtils.getLocalAddrId;
import static org.junit.Assert.assertEquals;
import static org.junit.Assert.assertFalse; import static org.junit.jupiter.api.Assertions.assertEquals;
import static org.junit.Assert.assertSame; import static org.junit.jupiter.api.Assertions.assertFalse;
import static org.junit.Assert.assertTrue; import static org.junit.jupiter.api.Assertions.assertSame;
import static org.junit.jupiter.api.Assertions.assertThrows;
import static org.junit.jupiter.api.Assertions.assertTrue;
public class AbstractChannelPoolMapTest { public class AbstractChannelPoolMapTest {
@Test(expected = ConnectException.class) @Test
public void testMap() throws Exception { public void testMap() throws Exception {
EventLoopGroup group = new LocalEventLoopGroup(); EventLoopGroup group = new LocalEventLoopGroup();
LocalAddress addr = new LocalAddress(getLocalAddrId()); LocalAddress addr = new LocalAddress(getLocalAddrId());
@ -60,7 +63,7 @@ public class AbstractChannelPoolMapTest {
assertFalse(poolMap.iterator().hasNext()); assertFalse(poolMap.iterator().hasNext());
assertEquals(0, poolMap.size()); assertEquals(0, poolMap.size());
SimpleChannelPool pool = poolMap.get(loop); final SimpleChannelPool pool = poolMap.get(loop);
assertEquals(1, poolMap.size()); assertEquals(1, poolMap.size());
assertTrue(poolMap.iterator().hasNext()); assertTrue(poolMap.iterator().hasNext());
@ -71,7 +74,12 @@ public class AbstractChannelPoolMapTest {
assertFalse(poolMap.iterator().hasNext()); assertFalse(poolMap.iterator().hasNext());
assertEquals(0, poolMap.size()); assertEquals(0, poolMap.size());
assertThrows(ConnectException.class, new Executable() {
@Override
public void execute() throws Throwable {
pool.acquire().syncUninterruptibly(); pool.acquire().syncUninterruptibly();
}
});
poolMap.close(); poolMap.close();
} }

View File

@ -23,14 +23,14 @@ import io.netty.channel.EventLoop;
import io.netty.channel.local.LocalAddress; import io.netty.channel.local.LocalAddress;
import io.netty.channel.local.LocalChannel; import io.netty.channel.local.LocalChannel;
import io.netty.util.concurrent.Future; import io.netty.util.concurrent.Future;
import org.junit.Test; import org.junit.jupiter.api.Test;
import java.util.concurrent.Callable; import java.util.concurrent.Callable;
import java.util.concurrent.CyclicBarrier; import java.util.concurrent.CyclicBarrier;
import java.util.concurrent.TimeUnit; import java.util.concurrent.TimeUnit;
import java.util.concurrent.TimeoutException; import java.util.concurrent.TimeoutException;
import static org.junit.Assert.*; import static org.junit.jupiter.api.Assertions.assertSame;
/** /**
* This is a test case for the deadlock scenario described in https://github.com/netty/netty/issues/8238. * This is a test case for the deadlock scenario described in https://github.com/netty/netty/issues/8238.

View File

@ -29,32 +29,33 @@ import io.netty.channel.local.LocalServerChannel;
import io.netty.channel.pool.FixedChannelPool.AcquireTimeoutAction; import io.netty.channel.pool.FixedChannelPool.AcquireTimeoutAction;
import io.netty.util.concurrent.Future; import io.netty.util.concurrent.Future;
import io.netty.util.concurrent.GenericFutureListener; import io.netty.util.concurrent.GenericFutureListener;
import org.junit.AfterClass; import org.junit.jupiter.api.AfterAll;
import org.junit.Assert; import org.junit.jupiter.api.BeforeAll;
import org.junit.BeforeClass; import org.junit.jupiter.api.Test;
import org.junit.Test; import org.junit.jupiter.api.function.Executable;
import java.util.concurrent.ExecutionException; import java.util.concurrent.ExecutionException;
import java.util.concurrent.TimeUnit; import java.util.concurrent.TimeUnit;
import java.util.concurrent.TimeoutException; import java.util.concurrent.TimeoutException;
import static io.netty.channel.pool.ChannelPoolTestUtils.getLocalAddrId; import static io.netty.channel.pool.ChannelPoolTestUtils.getLocalAddrId;
import static org.junit.Assert.assertEquals;
import static org.junit.Assert.assertFalse; import static org.junit.jupiter.api.Assertions.assertEquals;
import static org.junit.Assert.assertNotSame; import static org.junit.jupiter.api.Assertions.assertFalse;
import static org.junit.Assert.assertSame; import static org.junit.jupiter.api.Assertions.assertNotSame;
import static org.junit.Assert.assertTrue; import static org.junit.jupiter.api.Assertions.assertSame;
import static org.junit.Assert.fail; import static org.junit.jupiter.api.Assertions.assertThrows;
import static org.junit.jupiter.api.Assertions.assertTrue;
public class FixedChannelPoolTest { public class FixedChannelPoolTest {
private static EventLoopGroup group; private static EventLoopGroup group;
@BeforeClass @BeforeAll
public static void createEventLoop() { public static void createEventLoop() {
group = new DefaultEventLoopGroup(); group = new DefaultEventLoopGroup();
} }
@AfterClass @AfterAll
public static void destroyEventLoop() { public static void destroyEventLoop() {
if (group != null) { if (group != null) {
group.shutdownGracefully(); group.shutdownGracefully();
@ -104,12 +105,12 @@ public class FixedChannelPoolTest {
pool.close(); pool.close();
} }
@Test(expected = TimeoutException.class) @Test
public void testAcquireTimeout() throws Exception { public void testAcquireTimeout() throws Exception {
testAcquireTimeout(500); testAcquireTimeout(500);
} }
@Test(expected = TimeoutException.class) @Test
public void testAcquireWithZeroTimeout() throws Exception { public void testAcquireWithZeroTimeout() throws Exception {
testAcquireTimeout(0); testAcquireTimeout(0);
} }
@ -138,15 +139,17 @@ public class FixedChannelPoolTest {
AcquireTimeoutAction.FAIL, timeoutMillis, 1, Integer.MAX_VALUE); AcquireTimeoutAction.FAIL, timeoutMillis, 1, Integer.MAX_VALUE);
Channel channel = pool.acquire().syncUninterruptibly().getNow(); Channel channel = pool.acquire().syncUninterruptibly().getNow();
Future<Channel> future = pool.acquire(); final Future<Channel> future = pool.acquire();
try { assertThrows(TimeoutException.class, new Executable() {
@Override
public void execute() throws Throwable {
future.syncUninterruptibly(); future.syncUninterruptibly();
} finally { }
});
sc.close().syncUninterruptibly(); sc.close().syncUninterruptibly();
channel.close().syncUninterruptibly(); channel.close().syncUninterruptibly();
pool.close(); pool.close();
} }
}
@Test @Test
public void testAcquireNewConnection() throws Exception { public void testAcquireNewConnection() throws Exception {
@ -219,7 +222,7 @@ public class FixedChannelPoolTest {
pool.close(); pool.close();
} }
@Test(expected = IllegalStateException.class) @Test
public void testAcquireBoundQueue() throws Exception { public void testAcquireBoundQueue() throws Exception {
LocalAddress addr = new LocalAddress(getLocalAddrId()); LocalAddress addr = new LocalAddress(getLocalAddrId());
Bootstrap cb = new Bootstrap(); Bootstrap cb = new Bootstrap();
@ -240,22 +243,24 @@ public class FixedChannelPoolTest {
// Start server // Start server
Channel sc = sb.bind(addr).syncUninterruptibly().channel(); Channel sc = sb.bind(addr).syncUninterruptibly().channel();
ChannelPoolHandler handler = new TestChannelPoolHandler(); ChannelPoolHandler handler = new TestChannelPoolHandler();
ChannelPool pool = new FixedChannelPool(cb, handler, 1, 1); final ChannelPool pool = new FixedChannelPool(cb, handler, 1, 1);
Channel channel = pool.acquire().syncUninterruptibly().getNow(); Channel channel = pool.acquire().syncUninterruptibly().getNow();
Future<Channel> future = pool.acquire(); Future<Channel> future = pool.acquire();
assertFalse(future.isDone()); assertFalse(future.isDone());
try { assertThrows(IllegalStateException.class, new Executable() {
@Override
public void execute() throws Throwable {
pool.acquire().syncUninterruptibly(); pool.acquire().syncUninterruptibly();
} finally { }
});
sc.close().syncUninterruptibly(); sc.close().syncUninterruptibly();
channel.close().syncUninterruptibly(); channel.close().syncUninterruptibly();
pool.close(); pool.close();
} }
}
@Test(expected = IllegalArgumentException.class) @Test
public void testReleaseDifferentPool() throws Exception { public void testReleaseDifferentPool() throws Exception {
LocalAddress addr = new LocalAddress(getLocalAddrId()); LocalAddress addr = new LocalAddress(getLocalAddrId());
Bootstrap cb = new Bootstrap(); Bootstrap cb = new Bootstrap();
@ -277,19 +282,21 @@ public class FixedChannelPoolTest {
Channel sc = sb.bind(addr).syncUninterruptibly().channel(); Channel sc = sb.bind(addr).syncUninterruptibly().channel();
ChannelPoolHandler handler = new TestChannelPoolHandler(); ChannelPoolHandler handler = new TestChannelPoolHandler();
ChannelPool pool = new FixedChannelPool(cb, handler, 1, 1); ChannelPool pool = new FixedChannelPool(cb, handler, 1, 1);
ChannelPool pool2 = new FixedChannelPool(cb, handler, 1, 1); final ChannelPool pool2 = new FixedChannelPool(cb, handler, 1, 1);
Channel channel = pool.acquire().syncUninterruptibly().getNow(); final Channel channel = pool.acquire().syncUninterruptibly().getNow();
try { assertThrows(IllegalArgumentException.class, new Executable() {
@Override
public void execute() throws Throwable {
pool2.release(channel).syncUninterruptibly(); pool2.release(channel).syncUninterruptibly();
} finally { }
});
sc.close().syncUninterruptibly(); sc.close().syncUninterruptibly();
channel.close().syncUninterruptibly(); channel.close().syncUninterruptibly();
pool.close(); pool.close();
pool2.close(); pool2.close();
} }
}
@Test @Test
public void testReleaseAfterClosePool() throws Exception { public void testReleaseAfterClosePool() throws Exception {
@ -311,7 +318,7 @@ public class FixedChannelPoolTest {
// Start server // Start server
Channel sc = sb.bind(addr).syncUninterruptibly().channel(); Channel sc = sb.bind(addr).syncUninterruptibly().channel();
FixedChannelPool pool = new FixedChannelPool(cb, new TestChannelPoolHandler(), 2); final FixedChannelPool pool = new FixedChannelPool(cb, new TestChannelPoolHandler(), 2);
final Future<Channel> acquire = pool.acquire(); final Future<Channel> acquire = pool.acquire();
final Channel channel = acquire.get(); final Channel channel = acquire.get();
pool.close(); pool.close();
@ -321,15 +328,15 @@ public class FixedChannelPoolTest {
// NOOP // NOOP
} }
}).syncUninterruptibly(); }).syncUninterruptibly();
try { assertThrows(IllegalStateException.class, new Executable() {
@Override
public void execute() throws Throwable {
pool.release(channel).syncUninterruptibly(); pool.release(channel).syncUninterruptibly();
fail();
} catch (IllegalStateException e) {
// expected
} }
});
// Since the pool is closed, the Channel should have been closed as well. // Since the pool is closed, the Channel should have been closed as well.
channel.closeFuture().syncUninterruptibly(); channel.closeFuture().syncUninterruptibly();
assertFalse("Unexpected open channel", channel.isOpen()); assertFalse(channel.isOpen());
sc.close().syncUninterruptibly(); sc.close().syncUninterruptibly();
pool.close(); pool.close();
} }
@ -392,7 +399,7 @@ public class FixedChannelPoolTest {
pool.closeAsync().addListener(new GenericFutureListener<Future<? super Void>>() { pool.closeAsync().addListener(new GenericFutureListener<Future<? super Void>>() {
@Override @Override
public void operationComplete(Future<? super Void> future) throws Exception { public void operationComplete(Future<? super Void> future) throws Exception {
Assert.assertEquals(0, pool.acquiredChannelCount()); assertEquals(0, pool.acquiredChannelCount());
sc.close(closePromise).syncUninterruptibly(); sc.close(closePromise).syncUninterruptibly();
} }
}).awaitUninterruptibly(); }).awaitUninterruptibly();

View File

@ -27,7 +27,8 @@ import io.netty.channel.local.LocalChannel;
import io.netty.channel.local.LocalServerChannel; import io.netty.channel.local.LocalServerChannel;
import io.netty.util.concurrent.Future; import io.netty.util.concurrent.Future;
import org.hamcrest.CoreMatchers; import org.hamcrest.CoreMatchers;
import org.junit.Test; import org.junit.jupiter.api.Test;
import org.junit.jupiter.api.function.Executable;
import java.util.Queue; import java.util.Queue;
import java.util.concurrent.LinkedBlockingQueue; import java.util.concurrent.LinkedBlockingQueue;
@ -35,13 +36,13 @@ import java.util.concurrent.TimeUnit;
import static io.netty.channel.pool.ChannelPoolTestUtils.getLocalAddrId; import static io.netty.channel.pool.ChannelPoolTestUtils.getLocalAddrId;
import static org.hamcrest.MatcherAssert.assertThat; import static org.hamcrest.MatcherAssert.assertThat;
import static org.junit.Assert.assertEquals; import static org.junit.jupiter.api.Assertions.assertEquals;
import static org.junit.Assert.assertFalse; import static org.junit.jupiter.api.Assertions.assertFalse;
import static org.junit.Assert.assertNotNull; import static org.junit.jupiter.api.Assertions.assertNotNull;
import static org.junit.Assert.assertNotSame; import static org.junit.jupiter.api.Assertions.assertNotSame;
import static org.junit.Assert.assertSame; import static org.junit.jupiter.api.Assertions.assertSame;
import static org.junit.Assert.assertTrue; import static org.junit.jupiter.api.Assertions.assertThrows;
import static org.junit.Assert.fail; import static org.junit.jupiter.api.Assertions.assertTrue;
public class SimpleChannelPoolTest { public class SimpleChannelPoolTest {
@Test @Test
@ -67,25 +68,25 @@ public class SimpleChannelPoolTest {
Channel sc = sb.bind(addr).sync().channel(); Channel sc = sb.bind(addr).sync().channel();
CountingChannelPoolHandler handler = new CountingChannelPoolHandler(); CountingChannelPoolHandler handler = new CountingChannelPoolHandler();
ChannelPool pool = new SimpleChannelPool(cb, handler); final ChannelPool pool = new SimpleChannelPool(cb, handler);
Channel channel = pool.acquire().sync().getNow(); Channel channel = pool.acquire().sync().getNow();
pool.release(channel).syncUninterruptibly(); pool.release(channel).syncUninterruptibly();
Channel channel2 = pool.acquire().sync().getNow(); final Channel channel2 = pool.acquire().sync().getNow();
assertSame(channel, channel2); assertSame(channel, channel2);
assertEquals(1, handler.channelCount()); assertEquals(1, handler.channelCount());
pool.release(channel2).syncUninterruptibly(); pool.release(channel2).syncUninterruptibly();
// Should fail on multiple release calls. // Should fail on multiple release calls.
try { assertThrows(IllegalArgumentException.class, new Executable() {
@Override
public void execute() throws Throwable {
pool.release(channel2).syncUninterruptibly(); pool.release(channel2).syncUninterruptibly();
fail();
} catch (IllegalArgumentException e) {
// expected
assertFalse(channel.isActive());
} }
});
assertFalse(channel.isActive());
assertEquals(2, handler.acquiredCount()); assertEquals(2, handler.acquiredCount());
assertEquals(2, handler.releasedCount()); assertEquals(2, handler.releasedCount());
@ -118,7 +119,7 @@ public class SimpleChannelPoolTest {
Channel sc = sb.bind(addr).sync().channel(); Channel sc = sb.bind(addr).sync().channel();
CountingChannelPoolHandler handler = new CountingChannelPoolHandler(); CountingChannelPoolHandler handler = new CountingChannelPoolHandler();
ChannelPool pool = new SimpleChannelPool(cb, handler, ChannelHealthChecker.ACTIVE) { final ChannelPool pool = new SimpleChannelPool(cb, handler, ChannelHealthChecker.ACTIVE) {
private final Queue<Channel> queue = new LinkedBlockingQueue<Channel>(1); private final Queue<Channel> queue = new LinkedBlockingQueue<Channel>(1);
@Override @Override
@ -133,15 +134,15 @@ public class SimpleChannelPoolTest {
}; };
Channel channel = pool.acquire().sync().getNow(); Channel channel = pool.acquire().sync().getNow();
Channel channel2 = pool.acquire().sync().getNow(); final Channel channel2 = pool.acquire().sync().getNow();
pool.release(channel).syncUninterruptibly().getNow(); pool.release(channel).syncUninterruptibly().getNow();
try { assertThrows(IllegalStateException.class, new Executable() {
@Override
public void execute() throws Throwable {
pool.release(channel2).syncUninterruptibly(); pool.release(channel2).syncUninterruptibly();
fail();
} catch (IllegalStateException e) {
// expected
} }
});
channel2.close().sync(); channel2.close().sync();
assertEquals(2, handler.channelCount()); assertEquals(2, handler.channelCount());