
import java.net.InetAddress;
import java.net.ServerSocket;
import java.net.Socket;
import java.net.SocketException;
//import org.apache.log4j.Logger;
//import org.apache.log4j.PropertyConfigurator;
import javax.net.ServerSocketFactory;

/*
 * Opens sockets and starts the server. has a startup and shutdown method
 */
public class Server extends Thread{
	
	volatile ServerSocket serverSocket;
	protected boolean running;
	protected int port;
	protected int backlog; 
	protected ThreadPool threadPool;
	//private static Logger logger = Logger.getLogger(Server.class);

	public Server(int port,
			int backlog,
			String requestHandlerClassName,
			int maxQueueLength,
			int minThreads,
			int maxThreads){

		this.port = port;
		this.backlog = backlog;
		this.threadPool = new ThreadPool( requestHandlerClassName,
				maxQueueLength,
				minThreads,
				maxThreads);	
	}

	//startup the server
	public void startup(){
		//PropertyConfigurator.configure("config.properties");
		try
		{
			//	Create the Server Socket
			ServerSocketFactory ssf = ServerSocketFactory.getDefault();
			serverSocket = ssf.createServerSocket( this.port, this.backlog );
			// Start the thread
			this.start();
		}
		catch(Exception e)
		{
			//logger.info ("Couldn't create server socket: Exception: " + e );
			System.exit(1);
		}
	}


	//shutdown the server
	public void shutdown()
	{
		try
		{
			//logger.info("shutting down");
			this.running = false;
			this.serverSocket.close();
			//logger.info ("Server has been shutdown");
			System.exit(1);
		}
		catch(Exception e)
		{
			//logger.info ("Server has been shutdown");
			System.exit(1);
		}

	}

	//to start the server thread
	public void run()
	{
		// Start the server
		//logger.info( "Server Started, listening on port: " + this.port );
		this.running = true;
		while( running )
		{
			try
			{
				// Accept the next connection
				Socket socket = serverSocket.accept();
				// Log some debugging information
				InetAddress addr = socket.getInetAddress();
				//logger.info( addr.getHostAddress() + "at" + addr.getHostName()+"connected" );
				// Add the socket to the new RequestQueue
				this.threadPool.add( socket );
			}
			catch( SocketException se )
			{
				// We are closing the ServerSocket in order to shutdown the server, so if
				// we are not currently running then ignore the exception.
				if( this.running )
				{
					//logger.info(se);
				}
			}
			catch( Exception e )
			{
				e.printStackTrace();
			}
		}
		//logger.info( "Shutting down the server" );
		// Shutdown our request queue
		this.threadPool.shutdown();
	}


}
