de.uni_luebeck.inb.knowarc.usecases.invocation.UseCaseInvocation.java Source code

Java tutorial

Introduction

Here is the source code for de.uni_luebeck.inb.knowarc.usecases.invocation.UseCaseInvocation.java

Source

/* Part of the KnowARC Janitor Use-case processor for taverna
 *  written 2007-2010 by Hajo Nils Krabbenhoeft and Steffen Moeller
 *  University of Luebeck, Institute for Neuro- and Bioinformatics
 *  University of Luebeck, Institute for Dermatolgy
 *
 *  This package is free software; you can redistribute it and/or modify
 *  it under the terms of the GNU Lesser General Public License as published by
 *  the Free Software Foundation; either version 3 of the License, or
 *  (at your option) any later version.
 *
 *  This package is distributed in the hope that it will be useful,
 *  but WITHOUT ANY WARRANTY; without even the implied warranty of
 *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
 *  GNU Lesser General Public License for more details.
 *
 *  You should have received a copy of the GNU Lesser General Public License
 *  along with this package; if not, write to the Free Software
 *  Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA  02110-1301 USA
 */

package de.uni_luebeck.inb.knowarc.usecases.invocation;

import java.io.BufferedWriter;
import java.io.ByteArrayOutputStream;
import java.io.IOException;
import java.io.InputStream;
import java.io.InputStreamReader;
import java.io.OutputStreamWriter;
import java.net.MalformedURLException;
import java.net.URL;
import java.util.HashMap;
import java.util.List;
import java.util.Set;

import org.apache.commons.io.IOUtils;

import net.sf.taverna.t2.invocation.InvocationContext;
import net.sf.taverna.t2.reference.ExternalReferenceSPI;
import net.sf.taverna.t2.reference.Identified;
import net.sf.taverna.t2.reference.IdentifiedList;
import net.sf.taverna.t2.reference.ReferenceService;
import net.sf.taverna.t2.reference.ReferenceServiceException;
import net.sf.taverna.t2.reference.ReferenceSet;
import net.sf.taverna.t2.reference.T2Reference;
import net.sf.taverna.t2.reference.impl.external.object.InlineByteArrayReferenceBuilder;
import net.sf.taverna.t2.reference.impl.external.object.InlineStringReferenceBuilder;
import de.uni_luebeck.inb.knowarc.usecases.ScriptInput;
import de.uni_luebeck.inb.knowarc.usecases.ScriptInputStatic;
import de.uni_luebeck.inb.knowarc.usecases.ScriptInputUser;
import de.uni_luebeck.inb.knowarc.usecases.UseCaseDescription;

/**
 * An abstraction of various forms to bring job using the software that is
 * referenced as a use case towards their execution.
 * 
 * @author Hajo Nils Krabbenhoeft with some contribution by
 * @author Steffen Moeller
 */
public abstract class UseCaseInvocation {

    private String runId;

    protected static String getActualOsCommand(String osCommand, String pathToOriginal, String targetName,
            String pathTarget) {
        String actualOsCommand = osCommand;
        actualOsCommand = actualOsCommand.replace("%%PATH_TO_ORIGINAL%%", pathToOriginal);
        actualOsCommand = actualOsCommand.replace("%%TARGET_NAME%%", targetName);
        actualOsCommand = actualOsCommand.replace("%%PATH_TO_TARGET%%", pathTarget);
        return actualOsCommand;
    }

    protected UseCaseDescription usecase;
    protected final HashMap<String, String> tags = new HashMap<String, String>();
    protected int nTempFiles = 0;
    private static int submissionID = 0;
    protected static InlineByteArrayReferenceBuilder inlineByteArrayReferenceBuilder = new InlineByteArrayReferenceBuilder();
    protected static InlineStringReferenceBuilder inlineStringReferenceBuilder = new InlineStringReferenceBuilder();
    private InvocationContext invocationContext;
    private boolean retrieveData;

    /*
     * get the class of the data we expect for a given input
     */
    @SuppressWarnings("unchecked")
    public Class getType(String inputName) {
        if (!usecase.getInputs().containsKey(inputName))
            return null;
        ScriptInputUser input = (ScriptInputUser) usecase.getInputs().get(inputName);
        if (input.isList()) {
            if (input.isBinary())
                return List.class;
            else
                return List.class;
        } else {
            if (input.isBinary())
                return byte[].class;
            else
                return String.class;
        }
    }

    /*
     * get a list of all the input port names
     */
    public Set<String> getInputs() {
        return usecase.getInputs().keySet();
    }

    /*
     * get a id, incremented with each job. thus, this should be thread-wide
     * unique
     */
    public synchronized int getSubmissionID() {
        return submissionID++;
    }

