?? quickserver.java
字號(hào):
/*
* This file is part of the QuickServer library
* Copyright (C) QuickServer.org
*
* Use, modification, copying and distribution of this software is subject to
* the terms and conditions of the GNU Lesser General Public License.
* You should have received a copy of the GNU LGP License along with this
* library; if not, you can download a copy from <http://www.quickserver.org/>.
*
* For questions, suggestions, bug-reports, enhancement-requests etc.
* visit http://www.quickserver.org
*
*/
package org.quickserver.net.server;
import java.io.*;
import java.net.*;
import org.quickserver.net.*;
//v1.1
import org.quickserver.net.qsadmin.*;
//v1.2
import java.util.logging.*;
//v1.3
import org.quickserver.util.pool.*;
import org.quickserver.util.pool.thread.*;
import org.apache.commons.pool.*;
import org.quickserver.util.xmlreader.*;
import org.quickserver.sql.*;
//v1.3.1
import java.util.*;
//v1.3.2
import org.quickserver.util.*;
import java.util.regex.*;
//v1.3.3
import org.quickserver.security.*;
//v1.4.0
import javax.net.ssl.*;
import javax.net.*;
import java.security.*;
import java.security.cert.*;
import org.quickserver.util.io.*;
//v1.4.5
import java.nio.*;
import java.nio.channels.*;
import org.quickserver.net.server.impl.*;
/**
* Main class of QuickServer library. This class is used to create
* multi client servers quickly.
* <p>
* Ones a client is connected, it creates {@link ClientHandler} object,
* which is run using any thread available from the pool of threads
* maintained by {@link org.quickserver.util.pool.thread.ClientPool}, which
* handles the client. <br/>
* QuickServer divides the application logic of its developer over eight
* class, <br>
* <ul>
* <li>ClientEventHandler<br>
* Handles client events [Optional Class].
* <li>ClientCommandHandler [#]<br>
* Handles client character/string commands.
* <li>ClientObjectHandler [#]<br>
* Handles client interaction - Object commands.
* <li>ClientBinaryHandler [#]<br>
* Handles client interaction - binary data.
* <li>ClientWriteHandler [Optional Class]<br>
* Handles client interaction - writing data (Only used in non-blocking mode).
* <li>ClientAuthenticationHandler [Optional Class]<br>
* Used to Authencatet a client.
* <li>ClientData [Optional Class]<br>
* Client data carrier (support class)
* <li>ClientExtendedEventHandler [Optional Class]<br>
* Handles extended client events.
* </ul>
*
* [#] = Any one of these have to be set based on default DataMode for input.
* The default DataMode for input is String so if not changes you will
* have to set ClientCommandHandler.
* </p>
* <p>
* Eg:
* <code><BLOCKQUOTE><pre>
package echoserver;
import org.quickserver.net.*;
import org.quickserver.net.server.*;
import java.io.*;
public class EchoServer {
public static void main(String args[]) {
String cmdHandle = "echoserver.EchoCommandHandler";
QuickServer myServer = new QuickServer();
myServer.setClientCommandHandler(cmdHandle);
myServer.setPort(4123);
myServer.setName(Echo Server v1.0");
try {
myServer.startServer();
} catch(AppException e) {
System.err.println("Error in server : "+e);
e.printStackTrace();
}
}
}
</pre></BLOCKQUOTE></code></p>
*
* @version 1.4.7
* @author Akshathkumar Shetty
*/
public class QuickServer implements Runnable, Service, Cloneable, Serializable {
//Some variable are not initialised to any value because the
//default java value was desired initial value.
//'dev ' = development build not yet final
//'beta' = test build all features
private final static String VER = "1.4.7";//change also in QSAdminMain
private final static String NEW_LINE = "\r\n";
static {
System.out.print("Loading QuickServer v"+getVersion()+" ");
}
private String serverBanner;
private String clientAuthenticationHandlerString; //v1.4.6
private String clientEventHandlerString; //v1.4.6
private String clientExtendedEventHandlerString; //v1.4.6
private String clientCommandHandlerString;
private String clientObjectHandlerString; //v1.2
private String clientBinaryHandlerString; //v1.4
private String clientWriteHandlerString; //v1.4.5
private String clientDataString;
private Authenticator authenticator;
private ClientAuthenticationHandler clientAuthenticationHandler; //v1.4.6
private ClientEventHandler clientEventHandler; //v1.4.6
private ClientExtendedEventHandler clientExtendedEventHandler; //v1.4.6
private ClientCommandHandler clientCommandHandler;
private ClientObjectHandler clientObjectHandler; //v1.2
private ClientBinaryHandler clientBinaryHandler; //v1.4
private ClientWriteHandler clientWriteHandler; //v1.4.5
private ClientData clientData;
protected Class clientDataClass;
private int serverPort = 9876;
private Thread t; //Main thread
private ServerSocket server;
private String serverName = "QuickServer";
private long maxConnection = -1;
private int socketTimeout = 60 * 1000; //1 min socket timeout
private String maxConnectionMsg = "-ERR Server Busy. Max Connection Reached";
private String timeoutMsg = "-ERR Timeout";
private String maxAuthTryMsg = "-ERR Max Auth Try Reached";
private int maxAuthTry = 5; //v1.2
static {
System.out.print(".");
}
//--v1.1
private InetAddress ipAddr;
private boolean stopServer;
private Object[] storeObjects;
private QSAdminServer adminServer;
//--v1.2
//Logger for QuickServer
private static final Logger logger = Logger.getLogger(QuickServer.class.getName());
//Logger for the application using this QuickServer
private Logger appLogger;
//for Service interface
private long suspendMaxConnection; //backup
private String suspendMaxConnectionMsg; //backup
private int serviceState = Service.UNKNOWN;
static {
System.out.print(".");
}
//--v1.3
private QuickServerConfig config = new QuickServerConfig();
private String consoleLoggingformatter;
private String consoleLoggingLevel = "INFO";
private ClientPool pool;
private ObjectPool clientHandlerPool;
private ObjectPool clientDataPool;
private DBPoolUtil dBPoolUtil;
//--v1.3.1
private String loggingLevel = "INFO";
//--v1.3.2
private boolean skipValidation = false;
private boolean communicationLogging = true;
//--v1.3.3
private String securityManagerClass;
private AccessConstraintConfig accessConstraintConfig;
private ClassLoader classLoader;
private String applicationJarPath;
private ServerHooks serverHooks;
private ArrayList listOfServerHooks;
static {
System.out.print(".");
}
//--v1.4.0
private Secure secure;
private BasicServerConfig basicConfig = config;
private SSLContext sslc;
private KeyManager km[] = null;
private TrustManager tm[] = null;
private boolean runningSecure = false;
private SecureStoreManager secureStoreManager = null;
private Exception exceptionInRun = null;
//--v1.4.5
private ServerSocketChannel serverSocketChannel;
private Selector selector;
private boolean blockingMode = true;
private ObjectPool byteBufferPool;
private java.util.Date lastStartTime;
private ClientIdentifier clientIdentifier;
private GhostSocketReaper ghostSocketReaper;
private PoolManager poolManager;
private QSObjectPoolMaker qsObjectPoolMaker;
//--v1.4.6
private DataMode defaultDataModeIN = DataMode.STRING;
private DataMode defaultDataModeOUT = DataMode.STRING;
//-v1.4.7
private Throwable serviceError;
private Map registerChannelRequestMap;
static {
System.out.println(" Done");
//should be commented if not a patch release
//System.out.println("[Includes patch(#): t=152&p=532]");
//should be commented if not a dev release
//System.out.println("[Dev Build Date: Saturday, October 29, 2005]");
}
/** Returns the version of the library. */
public static final String getVersion() {
return VER;
}
/**
* Returns the numerical version of the library.
* @since 1.2
*/
public static final float getVersionNo() {
return getVersionNo(VER);
}
/**
* Returns the numerical version of the library.
* @since 1.4.5
*/
public static final float getVersionNo(String ver) {
//String ver = getVersion();
float version = 0;
int i = ver.indexOf(" "); //check if beta
if(i == -1)
i = ver.length();
ver = ver.substring(0, i);
i = ver.indexOf("."); //check for sub version
if(i!=-1) {
int j = ver.indexOf(".", i);
if(j!=-1) {
ver = ver.substring(0, i)+"."+
MyString.replaceAll(ver.substring(i+1), ".", "");
}
}
try {
version = Float.parseFloat(ver);
} catch(NumberFormatException e) {
throw new RuntimeException("Corrupt QuickServer");
}
return version;
}
/**
* Returns the new line string used by QuickServer.
* @since 1.2
*/
public static String getNewLine() {
return NEW_LINE;
}
/**
* Returns the Server name : port of the QuickServer.
*/
public String toString() {
return serverName + " : " + getPort();
}
/**
* Creates a new server without any configuration.
* Make sure you configure the QuickServer, before
* calling startServer()
* @see org.quickserver.net.server.ClientEventHandler
* @see org.quickserver.net.server.ClientCommandHandler
* @see org.quickserver.net.server.ClientObjectHandler
* @see org.quickserver.net.server.ClientBinaryHandler
* @see org.quickserver.net.server.ClientWriteHandler
* @see org.quickserver.net.server.ClientAuthenticationHandler
* @see org.quickserver.net.server.ClientHandler
* @see #configQuickServer
* @see #initService
* @see #setPort
* @see #setClientCommandHandler
* @since 1.2
*/
public QuickServer() {
}
/**
* Creates a new server with the specified
* <code>commandHandler</code> has it {@link ClientCommandHandler}.
* @param commandHandler the fully qualified name of the
* desired class that implements {@link ClientCommandHandler}
*
* @see org.quickserver.net.server.ClientCommandHandler
* @see org.quickserver.net.server.ClientAuthenticationHandler
* @see org.quickserver.net.server.ClientHandler
* @see #setPort
*/
public QuickServer(String commandHandler) {
setClientCommandHandler(commandHandler);
}
/**
* Creates a new server at <code>port</code> with the specified
* <code>commandHandler</code> has it {@link ClientCommandHandler}.
*
* @param commandHandler fully qualified name of the class that
* implements {@link ClientCommandHandler}
* @param port to listen on.
*
* @see org.quickserver.net.server.ClientCommandHandler
* @see org.quickserver.net.server.ClientAuthenticationHandler
* @see org.quickserver.net.server.ClientHandler
*/
public QuickServer(String commandHandler,int port) {
this(commandHandler); //send to another constructor
setPort(port);
}
/**
* Starts the QuickServer.
*
* @exception org.quickserver.net.AppException
* if Server already running or if it could not load the classes
* [ClientCommandHandler, ClientAuthenticationHandler, ClientData].
* @see #startService
*/
public void startServer() throws AppException {
logger.fine("Starting "+getName());
if(isClosed() == false) {
logger.warning("Server "+getName()+" already running.");
throw new AppException("Server "+getName()+" already running.");
}
if(serverBanner == null) {
serverBanner = "\n-------------------------------" +
"\n Name : " + getName() +
"\n Port : " + getPort() +
"\n-------------------------------\n";
logger.finest("Default Server Banner Generated");
}
try {
loadApplicationClasses();
//load class from Advanced Settings
Class clientIdentifierClass =
getClass(getBasicConfig().getAdvancedSettings().getClientIdentifier(), true);
clientIdentifier = (ClientIdentifier)
clientIdentifierClass.newInstance();
clientIdentifier.setQuickServer(QuickServer.this);
//load class from ObjectPoolConfig
Class poolManagerClass =
getClass(getBasicConfig().getObjectPoolConfig().getPoolManager(), true);
poolManager = (PoolManager) poolManagerClass.newInstance();
//load class QSObjectPoolMaker
Class qsObjectPoolMakerClass = getClass(
getBasicConfig().getAdvancedSettings().getQSObjectPoolMaker(), true);
qsObjectPoolMaker = (QSObjectPoolMaker) qsObjectPoolMakerClass.newInstance();
loadServerHooksClasses();
processServerHooks(ServerHook.PRE_STARTUP);
if(getSecure().isLoad()==true)
loadSSLContext(); //v1.4.0
loadBusinessLogic();
} catch(ClassNotFoundException e) {
logger.severe("Could not load class/s : " + e.getMessage());
throw new AppException("Could not load class/s : " + e.getMessage());
} catch(InstantiationException e) {
logger.severe("Could not instantiate class/s : " + e.getMessage());
throw new AppException("Could not instantiate class/s : "+e.getMessage());
} catch(IllegalAccessException e) {
logger.severe("Illegal access to class/s : " + e.getMessage());
throw new AppException("Illegal access to class/s : " + e.getMessage());
} catch(IOException e) {
logger.severe("IOException : " + e.getMessage());
logger.fine("StackTrace:\n"+MyString.getStackTrace(e));
throw new AppException("IOException : " + e.getMessage());
} catch(Exception e) {
logger.severe("Exception : " + e.getMessage());
logger.fine("StackTrace:\n"+MyString.getStackTrace(e));
throw new AppException("Exception : " + e);
}
?? 快捷鍵說明
復(fù)制代碼
Ctrl + C
搜索代碼
Ctrl + F
全屏模式
F11
切換主題
Ctrl + Shift + D
顯示快捷鍵
?
增大字號(hào)
Ctrl + =
減小字號(hào)
Ctrl + -