/* Copyright (c) 2009 Peter Troshin * * JAva Bioinformatics Analysis Web Services (JABAWS) @version: 1.0 * * This library is free software; you can redistribute it and/or modify it under the terms of the * Apache License version 2 as published by the Apache Software Foundation * * This library 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 Apache * License for more details. * * A copy of the license is in apache_license.txt. It is also available here: * @see: http://www.apache.org/licenses/LICENSE-2.0.txt * * Any republication or derived work distributed in source code form * must include this copyright and license notice. */ package compbio.engine.client; import java.io.File; import java.util.Arrays; import java.util.List; import org.apache.log4j.Logger; import compbio.engine.client.CommandBuilder.Parameter; import compbio.engine.conf.PropertyHelperManager; import compbio.util.PropertyHelper; import compbio.util.Util; public abstract class SkeletalExecutable implements Executable { protected static final PropertyHelper ph = PropertyHelperManager .getPropertyHelper(); private static Logger log = Logger.getLogger(SkeletalExecutable.class); protected String inputFile = "input.txt"; protected String outputFile = "output.txt"; protected String errorFile = "error.txt"; private boolean isInputSet = false; private boolean isOutputSet = false; private boolean isErrorSet = false; /** * This has to allow duplicate parameters as different options may have the * same value e.g. Muscle -weight1 clustalw -weight2 clustalw */ protected CommandBuilder cbuilder; public SkeletalExecutable() { cbuilder = new CommandBuilder(" "); } public SkeletalExecutable(String parameterKeyValueDelimiter) { assert parameterKeyValueDelimiter != null; cbuilder = new CommandBuilder(parameterKeyValueDelimiter); } public SkeletalExecutable setInput(String inFile) { if (compbio.util.Util.isEmpty(inFile)) { throw new IllegalArgumentException("Input file must not be NULL"); } this.inputFile = inFile; this.isInputSet = true; return this; } public SkeletalExecutable setOutput(String outFile) { if (compbio.util.Util.isEmpty(outFile) || PathValidator.isAbsolutePath(outFile)) { throw new IllegalArgumentException( "Output file must not be NULL and Absolute path could not be used! Please provide the filename only. Value provided: " + outFile); } this.outputFile = outFile; this.isOutputSet = true; return this; } public SkeletalExecutable setError(String errFile) { if (compbio.util.Util.isEmpty(errFile) || PathValidator.isAbsolutePath(errFile)) { throw new IllegalArgumentException( "Error file must not be NULL and Absolute path could not be used! Please provide the filename only. Value provided: " + errFile); } this.errorFile = errFile; this.isErrorSet = true; return this; } @Override public CommandBuilder getParameters(ExecProvider provider) { /* * Prevent modification of the parameters unintentionally. This is * important to preserve executable parameters intact as engine could * add things into the array as it see fit. For instance * ExecutableWrapper (part of local engines) add command line as the * first element of an array. */ paramValueUpdater(); return cbuilder; } @Override public Executable addParameters(List parameters) { cbuilder.addParams(parameters); return this; } public Executable setParameter(String parameter) { cbuilder.setParam(parameter); return this; } /** * This is a generic method of changing values of the parameters with * properties * * This method iterates via commands for an executable finding matches from * the Executable.properties file and replacing values in CommandBuilder * with a combination of value from CommandBuilder to merge path from * properties */ void paramValueUpdater() { for (Parameter command : cbuilder.getCommandList()) { if (command.value == null) { continue; } String propertyPath = compbio.engine.client.Util.getExecProperty( command.name + ".path", getType()); if (Util.isEmpty(propertyPath)) { continue; } if (new File(command.value).isAbsolute()) { // Matrix can be found so no actions necessary // This method has been called already and the matrix name // is modified to contain full path // no further actions is // necessary continue; } String absMatrixPath = compbio.engine.client.Util .convertToAbsolute(propertyPath); command.value = absMatrixPath + File.separator + command.value; cbuilder.setParam(command); } } /** * This method cannot really tell whether the files has actually been * created or not. It must be overridden as required. * * @see compbio.engine.client.Executable#getCreatedFiles() */ @Override public List getCreatedFiles() { return Arrays.asList(getOutput(), getError()); } @Override public String getInput() { return inputFile; } protected boolean isInputSet() { return isInputSet; } protected boolean isOutputSet() { return isOutputSet; } protected boolean isErrorSet() { return isErrorSet; } @Override public String getOutput() { return outputFile; } @Override public String getError() { return errorFile; } @Override public String toString() { String value = "Input: " + this.getInput() + "\n"; value += "Output: " + this.getOutput() + "\n"; value += "Error: " + this.getError() + "\n"; value += "Class: " + this.getClass() + "\n"; value += "Params: " + cbuilder + "\n"; return value; } @Override public Executable loadRunConfiguration(RunConfiguration rconfig) { if (!compbio.util.Util.isEmpty(rconfig.getOutput())) { setOutput(rconfig.getOutput()); } if (!compbio.util.Util.isEmpty(rconfig.getError())) { setError(rconfig.getError()); } if (!compbio.util.Util.isEmpty(rconfig.getInput())) { setInput(rconfig.getInput()); } this.cbuilder = (CommandBuilder) rconfig.getParameters(); return this; } @Override public boolean equals(Object obj) { if (obj == null) { return false; } if (!(obj instanceof SkeletalExecutable)) { return false; } SkeletalExecutable exec = (SkeletalExecutable) obj; if (!Util.isEmpty(this.inputFile) && !Util.isEmpty(exec.inputFile)) { if (!this.inputFile.equals(exec.inputFile)) { return false; } } if (!Util.isEmpty(this.outputFile) && !Util.isEmpty(exec.outputFile)) { if (!this.outputFile.equals(exec.outputFile)) { return false; } } if (!Util.isEmpty(this.errorFile) && !Util.isEmpty(exec.errorFile)) { if (!this.errorFile.equals(exec.errorFile)) { return false; } } if (!this.cbuilder.equals(exec.cbuilder)) { return false; } return true; } @Override public int hashCode() { int code = inputFile.hashCode(); code += outputFile.hashCode(); code += errorFile.hashCode(); code *= this.cbuilder.hashCode(); return code; } public String getClusterSettings() { String settings = ph.getProperty(getType().getSimpleName() .toLowerCase() + ".cluster.settings"); return settings == null ? "" : settings; } public abstract Class> getType(); }