View Javadoc
1   /*
2    * junixsocket
3    *
4    * Copyright 2009-2024 Christian Kohlschütter
5    *
6    * Licensed under the Apache License, Version 2.0 (the "License");
7    * you may not use this file except in compliance with the License.
8    * You may obtain a copy of the License at
9    *
10   *     http://www.apache.org/licenses/LICENSE-2.0
11   *
12   * Unless required by applicable law or agreed to in writing, software
13   * distributed under the License is distributed on an "AS IS" BASIS,
14   * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
15   * See the License for the specific language governing permissions and
16   * limitations under the License.
17   */
18  package org.newsclub.net.unix.demo.server;
19  
20  import java.io.IOException;
21  import java.net.ServerSocket;
22  import java.net.Socket;
23  import java.net.SocketAddress;
24  import java.net.SocketException;
25  import java.util.concurrent.Future;
26  
27  import org.newsclub.net.unix.AFSocketAddress;
28  import org.newsclub.net.unix.AFUNIXSocket;
29  import org.newsclub.net.unix.server.SocketServer;
30  
31  /**
32   * An {@link SocketServer} that's just good for demo purposes.
33   *
34   * @author Christian Kohlschütter
35   */
36  @SuppressWarnings("CatchAndPrintStackTrace" /* errorprone */)
37  abstract class DemoServerBase extends SocketServer<SocketAddress, Socket, ServerSocket> {
38    public DemoServerBase(SocketAddress listenAddress) {
39      super(listenAddress);
40    }
41  
42    private static String millisToHumanReadable(int millis, String zeroValue) {
43      if (millis == 0 && zeroValue != null) {
44        return "0 [ms] (" + zeroValue + ")";
45      } else {
46        float secs = millis / 1000f;
47        if ((secs - (int) secs) == 0) {
48          return millis + " [ms] == " + (int) (secs) + "s";
49        } else {
50          return millis + " [ms] == " + secs + "s";
51        }
52      }
53    }
54  
55    @Override
56    protected void onServerStarting() {
57      System.out.println();
58      System.out.println("Creating server: " + getClass().getName());
59      System.out.println("with the following configuration:");
60      System.out.println("- maxConcurrentConnections: " + getMaxConcurrentConnections());
61      System.out.println("- serverTimeout: " + millisToHumanReadable(getServerTimeout(), "none"));
62      System.out.println("- socketTimeout: " + millisToHumanReadable(getSocketTimeout(), "none"));
63      System.out.println("- serverBusyTimeout: " + millisToHumanReadable(getServerBusyTimeout(),
64          "none"));
65    }
66  
67    @Override
68    protected void onServerBound(SocketAddress address) {
69      System.out.println("Created server -- bound to " + address);
70    }
71  
72    @Override
73    protected void onServerBusy(long busySince) {
74      System.out.println("Server is busy");
75    }
76  
77    @Override
78    protected void onServerReady(int activeCount) {
79      System.out.println("Active connections: " + activeCount
80          + "; waiting for the next connection...");
81    }
82  
83    @Override
84    protected void onServerStopped(ServerSocket theServerSocket) {
85      System.out.println("Close server " + theServerSocket);
86    }
87  
88    @Override
89    protected void onSubmitted(Socket socket, Future<?> submit) {
90      System.out.println("Accepted: " + socket);
91    }
92  
93    @Override
94    protected void onBeforeServingSocket(Socket socket) {
95      System.out.println("Serving socket: " + socket);
96      if (socket instanceof AFUNIXSocket) {
97        try {
98          System.out.println("Client's credentials: " + ((AFUNIXSocket) socket).getPeerCredentials());
99        } catch (IOException e) {
100         e.printStackTrace();
101       }
102     }
103   }
104 
105   @Override
106   protected void onServerShuttingDown() {
107     System.out.println("Nothing going on for a long time, I better stop listening");
108   }
109 
110   @Override
111   protected void onSocketExceptionDuringAccept(SocketException e) {
112     e.printStackTrace();
113   }
114 
115   @Override
116   protected void onSocketExceptionAfterAccept(Socket socket, SocketException e) {
117     System.out.println("Closed (not executed): " + socket);
118   }
119 
120   @Override
121   protected void onServingException(Socket socket, Throwable t) {
122     if (socket.isClosed()) {
123       // "Broken pipe", etc.
124       System.out.println("The other end disconnected (" + t.getMessage() + "): " + socket);
125       return;
126     }
127     System.err.println("Exception thrown in " + socket + ", connected: " + socket.isConnected()
128         + ", " + socket.isBound() + "," + socket.isClosed() + "," + socket.isInputShutdown() + ","
129         + socket.isOutputShutdown());
130     t.printStackTrace();
131   }
132 
133   @Override
134   protected void onAfterServingSocket(Socket socket) {
135     System.out.println("Closed: " + socket);
136   }
137 
138   @Override
139   protected void onListenException(Exception e) {
140     e.printStackTrace();
141   }
142 
143   @Override
144   protected ServerSocket newServerSocket() throws IOException {
145     SocketAddress listenAddress = getListenAddress();
146     if (listenAddress instanceof AFSocketAddress) {
147       return ((AFSocketAddress) listenAddress).getAddressFamily().newServerSocket();
148     } else {
149       return new ServerSocket();
150     }
151   }
152 }