Jump to content


Check out our Community Blogs

Register and join over 40,000 other developers!


Recent Status Updates

View All Updates

Photo
- - - - -

SSL / HTTPS server with Java

timer authentication

  • Please log in to reply
No replies to this topic

#1 fkl

fkl

    CC Devotee

  • Senior Member
  • PipPipPipPipPipPip
  • 417 posts

Posted 24 June 2011 - 03:33 PM

I wrote a basic HTTPS server in java a while back which allows basic authentication using certificates. It was a GUI application but i thought of just pasting the server part and certificate generation info here in case it is useful for any one.

Server Certificate is generated using keytool.exe that comes with jdk. Follow these steps. It creates an RSA certificate, referenced by the alias <alias>, and stored in a keystore named certs. keytool is located in java/bin directory.

$: keytool -genkey -keystore certs -keyalg rsa -alias <alias> -storepass serverkspw -keypass serverpw

The keytool then prompts for information which is shown below.

What is your first and last name?
[Unknown]: <name>
What is the name of your organizational unit?
[Unknown]: Software Development
What is the name of your organization?
[Unknown]: xyz.com
What is the name of your City or Locality?
[Unknown]: Mountain View
What is the name of your State or Province?
[Unknown]: CA
What is the two-letter country code for this unit?
[Unknown]: US

i have used a keystore password of serverkspw and a key password of serverpw. You can use a different alias too. Also, information such as machine name or ip address should be used for name.

This will generate a file named "certs". Either copy it into your working directory and remove the "d://" (absolute path) from the code OR (preferred) if the above does not work i.e. program gives exception on creating secure socket, then simply enter absolute path of certs file in place of "d://".

This will complete your certificate work. Please ensure that the same username
and password are entered in the application. I used serverkspw and a key password of serverpw for the certificate attached with this code.

/*
 * Contains HTTP server's (HTTPS) secure socket specific code.
 * 
 */

package securehttpserver;

import java.io.*;
import java.security.*;
import javax.net.*;
import javax.net.ssl.*;

// Timer is used to expire a session after specified interval i.e. 5 min.
import java.util.Timer;

public class SecureServer implements Runnable
{

    // Constructor take GUI reference which should be removed or modified, Certificate 
    // username (Keystore password) and password (Key password) as params and 
    // assign them locally.
	SecureServer(GUI app, String username, String password)
	{
        this.app = app; // ignore this was poor OO using a GUI pointer

        // File name containing the certificate i generated using keytool
		KEYSTORE = "certs";

        // Keystore password (i.e. username) given while generating certificate.
        // It has to be a character array since strings are immutable.
        KEYSTOREPW = username.toCharArray(); //"serverkspw".

        // The actual password used to generate the key i.e. password. This is
        // also char array for the same reason mentioned above.
        KEYPW = password.toCharArray(); //"serverpw"

        // We do not require client to authenticate to us in the start of
        // key handshaking before actual communication.
        requireClientAuthentication = false;
	}

    // The steps required to obtain a secure server socket generated after keys
    // have been established using the certificate.
    void getServerSocket()
    {
        try
        {
            // Make sure that JSSE is available
            Security.addProvider(new com.sun.net.ssl.internal.ssl.Provider());

            // A keystore is where keys and certificates are kept
            // Both the keystore and individual private keys should be password
            // protected.
            KeyStore keystore = KeyStore.getInstance("JKS");

            keystore.load( new FileInputStream("d://"+ KEYSTORE), KEYSTOREPW);

            // A KeyManagerFactory is used to create key managers
            KeyManagerFactory kmf = KeyManagerFactory.getInstance("SunX509");

            // Initialize the KeyManagerFactory to work with our keystore
            kmf.init(keystore, KEYPW);

            // An SSLContext is an environment for implementing JSSE
            // It is used to create a ServerSocketFactory
            SSLContext sslc = SSLContext.getInstance("SSLv3");

            // Initialize the SSLContext to work with our key managers
            sslc.init(kmf.getKeyManagers(), null, null);

            // Create a ServerSocketFactory from the SSLContext
            ServerSocketFactory ssf = sslc.getServerSocketFactory();
        
            // Socket to me on port 443 i.e. the standard port for HTTPS
            serverSocket =  (SSLServerSocket) ssf.createServerSocket(443);

            // Authenticate the client?
            serverSocket.setNeedClientAuth(requireClientAuthentication);
        }

        catch(Exception e)
        {
            e.getMessage();
        }
    }


    // Automatically invoked method when thread.start() is called. It is
    // required to be implemented when using Interface Runnable.
    public void run ()
    {
        try
        {
            // Obtain secure socket using certificate and all related information
            this.getServerSocket();

            while (true)
            {
                // Waiting for client request for connection
                //this.app.display("Secure Server started listening on port 443\n");
                connectedSocket = (SSLSocket) serverSocket.accept();

                // Connection established for an incoming client. Acquire the
                // Secure Session object to maintain session.
                session = connectedSocket.getSession();

                // SHOULD BE COMMENTED SINCE A CUSTOM TIMER WAS USED
                // Create a new timer, pass the session object to it, along with
                // the expiry interval i.e. 5 minutes in milli secs.
                // The timer executes in a separate thread of Class ExpireSession
                // which actually kills the session. Other fields passed are
                // GUI reference and the client's ip address which is printed
                // while terminating session for identification.
                Timer sessionTimer = new Timer();
                sessionTimer.schedule(new ExpireSession(sessionTimer, session,
                        this.app, connectedSocket.getInetAddress()), 5*60*1000);

                // SHOULD BE COMMENTED, separate file access class 
                // Since session is properly maintained, so now process the
                // actual client request i.e. parse incoming text, fetch the file,
                // and return it on the secure stream. This step is similar to
                // starting new FileRequest except it operates on secure socket.
                //new Thread(new SecureFileRequest(connectedSocket, this.app)).start();

                //display("Got a file request on secure socket... \n");
            }
        }

        catch (IOException e)
        {
            e.printStackTrace();
        }
    }

    // Data members for this class
    private String KEYSTORE;
    private char[] KEYSTOREPW;
    private char[] KEYPW;
    private boolean requireClientAuthentication;
    private SSLServerSocket serverSocket;
    private SSLSocket connectedSocket;
    private SSLSession session;
    //private GUI app;
}

  • 0
Today is the first day of the rest of my life





Also tagged with one or more of these keywords: timer, authentication

Recommended from our users: Dynamic Network Monitoring from WhatsUp Gold from IPSwitch. Free Download