summaryrefslogblamecommitdiffstats
path: root/src/main/java/org/openslx/imagemaster/serverconnection/ConnectionHandler.java
blob: 44c8e161460fa491b7cfcaa5500b70e4afe1d193 (plain) (tree)
1
2
3
4
5
6
7
8


                                                 
                           
                              
                      
                     
                                              


                                               





                                       




                                                                




                                              




                                                   


                                                         
                                                                       


                                                       
 

                                                                                
 

                                                                                                          
                                                                            

                                                                                                                                               


                                         
                
                                                                                             
                     





                                                                                                                         
                                                                         

                                                                        
                                                                                                                                                       
                                         

                                                                 
                                         

                 
 
           
















































                                                                                                                             
                                                                                                                              


           

                                                       
           
                                        
                                            
           
                                                                            
         

                                                           
         
 






                                                         
                                                                              
         

                                                             





                                                       
                                                                      
         


                                                                         
         
 



                                                       
                                                                                           
         


                                                                             

         
package org.openslx.imagemaster.serverconnection;

import java.io.FileInputStream;
import java.io.IOException;
import java.security.KeyStore;
import java.util.List;
import java.util.Map;
import java.util.concurrent.ConcurrentHashMap;
import java.util.concurrent.SynchronousQueue;
import java.util.concurrent.ThreadPoolExecutor;
import java.util.concurrent.TimeUnit;

import javax.net.ssl.KeyManager;
import javax.net.ssl.KeyManagerFactory;
import javax.net.ssl.SSLContext;

import org.apache.log4j.Logger;
import org.openslx.bwlp.thrift.iface.ImagePublishData;
import org.openslx.bwlp.thrift.iface.InvocationError;
import org.openslx.bwlp.thrift.iface.TInvocationException;
import org.openslx.bwlp.thrift.iface.TTransferRejectedException;
import org.openslx.bwlp.thrift.iface.TransferInformation;
import org.openslx.filetransfer.Downloader;
import org.openslx.filetransfer.IncomingEvent;
import org.openslx.filetransfer.Listener;
import org.openslx.filetransfer.Uploader;
import org.openslx.imagemaster.Globals;
import org.openslx.imagemaster.crcchecker.CrcFile;
import org.openslx.imagemaster.db.mappers.DbOsVirt;
import org.openslx.imagemaster.db.mappers.DbUser;
import org.openslx.imagemaster.util.RandomString;
import org.openslx.imagemaster.util.Util;

/**
 * Class to handle all incoming and outgoing connections.
 * Also handles the authentication and the saving/delivering of images.
 */
public class ConnectionHandler implements IncomingEvent
{

	private static Logger log = Logger.getLogger( ConnectionHandler.class );
	private static SSLContext sslContext;

	private static Map<String, AbstractTransfer> pendingIncomingUploads = new ConcurrentHashMap<>();
	private static Map<String, AbstractTransfer> pendingIncomingDownloads = new ConcurrentHashMap<>();
	private static IncomingEvent eventHandler = new ConnectionHandler();
	private static ThreadPoolExecutor uploadPool = new ThreadPoolExecutor( 0, 5, 6, TimeUnit.MINUTES, new SynchronousQueue<Runnable>() );
	private static ThreadPoolExecutor downloadPool = new ThreadPoolExecutor( 0, 5, 6, TimeUnit.MINUTES, new SynchronousQueue<Runnable>() );

	private static Listener listener;

