简体   繁体   中英

Connection refusal on Java7 async NIO2 server

I have written a async socketserver using java 7 nio2.

Here is a snipper of the Server.

public class AsyncJava7Server implements Runnable, CounterProtocol, CounterServer{
    private int port = 0;
    private AsynchronousChannelGroup group;
    public AsyncJava7Server(int port) throws IOException, InterruptedException, ExecutionException {
        this.port = port;
    }

    public void run() {
        try {
            String localhostname = java.net.InetAddress.getLocalHost().getHostName();
            group = AsynchronousChannelGroup.withThreadPool(
                 Executors.newCachedThreadPool(new NamedThreadFactory("Channel_Group_Thread")));

            // open a server channel and bind to a free address, then accept a connection
            final AsynchronousServerSocketChannel asyncServerSocketChannel =
                           AsynchronousServerSocketChannel.open(group).bind(
                                 new InetSocketAddress(localhostname, port));

            asyncServerSocketChannel.accept(null, 
                 new CompletionHandler <AsynchronousSocketChannel, Object>() {
                            @Override
                            public void completed(final AsynchronousSocketChannel asyncSocketChannel, 
                                      Object attachment) {
                                    // Invoke simple handle accept code - only takes about 10 milliseconds.
                                    handleAccept(asyncSocketChannel); 
                                    asyncServerSocketChannel.accept(null, this);
            }
                            @Override
                            public void failed(Throwable exc, Object attachment) {
                                System.out.println("***********" + exc  + " statement=" + attachment);  
            }
                 });

and here is a snippet of the client code which tries to connect...

public class AsyncJava7Client implements CounterProtocol, CounterClientBridge {
    AsynchronousSocketChannel asyncSocketChannel;

    private String serverName= null;
    private int port;
    private String clientName;

    public AsyncJava7Client(String clientName, String serverName, int port) throws IOException {
        this.clientName = clientName;
        this.serverName = serverName;
        this.port = port;
    }

    private void connectToServer() {
        Future<Void> connectFuture = null;
        try {
            log("Opening client async channel...");
            asyncSocketChannel = AsynchronousSocketChannel.open();

            // Connecting to server
            connectFuture = asyncSocketChannel.connect(new InetSocketAddress("Alex-PC", 9999));
       } catch (Exception ex) {
            ex.printStackTrace();
            throw new RuntimeException(ex);
       }
       // open a new socket channel and connect to the server
       long beginTime  = 0;
       try {
           // You have two seconds to connect. This will throw exception if server is not there.
           beginTime = System.currentTimeMillis();
           Void connectVoid = connectFuture.get(15, TimeUnit.SECONDS);
       } catch (Exception ex) {
           //EXCEPTIONS THROWN HERE AFTER ABOUT 150 CLIENTS
           long endTime = System.currentTimeMillis();
           long timeTaken = endTime - beginTime;
           log("************* TIME TAKEN=" + timeTaken);
           ex.printStackTrace();
           throw new RuntimeException(ex);
       }
 }

I have a test which fires off clients.

 @Test
 public void testManyClientsAtSametime() throws Exception {
     int clientsize = 150;
     ScheduledThreadPoolExecutor executor = 
            (ScheduledThreadPoolExecutor) Executors.newScheduledThreadPool(clientsize + 1, 
                new NamedThreadFactory("Test_Thread"));
     AsyncJava7Server asyncJava7Server = startServer();
     List<AsyncJava7Client> clients = new ArrayList<AsyncJava7Client>();
     List<Future<String>> results = new ArrayList<Future<String>>();

     for (int i = 0; i < clientsize; i++) {
         // Now start a client
         final AsyncJava7Client client = 
               new AsyncJava7Client("client" + i, InetAddress.getLocalHost().getHostName(), 9999);
         clients.add(client);
     }

     long beginTime = System.currentTimeMillis();
     Random random = new Random();
     for (final AsyncJava7Client client: clients) {
         Callable<String> callable = new Callable<String>() {
             public String call() {
                 ...
                 ... invoke APIs to connect client to server
                 ...
                 return counterValue;
             }
     };

     long delay = random.nextLong() % 10000;  // somewhere between 0 and 10 seconds.
     Future<String> startClientFuture = executor.schedule(callable, delay, TimeUnit.MILLISECONDS);
     results.add(startClientFuture);
 }

It works super for about 100 clients. At about 140+ I get a load of exceptions in the client - when it tries to connect. The exception is: java.util.concurrent.ExecutionException: java.io.IOException: The remote computer refused the network connection.

My test is on a single laptop running windows 7. When it bombs out I check the TCP connections and there about 500 - 600 connections -that's ok. AS I have similiar JDK 1.0 java.net socket programs that can handle 4,000 TCP connections.

No exceptions or anything dodgy looking in server.

So I am at a loss as to what could be wrong here. any ideas?

Try using the form of bind that accepts a backlog limit and set that to a higher number. For example:

            final AsynchronousServerSocketChannel asyncServerSocketChannel =
                       AsynchronousServerSocketChannel.open(group).bind(
                             new InetSocketAddress(localhostname, port), 1000);

I don't know what the win7 implementation limit is by default but can be a cause of refused connections.

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM