You're here: Snippet Directory » Java (241)
Language:

Simple Multi-Threaded Server

Language: English
Programming Language: Java
Published by: technochump [not registered]
Last Update: 5/15/2006
Views: 10279


Description

This is a simple server allowing multiple users to connect and communicate simultaneously. It is written as a component so that it can be extended into a thread where your code can be inserted. It may not be the best server but it should be goodfor testing. Have any questions just send me an email <technochump@netscape.net> Here is how you extend it.import java.io.*;/*** The Server Component I called esKernel ***/public class nTalk extends esKernel {public static void main(String argv[]) {/*** This was a chat client I called it nTalk ****/new nTalk(argv);}nTalk(String argv[]) { /*** Required to kick off the Server ***/ startServer(argv);}/*** Once the server is started it will call this function ***/public void serverStarted() { }/*** Once a user(lPID) logs in this function is kicked off ****/public void clientLogin(int lPID) { /*** Send information to the user where lpid = user **/ clientSend("Welcome User", lPID); /*** Function to disconnect user where lpid = user **/ disconnectClient(lPID);}/*** Once a user(lPID) logs off this function is kicked off ***/public void clientLogout(int lPID) { }/*** when the user sends information to the server this function kicks off ***/public void clientRecieve(String lineIn, int lPID) { }}

Code