	static {
		log.debug( "Starting listener on port " + Globals.getFiletransferPortSsl() );
		try {
			String pathToKeyStore = Globals.getSslKeystoreFile();
			char[] passphrase = Globals.getSslKeystorePassword().toCharArray();
			KeyStore keystore = KeyStore.getInstance( "JKS" );
			keystore.load( new FileInputStream( pathToKeyStore ), passphrase );
			KeyManagerFactory kmf = KeyManagerFactory.getInstance( KeyManagerFactory.getDefaultAlgorithm() );
			kmf.init( keystore, passphrase );
			sslContext = SSLContext.getInstance( "TLSv1.2" );
			KeyManager[] keyManagers = kmf.getKeyManagers();
			sslContext.init( keyManagers, null, null );
			listener = new Listener( eventHandler, sslContext, Globals.getFiletransferPortSsl(), Globals.getFiletransferTimeout() * 1000 );
			listener.start();
		} catch ( Exception e ) {
			log.error( "Initialization failed.", e );
			System.exit( 2 );
		}
	}

	/**
	 * Checks if this image is already uploading and returns a new list with missing blocks if so.
	 * Puts the new image into processing list else.
	 * 
	 * @param serverSessionId The uploading server
	 * @param imageData The data of the image
	 * @return
	 * @throws UploadException If some error occurred during the process
	 */
	public static TransferInformation getUploadInfos( ImagePublishData imageData, List<Integer> crcSums )
			throws TTransferRejectedException, TInvocationException
	{
		// check image data
		if ( Util.isEmpty( imageData.imageName ) )
			throw new TInvocationException( InvocationError.INVALID_DATA, "Image name not set" );
		if ( !DbUser.exists( imageData.user ) )
			throw new TInvocationException( InvocationError.INVALID_DATA, "Invalid or missing image owner" );
		if ( DbOsVirt.osExists( imageData.osId ) )
			throw new TInvocationException( InvocationError.INVALID_DATA, "Content operating system not set" );
		if ( DbOsVirt.virtExists( imageData.virtId ) )
			throw new TInvocationException( InvocationError.INVALID_DATA, "Content virtualizer system not set" );
		if ( imageData.fileSize <= 0 )
			throw new TInvocationException( InvocationError.INVALID_DATA, "File size is too small" );

		log.debug( "A satellite is submitting " + imageData.imageVersionId );

		final String uuid = imageData.imageVersionId;
		final String filepathRelative;
		final CrcFile crcFile;
		if ( crcSums == null ) {
			crcFile = null;
		} else {
			crcFile = new CrcFile( crcSums );
		}
		ImagePublishData image;

		synchronized ( pendingIncomingUploads ) {
			/*
			// check if image is already uploading
			if ( ( image = uploadingImages.get( uuid ) ) == null ) {
				// TODO insert new image to DB
				uploadingImages.put( uuid, image );
			}
			*/
		}

		final String token = RandomString.generate( 50, false );

		// TODO addUpload( token, image );
		// TODO Set crc file on image - if there is already a crc file assigned, this does nothing
		return new TransferInformation( token, Globals.getFiletransferPortPlain(), Globals.getFiletransferPortSsl() );
	}

	/**
	 * Add a new allowed incoming upload connection
	 * for the given token and image.
	 * 
	 * @param token The unique token
	 * @param image Image being uploaded
	 */
	public static void addUpload( String token, AbstractTransfer image )
	{
		pendingIncomingUploads.put( token, image );
		log.debug( "Added upload" );
	}

	/**
	 * Add a new allowed incoming download connection
	 * for the given token and image.
	 * 
	 * @param token The unique token
	 * @param image Image being uploaded
	 */
	public static void addDownload( String token, AbstractTransfer image )
	{
		pendingIncomingDownloads.put( token, image );
		log.debug( "Added download" );
	}

	/**
	 * Server is uploading - client is downloading!
	 */
	@Override
	public void incomingDownloadRequest( final Uploader uploader )
	{
		// TODO
		uploader.sendErrorCode( "Too many concurrent uploads." );
		uploader.cancel();
	}

	/**
	 * Server is downloading - client is uploading!
	 */
	@Override
	public void incomingUploadRequest( final Downloader downloader ) throws IOException
	{
		// TODO
		downloader.sendErrorCode( "Too many concurrent downloads." );
		downloader.cancel();
	}
}