    /*
     * set the data for the input port with given name
     */
    @SuppressWarnings("unchecked")
    public void setInput(String inputName, ReferenceService referenceService, T2Reference t2Reference)
            throws InvocationException {
        if (t2Reference == null) {
            throw new InvocationException("No input specified for " + inputName);
        }
        ScriptInputUser input = (ScriptInputUser) usecase.getInputs().get(inputName);
        if (input.isList()) {
            IdentifiedList<T2Reference> listOfReferences = (IdentifiedList<T2Reference>) referenceService
                    .getListService().getList(t2Reference);

            if (!input.isConcatenate()) {
                // this is a list input (not concatenated)
                // so write every element to its own temporary file
                // and create a filelist file

                // we need to write the list elements to temporary files
                ScriptInputUser listElementTemp = new ScriptInputUser();
                listElementTemp.setBinary(input.isBinary());
                listElementTemp.setTempFile(true);

                String lineEndChar = "\n";
                if (!input.isFile() && !input.isTempFile()) {
                    lineEndChar = " ";
                }

                String listFileContent = "";
                String filenamesFileContent = "";
                // create a list of all temp file names
                for (T2Reference cur : listOfReferences) {
                    String tmp = setOneInput(referenceService, cur, listElementTemp);
                    listFileContent += tmp + lineEndChar;
                    int ind = tmp.lastIndexOf('/');
                    if (ind == -1) {
                        ind = tmp.lastIndexOf('\\');
                    }
                    if (ind != -1) {
                        tmp = tmp.substring(ind + 1);
                    }
                    filenamesFileContent += tmp + lineEndChar;
                }

                // how do we want the listfile to be stored?
                ScriptInputUser listFile = new ScriptInputUser();
                listFile.setBinary(false); // since its a list file
                listFile.setFile(input.isFile());
                listFile.setTempFile(input.isTempFile());
                listFile.setTag(input.getTag());
                T2Reference listFileContentReference = referenceService.register(listFileContent, 0, true,
                        invocationContext);

                tags.put(listFile.getTag(), setOneInput(referenceService, listFileContentReference, listFile));

                listFile.setTag(input.getTag() + "_NAMES");
                T2Reference filenamesFileContentReference = referenceService.register(filenamesFileContent, 0, true,
                        null);
                tags.put(listFile.getTag(), setOneInput(referenceService, filenamesFileContentReference, listFile));
            } else {
                try {
                    // first, concatenate all data
                    if (input.isBinary()) {
                        ByteArrayOutputStream outputStream = new ByteArrayOutputStream();
                        BufferedWriter outputWriter = new BufferedWriter(new OutputStreamWriter(outputStream));
                        for (T2Reference cur : listOfReferences) {
                            InputStreamReader inputReader = new InputStreamReader(
                                    getAsStream(referenceService, cur));
                            IOUtils.copyLarge(inputReader, outputWriter);
                            inputReader.close();
                        }
                        outputWriter.close();
                        T2Reference binaryReference = referenceService.register(outputStream.toByteArray(), 0, true,
                                invocationContext);
                        tags.put(input.getTag(), setOneInput(referenceService, binaryReference, input));
                    } else {
                        ByteArrayOutputStream outputStream = new ByteArrayOutputStream();
                        BufferedWriter outputWriter = new BufferedWriter(new OutputStreamWriter(outputStream));
                        for (T2Reference cur : listOfReferences) {
                            InputStreamReader inputReader = new InputStreamReader(
                                    getAsStream(referenceService, cur));
                            IOUtils.copyLarge(inputReader, outputWriter);
                            outputWriter.write(" ");
                            inputReader.close();
                        }
                        outputWriter.close();
                        T2Reference binaryReference = referenceService.register(outputStream.toByteArray(), 0, true,
                                invocationContext);
                        tags.put(input.getTag(), setOneInput(referenceService, binaryReference, input));
                    }
                } catch (IOException e) {
                    throw new InvocationException(e);
                }
            }
        } else {
            tags.put(input.getTag(), setOneInput(referenceService, t2Reference, input));
        }
    }

    /*
     * submit a grid job and wait for it to finish, then get the result as
     * on-demand downloads or directly as data (in case of local execution)
     */
    public HashMap<String, Object> Submit(ReferenceService referenceService) throws InvocationException {
        submit_generate_job(referenceService);
        return submit_wait_fetch_results(referenceService);
    }

    /*
     * just submit the job. useful if you want to wait for it to finish later on
     * 
     * Can the statics be made more static?
     */
    public void submit_generate_job(ReferenceService referenceService) throws InvocationException {
        for (ScriptInputStatic input : usecase.getStatic_inputs()) {
            T2Reference ref;
            if (input.getUrl() != null) {
                // Does this work OK with binary
                try {
                    ref = referenceService.register(new URL(input.getUrl()), 0, true, null);
                } catch (ReferenceServiceException e) {
                    throw new InvocationException(e);
                } catch (MalformedURLException e) {
                    throw new InvocationException(e);
                }
            } else {
                ref = referenceService.register((String) input.getContent(), 0, true, null);
            }
            tags.put(input.getTag(), setOneInput(referenceService, ref, input));

        }
        submit_generate_job_inner();
    }

    protected abstract void submit_generate_job_inner() throws InvocationException;

    /*
     * wait for a submitted job to finish and fetch the results
     */
    public abstract HashMap<String, Object> submit_wait_fetch_results(ReferenceService referenceService)
            throws InvocationException;

    public abstract String setOneInput(ReferenceService referenceService, T2Reference t2Reference,
            ScriptInput input) throws InvocationException;

    protected InputStream getAsStream(ReferenceService referenceService, T2Reference t2Reference) {
        Identified identified = referenceService.resolveIdentifier(t2Reference, null, null);
        if (identified instanceof ReferenceSet) {
            ExternalReferenceSPI ref = ((ReferenceSet) identified).getExternalReferences().iterator().next();
            return ref.openStream(invocationContext);
        }
        return null;
    }

    public void setContext(InvocationContext context) {
        this.invocationContext = context;

    }

    public InvocationContext getContext() {
        return this.invocationContext;
    }

    public abstract void setStdIn(ReferenceService referenceService, T2Reference t2Reference);

    public abstract void rememberRun(String runId);

    /**
     * @return the runId
     */
    protected String getRunId() {
        return runId;
    }

    /**
     * @param runId the runId to set
     */
    protected void setRunId(String runId) {
        this.runId = runId;
    }

    /**
     * @return the retrieveData
     */
    protected boolean isRetrieveData() {
        return retrieveData;
    }

    /**
     * @param retrieveData the retrieveData to set
     */
    protected void setRetrieveData(boolean retrieveData) {
        this.retrieveData = retrieveData;
    }

}