1 import java.io.*; 2 import java.net.*; 3 4 public class esKernel extends Thread { 5 6 protected int MAXIMUMSOCKETS = 200; 7 protected Thread Samurai[]; 8 protected Thread Ninja; 9 protected Socket client[]; 10 protected BufferedReader clientInput[]; 11 protected PrintStream clientOutput[]; 12 protected ServerSocket server; 13 protected String NAME = "SLT(Socket Transit Lite)"; 14 protected String VERSION = "062600MN"; 15 protected String BUILD = "21"; 16 17 public int OWNED = 1, FREE = 0; 18 public int clientPID[]; 19 public int serverPORT = 1060; 20 public int curPID = 0; 21 public int cachedPID = 0; 22 public int freeSOCKETS = 0; 23 24 public boolean dontLoad = false, quietMode = false; 25 26 27 public void startServer(String argv[]) { 28 int lPID = curPID; 29 30 for(int I = 0; I < argv.length; I+=2) { 31 if(argv[I].equals("--help")) showHelp(); 32 if(argv[I].equals("--version")) showVersion(); 33 if(argv[I].equals("--quiet")) setQuiet(); 34 if(argv[I].equals("--lazy")) { 35 if(I + 1 >= argv.length) { 36 showHelp(); 37 } else { 38 buildLazy(argv[I + 1]); 39 } 40 } 41 if(argv[I].equals("--port")) { 42 if(I + 1 >= argv.length) { 43 showHelp(); 44 } else { 45 setPort(Integer.parseInt(argv[I + 1])); 46 } 47 } 48 if(argv[I].equals("--sockets")) { 49 if(I + 1 >= argv.length) { 50 showHelp(); 51 } else { 52 setSockets(Integer.parseInt(argv[I + 1])); 53 } 54 } 55 } 56 57 if(dontLoad) return; 58 59 loadSockets(); 60 statusMessage(); 61 serverStarted(); 62 63 /** Start up our command line Input Stream **/ 64 Ninja = new Thread(this); 65 Ninja.start(); 66 67 /** ClientPid[0] needs to be set to OWNED **/ 68 curPID = getClientPID(); 69 70 try { 71 server = new ServerSocket(serverPORT, MAXIMUMSOCKETS, null); 72 } catch(IOException ie) { 73 showError(0, -1); 74 System.exit(0); 75 } 76 77 while(true) { 78 try { 79 client[lPID] = server.accept(); 80 } catch(IOException ie) { 81 showError(1, lPID); 82 } 83 84 Samurai[lPID] = new Thread(this); 85 try { 86 clientInput[lPID] = new BufferedReader(new InputStreamReader(client[lPID].getInputStream())); 87 clientOutput[lPID] = new PrintStream(client[lPID].getOutputStream()); 88 } catch(IOException ie) { 89 showError(2, lPID); 90 } 91 /** This is my attempt to limit connections **/ 92 if(lPID > MAXIMUMSOCKETS - 3) { 93 clientOutput[lPID].println("SORRY, THIS SERVER IS CURRENTLY FULL."); 94 clientOutput[lPID].flush(); 95 showError(5, lPID); 96 disconnectClient(lPID); 97 } else { 98 Samurai[lPID].start(); 99 } 100 curPID = lPID; 101 lPID = getClientPID(); 102 } 103 } 104 105 public void run() { 106 int lPID = curPID; 107 String lineIn = ""; 108 if(Thread.currentThread() == Ninja) { 109 startCommandLineStream(); 110 } 111 112 clientLogin(lPID); 113 while((lineIn != null) && (clientInput[lPID] != null)) { 114 try { 115 lineIn = clientInput[lPID].readLine(); 116 } catch(IOException ie) { 117 showError(3, lPID); 118 break; 119 } 120 if(lineIn != null) 121 parseDataInput(lineIn, lPID); 122 } 123 disconnectClient(lPID); 124 } 125 126 public int getClientPID() { 127 for(int I = 0; I < MAXIMUMSOCKETS; I++) { 128 if(clientPID[I] == FREE) { 129 clientPID[I] = OWNED; 130 cachedPID = I; 131 freeSOCKETS--; 132 return I; 133 } 134 } 135 cachedPID = -1; 136 return -1; 137 } 138 139 public int disconnectClient(int dPID) { 140 if(clientPID[dPID] == FREE) return -1; 141 142 try { 143 if(clientInput[dPID] != null) 144 clientInput[dPID].close(); 145 if(clientOutput[dPID] != null) 146 clientOutput[dPID].close(); 147 if(client[dPID] != null) 148 client[dPID].close(); 149 } catch(IOException ie) { 150 showError(4, dPID); 151 } 152 153 clientInput[dPID] = null; 154 clientOutput[dPID] = null; 155 Samurai[dPID] = null; 156 client[dPID] = null; 157 clientPID[dPID] = FREE; 158 freeSOCKETS++; 159 if(!quietMode) { 160 System.out.println("Client Disconnected Successfuly."); 161 System.out.println("Client PID # " + String.valueOf(dPID) + " now FREE."); 162 } 163 clientLogout(dPID); 164 return dPID; 165 } 166 167 public void loadSockets() { 168 Samurai = new Thread[MAXIMUMSOCKETS]; 169 client = new Socket[MAXIMUMSOCKETS]; 170 clientInput = new BufferedReader[MAXIMUMSOCKETS]; 171 clientOutput = new PrintStream[MAXIMUMSOCKETS]; 172 clientPID = new int[MAXIMUMSOCKETS]; 173 freeSOCKETS = MAXIMUMSOCKETS; 174 } 175 176 public void showError(int ErrorMessage, int lPID) { 177 String Error[] = new String[6]; 178 String clientID = ""; 179 if(quietMode) return; 180 if(lPID > -1) 181 clientID = "CLIENT # " + String.valueOf(lPID); 182 183 Error[0] = "Error 0:\n" + clientID + "\nDESCRIPTION: Can't Open Port " + String.valueOf(serverPORT) + ".\nSOLUTION: Try Restarting Server with --port x.\nRESULT: KILLED SERVER!!"; 184 Error[1] = "Error 1:\n" + clientID + "\nDESCRIPTION: Server is no Longer Accepting Connections.\nSOLUTION: Restart Server.\nRESULT: No Action Taken."; 185 Error[2] = "Error 2:\n" + clientID + "\nDESCRIPTION: Can't establish a Consistant Connection with Client.\nSOLUTION: Attempt to Kill Client.\nRESULT:"; 186 Error[3] = "Error 3:\n" + clientID + "\nDESCRIPTION: Client Sending Bogus Data!\nSOLUTION: Attempting to Kill Client!!\nRESULT:"; 187 Error[4] = "Error 4:\n" + clientID + "\nDESCRIPTION: Can't Terminate Connection with Client.\nSOLUTION: Preforming Explicit Kill!!\nRESULT:"; 188 Error[5] = "Error 5:\n" + clientID + "\nDESCRIPTION: SERVER FULL CAN'T ACCEPT CONNECTION\nSOLUTION: Kill USER\nRESULT:"; 189 System.out.println(Error[ErrorMessage]); 190 } 191 192 public void statusMessage() { 193 System.out.println("<------------------------- STATUS ------------------------->"); 194 System.out.println(" [" + NAME + "]"); 195 System.out.println(" VERSION " + VERSION + " BUILD: " + BUILD); 196 System.out.println(" USING PORT: " + String.valueOf(serverPORT)); 197 System.out.println(" CLIENTS: MAX -> " + String.valueOf(MAXIMUMSOCKETS) + " CURRENT -> " + String.valueOf(MAXIMUMSOCKETS - freeSOCKETS) + " FREE PIDS -> " + String.valueOf(freeSOCKETS)); 198 System.out.println("<---------------------------------------------------------->"); 199 } 200 201 public void showHelp() { 202 System.out.println("\n[" + NAME + "]"); 203 System.out.println("Version " + VERSION + " BUILD " + BUILD); 204 System.out.println("Chris Higgins 2000\n"); 205 System.out.println("--help -> Shows this Message"); 206 System.out.println("--sockets x -> Where x equals Maximum Sockets Allowed (expressed as an Integer)"); 207 System.out.println("--quiet -> Don't show any Messages"); 208 System.out.println("--port x -> Where x equals port to host (expressed as an Integer)"); 209 System.out.println("--version -> Shows version Number"); 210 System.out.println("--lazy s -> Build a templet-ready java file called s."); 211 dontLoad = true; 212 } 213 214 public void showVersion() { 215 System.out.println("\n[" + NAME + "]"); 216 System.out.println("Version " + VERSION + " BUILD: " + BUILD); 217 System.out.println("Chris Higgins <technochump@netscape.net>"); 218 System.out.println("2000"); 219 dontLoad = true; 220 } 221 222 public void setPort(int newPORT) { 223 serverPORT = newPORT; 224 } 225 226 public void setSockets(int newSOCKETS) { 227 MAXIMUMSOCKETS = newSOCKETS; 228 } 229 230 public boolean setQuiet() { 231 if(quietMode) { 232 quietMode = false; 233 } else { 234 quietMode = true; 235 } 236 return quietMode; 237 } 238 239 public void buildLazy(String fileName) { 240 System.out.println("import java.io.*;\n"); 241 System.out.println("public class " + fileName + " extends esKernel {\n"); 242 System.out.println("public static void main(String argv[]) {"); 243 System.out.println("new " + fileName + "(argv);"); 244 System.out.println("}\n"); 245 System.out.println(fileName + "(String argv[]) {"); 246 System.out.println("startServer(argv);"); 247 System.out.println("}\n"); 248 System.out.println("public void serverStarted() { \n\n}\n"); 249 System.out.println("public void clientLogin(int lPID) { \n\n}\n"); 250 System.out.println("public void clientLogout(int lPID) { \n\n}\n"); 251 System.out.println("public void clientRecieved(String lineIn, int lPID) { \n\n}\n"); 252 System.out.println("}"); 253 dontLoad = true; 254 } 255 256 public void parseDataInput(String lineIn, int pPID) { 257 if(!quietMode) 258 System.out.println(lineIn + "<CLIENT # " + String.valueOf(pPID) + ">"); 259 clientRecieve(lineIn, pPID); 260 } 261 262 /*** Used as an Ancestry Reference ***/ 263 public void serverStarted() { 264 265 } 266 /*** Used as an Ancestry Reference ***/ 267 public void clientLogin(int lPID) { 268 269 } 270 271 /*** Used as an Ancestry Reference ***/ 272 public void clientLogout(int lPID) { 273 274 } 275 276 /*** Used as an Ancestry Reference ***/ 277 public void clientRecieve(String lineIn, int pPID) { 278 279 } 280 281 public void clientSend(String isMessage, int pPID) { 282 if((clientPID[pPID] != OWNED) || (pPID == cachedPID)) return; 283 clientOutput[pPID].println(isMessage); 284 clientOutput[pPID].flush(); 285 } 286 287 /*** 288 Takes care of Admin Inputs from the Command Line While the Server is 289 Running 290 ***/ 291 public void startCommandLineStream() { 292 BufferedReader serverCommandLine; 293 serverCommandLine = new BufferedReader(new InputStreamReader(System.in)); 294 while(true) { 295 try { 296 parseCommandLineInput(serverCommandLine.readLine()); 297 } catch(IOException ie) { break; } 298 } 299 } 300 301 public void parseCommandLineInput(String lineIn) { 302 if(lineIn.startsWith("/quit")) 303 System.exit(0); 304 if(lineIn.startsWith("/broadcast")) { 305 for(int I = 0; I < MAXIMUMSOCKETS; I++) { 306 clientSend(lineIn.substring(11, lineIn.length()), I); 307 } 308 System.out.println("# Message Broadcasted."); 309 } 310 if(lineIn.startsWith("/quiet")) { 311 if(setQuiet()) { 312 System.out.println("# Quiet Mode Enabled."); 313 } else { 314 System.out.println("# Quiet Mode Disabled."); 315 } 316 } 317 if(lineIn.startsWith("/status")) 318 statusMessage(); 319 if(lineIn.startsWith("/kill")) 320 disconnectClient(Integer.parseInt(lineIn.substring(6, lineIn.length()))); 321 if(lineIn.startsWith("/help")) { 322 System.out.println("/***** Command Line Help *****/"); 323 System.out.println("/quit -> Used to terminate server."); 324 System.out.println("/broadcast x -> Broadcast Message <x> to all Users."); 325 System.out.println("/kill i -> Disconnect user <i>."); 326 System.out.println("/help -> Display this Message."); 327 System.out.println("/quiet -> Enter or disable Quiet Mode"); 328 System.out.println("/trace i -> Trace user <i>."); 329 System.out.println("/message i -> Send Message to user <i>."); 330 System.out.println("/who -> Show all used PIDS."); 331 System.out.println("/status -> Show current server status."); 332 } 333 } 334 335 } 336

No comments avaiable

Add a comment

Name *  

Email (won't be displayed) *    

Website  

Comment *  

Sicherheitscode Security Code *    

RSS