package org.gcube.dataanalysis.geo.utils.transfer; import java.io.File; import java.io.FileOutputStream; import java.io.InputStream; import java.io.OutputStream; import java.net.URI; import java.util.concurrent.ExecutorService; import java.util.concurrent.Executors; import java.util.concurrent.TimeUnit; import org.apache.commons.net.io.CopyStreamEvent; import org.apache.commons.net.io.CopyStreamListener; import org.apache.commons.net.io.Util; import org.apache.commons.vfs2.FileObject; import org.apache.commons.vfs2.FileSystemException; import org.apache.commons.vfs2.VFS; /** * * @author Andrea Manzi * */ public class TransferUtil { public static int bufferSize = Util.DEFAULT_COPY_BUFFER_SIZE * 1000; private long bytesTransferredForCurrent; static int connectiontimeout = 100000000; static int transferTimeout = 100000000; VFileSystemManager localFSManager = null; private ExecutorService pool; public TransferUtil() throws FileSystemException { localFSManager = new VFileSystemManager("/"); pool = Executors.newFixedThreadPool(1); } public int getConnectiontimeout() { return connectiontimeout; } public void setConnectiontimeout(int connectiontimeout) { TransferUtil.connectiontimeout = connectiontimeout; } public int getTransferTimeout() { return transferTimeout; } public void setTransferTimeout(int transferTimeout) { TransferUtil.transferTimeout = transferTimeout; } /** * * @param uri * @param connectionTimeout * @return * @throws FileSystemException */ public static InputStream getInputStream(URI uri, int connectionTimeout) throws FileSystemException { connectiontimeout = connectionTimeout; FileObject inputFile = TransferUtil.prepareFileObject(uri.toString()); return inputFile.getContent().getInputStream(); } /** * * @param uri * @param outfile * @throws Exception */ public synchronized long transfer(URI uri, String outfile) throws Exception { bytesTransferredForCurrent = 0; FileObject inputFile = TransferUtil.prepareFileObject(uri.toString()); InputStream sourceFileIn = inputFile.getContent().getInputStream(); // getting outfile info FileOutputStream out = new FileOutputStream(new File(outfile)); // parameters boolean terminate = false; bytesTransferredForCurrent = 0; CopyStreamHandler handler = new CopyStreamHandler(sourceFileIn, out, inputFile.getContent().getSize(), listener); try { pool.execute(handler); pool.shutdown(); } catch (Exception e) { e.printStackTrace(); pool.shutdownNow(); throw new Exception("Error while executing the transfer",e); } // waiting for transfer to complete terminate = pool.awaitTermination(transferTimeout, TimeUnit.MILLISECONDS); sourceFileIn.close(); out.close(); return bytesTransferredForCurrent; } /** * * @param uri * @param outfile * @throws Exception */ public synchronized void performTransfer(URI uri, String outfile) throws Exception { bytesTransferredForCurrent = 0; // parameters boolean terminate = false; FileObject inputFile = TransferUtil.prepareFileObject(uri.toString()); InputStream sourceFileIn = inputFile.getContent().getInputStream(); // getting outfile info FileOutputStream out = new FileOutputStream(new File(outfile)); CopyStreamHandler handler = new CopyStreamHandler(sourceFileIn, out, inputFile.getContent().getSize(), listener); try { pool.execute(handler); pool.shutdown(); } catch (Exception e) { e.printStackTrace(); pool.shutdownNow(); throw new Exception("Error while executing the transfer",e); } // waiting for transfer to complete terminate = pool.awaitTermination(transferTimeout, TimeUnit.MILLISECONDS); sourceFileIn.close(); out.close(); } /** * * @param uri * @param outPath * @throws Exception */ public synchronized void performTransferToFolder(URI uri, String outPath) throws Exception { FileObject inputFile = TransferUtil.prepareFileObject(uri.toString()); InputStream sourceFileIn = inputFile.getContent().getInputStream(); // getting outfile info String outputFile; outputFile = inputFile.getName().getBaseName(); if (outPath.endsWith("/")) outPath = outPath.substring(0, outPath.length() - 1); String relativeOutputFile = outPath + File.separator + outputFile; FileObject absoluteOutputFile = localFSManager .resolveFile(relativeOutputFile); FileObject absolutePath = localFSManager.resolveFile(outPath); absolutePath.createFolder(); // parameters boolean terminate = false; OutputStream destinationFileOut = absoluteOutputFile.getContent() .getOutputStream(); bytesTransferredForCurrent = 0; CopyStreamHandler handler = new CopyStreamHandler(sourceFileIn, destinationFileOut, inputFile.getContent().getSize(), listener); try { pool.execute(handler); pool.shutdown(); } catch (Exception e) { e.printStackTrace(); pool.shutdownNow(); absoluteOutputFile.delete(); throw new Exception("Error while executing the transfer",e); } // waiting for transfer to complete terminate = pool.awaitTermination(transferTimeout, TimeUnit.MILLISECONDS); sourceFileIn.close(); destinationFileOut.close(); } /** * * @param URI * @return * @throws FileSystemException */ private static FileObject prepareFileObject(String URI) throws FileSystemException { return VFS.getManager().resolveFile(URI, Utils.createDefaultOptions(URI,connectiontimeout)); } CopyStreamListener listener = new CopyStreamListener() { @Override public void bytesTransferred(long arg0, int arg1, long arg2) { // only for the current object bytesTransferredForCurrent = bytesTransferredForCurrent + arg1; } @Override public void bytesTransferred(CopyStreamEvent arg0) { } }; }