Package LONI.visitor

Source Code of LONI.visitor.LoniToGalaxyConverter

package LONI.visitor;

import java.util.*;

import org.apache.commons.lang3.StringEscapeUtils;

import CLInterface.ConverterConstants;
import CLInterface.Printer;
import Core.Pair;
import Galaxy.Tree.Tool.Tool;
import Galaxy.Tree.Tool.Input.Input;
import Galaxy.Tree.Tool.Input.Param.Option;
import Galaxy.Tree.Tool.Output.Data;
import Galaxy.Tree.Workflow.ExternalOutput;
import Galaxy.Tree.Workflow.InputConnection;
import Galaxy.Tree.Workflow.Position;
import Galaxy.Tree.Workflow.Step;
import Galaxy.Tree.Workflow.Workflow;
import Galaxy.Tree.Workflow.ToolState.Primitive;
import Galaxy.Tree.Workflow.ToolState.PrimitiveOrMap;
import Galaxy.Visitor.DFSWorkflowVisitor.StepVisitor;
import Galaxy.Visitor.util.Context;
import LONI.tree.workflow.Connection;
import LONI.tree.workflow.Connections;
import LONI.tree.module.Output;
import LONI.tree.module.Parameter;
import LONI.tree.module.Value;
import LONI.tree.module.format.FileType;
import LONI.tree.workflow.Pipeline;
import LONI.tree.GraphObject.DataModule;
import LONI.tree.GraphObject.GraphObject;
import LONI.tree.GraphObject.Module;
import LONI.tree.GraphObject.ModuleGroup;
import LONI.visitor.util.GalaxyContext;
import Specification.GalaxySpecification;

public class LoniToGalaxyConverter extends DFSVisitor<Object,GalaxyContext> {
  private static int NODE_COUNT = 0;
 
  public static int getId() {
   
    return NODE_COUNT++; /* whoa, using post-decrement properly in java! */
  }
  /**
   * Convert a Pipeline to a Galaxy Workflow
   */
  public Object visit(Pipeline pipeline) {
    Workflow workflow;
    ModuleGroup mgroup = pipeline.getPipelineModuleGroup();
    Connections conns = pipeline.getConnections();
    GalaxyContext context=  new GalaxyContext();
    context.getDatabase().clear();
    NODE_COUNT = 0;
   
    //convert the module group
    Pair<List<Step>, Object> mystp = moduleVisitor.visit(mgroup, context);
   
    /* Visit connections */
    List<Pair<Pair<Integer,String>, InputConnection>> connlist;
    connlist = (List<Pair<Pair<Integer,String>, InputConnection>>) visit(conns, context).getElem1();
   
    /* Add resulting connections */
    for(Pair<Pair<Integer,String>, InputConnection> myconn : connlist){
      for(Step mystep : mystp.getElem1()){
        if(mystep.getId() == myconn.getElem1().getElem1().intValue()){
          mystep.getConnections().put(
              myconn.getElem1().getElem2(), myconn.getElem2());
        }
      }
    }
    //create workflow from modulegroup, connections
    workflow = new Workflow(mgroup.getName(),
        mgroup.getDescription(),
        pipeline.getVersion(),
        true);
    //add steps retrieved from visiting modulegroup.
    for(Step s : mystp.getElem1())
      workflow.addStep(s.getId(), s);
    return workflow;
  }
 
  /*
   * Convert a connection to an InputConnection and sink string.
   */
  public Pair<Object,Object> visit(Connection connection, GalaxyContext context){
    List<Pair<Integer,String>> src = context.getDatabase().getGalaxyMapping(connection.getSource());
    List<Pair<Integer,String>> snk = context.getDatabase().getGalaxyMapping(connection.getSink());
    List<Pair<Pair<Integer,String>,InputConnection>>result = new LinkedList<Pair<Pair<Integer,String>,InputConnection>>();
   
    //if there are no mappings for either the source or sink, don't do anything.
    if(src == null || snk == null){
      Printer.log("No ID mappings found");
      return new Pair<Object,Object>(result, null);
    }
   
    //if there are an uneven amount of source mappings to sink mappings.
    if( src.size() != snk.size()){
      Printer.log("Connection nodes do not have matching cardinalities");
      return new Pair<Object,Object>(result, null);
    }
   
    //If the mappings are empty for either source or sink
    if(src.size() == 0 || snk.size() == 0){
      Printer.log("No entries");
      return new Pair<Object,Object>(result, null);
    }
    //create InputConnection, sink pairs from src, snk mappings.
    for(int i=0; i < src.size(); i++){
      InputConnection inputConn = new InputConnection();
      inputConn.setSourceId(src.get(i).getElem1());
      inputConn.setOutputName(src.get(i).getElem2());
      result.add(new Pair<Pair<Integer,String>,InputConnection>(snk.get(i), inputConn));
     
     
    }
    return new Pair<Object,Object>(result, null);
  }
 
  public Pair<Object,Object> visit(Connections connections, GalaxyContext o){
    List<Pair<Pair<Integer,String>, InputConnection>> conns;
    conns = new LinkedList<Pair<Pair<Integer,String>, InputConnection>>();
    //visit each connection in the connections object
    if(connections != null && connections.getConnections()!=null){
      for(Connection connection : connections.getConnections()){
        Pair<Object,Object> obj = visit(connection, o);
        if(obj != null)
          conns.addAll((List<Pair<Pair<Integer,String>,InputConnection>>)obj.getElem1());
       
      }
    }
    //return the aggregation of returned objects.
    return new Pair<Object,Object>(conns, null);
  }
  {
    moduleVisitor = new ModuleVisitor<List<Step>>(){
     
      public String nameToCardinalityName(String name, int num){
        return name + "_CARD" + num;
      }
     
      // convert modulegroup to list of steps.
      public Pair<List<Step>,Object> visit(ModuleGroup moduleGroup, GalaxyContext o){
        List<Step> step = new ArrayList<Step>();
        //visit each graphobject in module group.
        for(GraphObject graphObject: moduleGroup.getModules()){
          Pair<List<Step>, Object> obj = visit(graphObject, o);
          step.addAll(obj.getElem1());
        }
        //return list of steps.
        return new Pair<List<Step>, Object>(step, null);
      }
     
      //Double Dispatch: use polymorphism to call most specific visitor.
      public Pair<List<Step>,Object> visit(GraphObject graphObject, GalaxyContext context) {
        // TODO Auto-generated method stub
        return graphObject.accept(this, context);
      }
      //Convert module to list of steps.
      public Pair<List<Step>,Object> visit(Module module, GalaxyContext parentContext) {
        List<Step> steps = new ArrayList<Step>();
        Step step = new Step();
        //get unique id from tooldatabase
        String toolId = GalaxySpecification.getDatabase().getUniqueToolID(module.getId());
        //create child context from parent context.
        GalaxyContext childContext = parentContext.copy();
       
        //set basic information
        if(module.getDescription() != null)
          step.setAnnotation(module.getDescription());
       
        step.setId(getId());
        step.setToolType("tool");
        step.setName(module.getName());
        step.setStepPosition(new Position(module.getPosX(), module.getPosY()));
        step.setToolId(toolId);
       
        //add tool state __page__ tag.
        step.getToolState().getToolState().getSecond().put
        ("__page__", new PrimitiveOrMap(new Primitive("0")));
       
        //set step id of child context. All visits using this context may
        //refer to this step id.
        childContext.setParentStepId(step.getId());
       
        //create a new tool
        Tool tool = new Tool();
        tool.setId(toolId);
        tool.setFullName(module.getId());
        tool.setDescription(module.getDescription());
        tool.setVersion("1.0.0");
        //map self
        //create a galaxy id-toolid-name association with loni id.
        childContext.getDatabase().addMapping
          (module.getName(), step.getId(), tool.getId());
       
       
        /*
         * Process high cardinality inputs:
         * Turn them into multiple outputs
         */
        List<Parameter> processed_in = new LinkedList<Parameter>();
        if(module.getInputs() != null){
        for(Parameter p : module.getInputs()){
          int cardinality = p.getFormat().getCardinality();
          if(cardinality > 1){
            for(int i=0; i<cardinality; i++){
              Parameter p_tmp = p.copy();
              p_tmp.setId(nameToCardinalityName(p.getId(),i));
              p_tmp.setName(nameToCardinalityName(p.getName(),i));
              p_tmp.getFileFormat().setCardinality(1);
              if(p.isPrefixAllArgs()==false &&
                  i>0){
                p_tmp.setPrefix("");
                p_tmp.setPrefixSpaced(false);
               
              }
              //If the values object is large enough
              if(p.getValues() != null &&
                  p.getValues().getValues().size() > i){
               
                Value singleVal = p.getValues().getValues().get(i);
                p_tmp.getValues().clearValues();
                p_tmp.getValues().addValue(singleVal);
              }
              childContext.getDatabase().addMapping(p.getId(), p_tmp.getId(), null, null);
              processed_in.add(p_tmp);
            }
           
          }
          else if(cardinality < 0){
            Printer.log("Infinite Cardinalities not supported.");
            p.getFileFormat().setCardinality(1);
            processed_in.add(p);
          }
          else if(cardinality == 0){
            Printer.log("Warning: Cardinality zero found.");
            p.getFileFormat().setCardinality(1);
            processed_in.add(p);
          }
          else{
            processed_in.add(p);
          }
        }
        module.getInputs().clear();
        module.getInputs().addAll(processed_in);
        }
       
        //continued: Handle high cardinality i/o
        List<Output> processed_out = new LinkedList<Output>();
        if(module.getOutputs() != null){
        for(Output o : module.getOutputs()){
          int cardinality = o.getFormat().getCardinality();
          if(cardinality > 1){
            for(int i=0; i<cardinality; i++){
              Output o_tmp = o.copy();
              o_tmp.setId(nameToCardinalityName(o.getId(),i));
              o_tmp.setName(nameToCardinalityName(o.getName(),i));
              o_tmp.getFormat().setCardinality(1);
              if(o.getPrefixAllArgs() != null &&
                 o.getPrefixAllArgs().equals(false)&&
                 i > 0){
                o_tmp.setPrefix("");
                o_tmp.setPrefixSpaced(false);
                //l
               
              }
              childContext.getDatabase().addMapping(o.getId(), o_tmp.getId(), null, null);
              processed_out.add(o_tmp);
              //get the name
              String src = o.getName();
              List<String> sources = childContext.getConnections().getSources(src);
              if(sources != null){
                childContext.getConnections().removeConnectionsToSink(src);
                for(String source : sources){
                  childContext.getConnections().addContext(source, o_tmp.getName());
                }
              }
            }
          }
          else
            processed_out.add(o);
        }
        module.getOutputs().clear();
        module.getOutputs().addAll(processed_out);
       
        }
       
        String command_str;
        /*
         * Process localhost command
         *
         */
        command_str = module.getLocation();
        if(command_str.startsWith(ConverterConstants.LOCALHOST_PATH))
          command_str= command_str.replace(ConverterConstants.LOCALHOST_PATH, "");
        else if(command_str.startsWith(ConverterConstants.PIPELINE_PATH))
          command_str.replace(ConverterConstants.PIPELINE_PATH, "");
       
        Map<Integer, List<Pair<String,String>>> commandStack = new HashMap<Integer, List<Pair<String,String>>>();
       
       
        /*
         * Construct command
         *
         */
        if(module.getInputs() != null){
         
          for(Parameter p : module.getInputs()){
            Pair<Pair<Object,Object>,Object> ob = propertyVisitor.visit(p, childContext);
            Pair<String,String> state = (Pair<String,String>) ob.getElem1().getElem1();
            Galaxy.Tree.Tool.Input.Param.Parameter input = (Galaxy.Tree.Tool.Input.Param.Parameter) ob.getElem1().getElem2();
         
            String prefix = "";
            if(p.getPrefix() != null)
              prefix = p.getPrefix();
            if(p.isPrefixSpaced())
              prefix += " ";
           
            String arg = "$"+input.getName();
            //Add parameter to command stack
            if(!commandStack.containsKey(p.getOrder()))
              commandStack.put(p.getOrder(), new ArrayList<Pair<String,String>>());
            commandStack.get(p.getOrder()).add(new Pair(prefix, arg));
           
            step.getToolState().addState(state.getElem1(), input.getFormat() == null || input.getFormat().equals("") ? "\"" + StringEscapeUtils.escapeJava(state.getElem2()) + "\"" : state.getElem2());
            tool.getToolInputs().getInputList().add(input);
          }
        }
        if(module.getOutputs() != null){
          for(Output out : module.getOutputs()){
            Pair<Object,Object> ob = propertyVisitor.visit(out, childContext);
            Pair<ExternalOutput,Data> datapair= (Pair<ExternalOutput,Data>) ob.getElem1();
           
            String prefix = "";
            if(out.getPrefix() != null)
              prefix = out.getPrefix();
            if(out.getPrefixSpaced() != null &&
              out.getPrefixSpaced()==true)
              prefix += " ";
           
            String arg = "$"+datapair.getElem2().getName();
            //Add parameter to command stack
            if(!commandStack.containsKey(out.getOrder()))
              commandStack.put(out.getOrder(), new ArrayList<Pair<String,String>>());
            commandStack.get(out.getOrder()).add(new Pair(prefix, arg));
           
           
            step.getExternalOutputs().add(datapair.getElem1());
            tool.getToolOutputs().getOutputs().add(datapair.getElem2());
         
          }
        }
        for(Integer currPos = 0; commandStack.containsKey(currPos); currPos++){
          for(Pair<String,String> elem : commandStack.get(currPos)){
            command_str += " " + elem.getElem1()+elem.getElem2();
          }
        }
        //finished creating command
       
        Galaxy.Tree.Tool.Command.Command command = new Galaxy.Tree.Tool.Command.Command();
        command.setCommand(command_str);
        tool.setToolCommand(command);
       
        //Step step = new Step(getId(), module.getName(), module.getDescription(), module.getId(), module.getVersion(),"", "tool", new Position(module.getPosX(), module.getPosY()));
        //add tool to database
        String pkg  =module.getPackage();
        if(pkg == null)
          pkg = "default";
        GalaxySpecification.getDatabase().addTool(pkg, tool);
        steps.add(step);
        return new Pair<List<Step>,Object>(steps,null);
      }
      public Pair<List<Step>,Object> visit(DataModule dataModule, GalaxyContext parentContext) {
        List<Step> steps = new ArrayList<Step>();
        GalaxyContext childContext = parentContext.copy();
       
        if(dataModule.isDirSource() || dataModule.isDirDump()){
          Printer.log("Directory Data Modules not Supported.");
          return null;
        }
        //do not process sinks
        if(dataModule.isSource() == false ){
          Printer.log("Sink Discarded.");
          return new Pair<List<Step>,Object>(steps, null);
        }
       
        //spawn several inputs if the datamodule has a cardinality greater than 1
        if(dataModule.getValues() != null){
         
          int num_entries = dataModule.getValues().getValues().size();
         
          if(num_entries > 1){
            String parentId = dataModule.getId();
            String outputId = dataModule.getOutputs().get(0).getId();
            for(int i=0 ; i < num_entries; i++){
              DataModule childData = dataModule.copy();
              String childId = nameToCardinalityName(parentId, i);
              String childOutputId = nameToCardinalityName(outputId, i);
              //change childDataID
              childData.setId(childId);
              childData.getValues().clearValues();
              childData.getOutputs().get(0).setId(childOutputId);
                parentContext.getDatabase().addMapping(parentId, childId, null, null);
                parentContext.getDatabase().addMapping(outputId, childOutputId, null, null);
               
                Pair<List<Step>,Object> galDataModule = visit(childData, parentContext);
                steps.addAll(galDataModule.getElem1());
            }
            return new Pair<List<Step>, Object>(steps, null);
          }
        }
        //Step step = new Step(getId(), dataModule.getName(), dataModule.getDescription(), dataModule.getId(), dataModule.getVersion(), "", "tool", new Position(dataModule.getPosX(), dataModule.getPosY()));
        Step step = new Step();
        if(dataModule.isSource() || dataModule.isDirSource()){
          step.setId(getId());
          step.setName(dataModule.getName());
          if(dataModule.getDescription() != null)
            step.setAnnotation(dataModule.getDescription());
          step.setToolType("data_input");
          step.setStepPosition(new Position(dataModule.getPosX(), dataModule.getPosY()));
          step.setToolVersion(dataModule.getVersion());
          //step.setToolState("");
          step.getToolState().getToolState().getSecond().put
          ("input", new PrimitiveOrMap(new Primitive("null")));
          step.getToolState().getToolState().getSecond().put
          ("__page__", new PrimitiveOrMap(new Primitive("0")));
          childContext.setParentStepId(step.getId());
          steps.add(step);
        }
       
        if(dataModule.getInputs() != null){
          for(Parameter p : dataModule.getInputs()){
            Pair<Pair<Object,Object>, Object> ob;
            //get the incoming connections into a module
            //visit the parameter
            ob =  propertyVisitor.visit(p, childContext);
            Input in = (Input) ob.getElem1().getElem2();
            Pair<String,String> statepair = (Pair<String,String>) ob.getElem1().getElem1();
            //update tool, step information
            step.getToolState().addState(statepair.getElem1(), statepair.getElem2());
          }
        }
        if(dataModule.getOutputs() != null){
          for(Output o: dataModule.getOutputs()){
            Pair<Object, Object> ob;
            ob = propertyVisitor.visit(o, childContext);
            Pair<ExternalOutput,Data> datapair= (Pair<ExternalOutput,Data>) ob.getElem1();
            childContext.getDatabase().addMapping(o.getId(), step.getId(), "output");
            datapair.getElem1().setName("output");
            step.getExternalOutputs().add(datapair.getElem1());
          }
        }
       
       
        return new Pair<List<Step>,Object>(steps, null);
      }
    };
  }
  {
    propertyVisitor = new PropertyVisitor<Pair<Object,Object>>(){
     
      public String sanitizeName(String name){
        name = name.replaceAll(" ", "");
       
        return name;
      }
     
      public <T> String commaDelimited(List<T> list){
        String commadelim="";
        int token_count = 1;
        for(Object l : list){
          commadelim += l.toString();
          if(token_count < list.size())
            commadelim += ",";
          token_count++;
        }
        return commadelim;
      }
      public Pair<Pair<Object,Object>, Object> visit(Parameter parameter, GalaxyContext context){
        Galaxy.Tree.Tool.Input.Param.Parameter param = new Galaxy.Tree.Tool.Input.Param.Parameter();
       
        param.setName(sanitizeName(parameter.getName()));
        param.setLabel(parameter.getName()+":"+parameter.getDescription());
        param.setOptional((parameter.isRequired()==false));
     
        String loniType = parameter.getFormat().getType();
        String mytype;
       
        //Determine type of parameter
        if(loniType.equals("File"))
          mytype= "data";
        else if(loniType.equals("String"))
          mytype = "text";
       
        else if(loniType.equals("Number"))
          mytype = "integer";
        else if(loniType.equals("Enumerated")){
          mytype = "select";
        }
        else
          mytype = "unknown";
        param.setType(mytype);
       
        //If we have an enumeration, compile list
        if(mytype.equals("select") &&
           parameter.getFormat().getEnumerations() != null){
          for(String e : parameter.getFormat().getEnumerations()){
            Option opt = new Option();
            opt.setValue(e);
            opt.setContents(e);
            param.getOptionList().add(opt);
          }
        }
        if(mytype.equals("integer")){
          param.setValue("0");
          param.setSize("4");
        }
       
        //Determine format
        if(parameter.getFormat().getFileTypes() != null){
          String formatString="";
          List<FileType> fileTypes = parameter.getFormat().getFileTypes().getFileTypes();
          for(FileType ft : fileTypes){
            formatString += "," + ft.getName();
           
          }
          if(formatString.length() > 0)
            formatString = formatString.substring(1);
          param.setFormat(formatString);
        }
       
       
        //map this id to the galaxy id
        context.getDatabase().addMapping(
            parameter.getId(),
            context.getParentStepId(),
            param.getName());
       
        //String fformat=  parameter.getFileFormat().getType();
        //param.setFormat(fformat);
       
        Pair<String,String> statepair;
        if(mytype.equals("data")){
          statepair = new Pair<String,String>(param.getName(),"null");
        }
        else{
         
          String value = "null";
         
          if(parameter.getValues()!= null &&
             parameter.getValues().getValues().isEmpty() == false)
              value= parameter.getValues().getValues().get(0).getValue().toString();
         
          statepair = new Pair<String,String>(param.getName(), value);
         
         
        }
       
        Pair<Object,Object> toolStepPair;
        toolStepPair= new Pair<Object,Object>(statepair, param);
       
        return new Pair<Pair<Object,Object>, Object>(toolStepPair, null);
      }
     
     
      public Pair<Pair<Object,Object>, Object> visit(Output parameter, GalaxyContext context){
        Data toolData = new Data();
       
        toolData.setName(sanitizeName(parameter.getName()));
        toolData.setLabel(parameter.getDescription());
       
        //Create the external output
        ExternalOutput ep = new ExternalOutput();
        ep.setName(toolData.getName());
       
       
        String mytype;
        String type = parameter.getFormat().getType();
        if(type.equals("File"))
          mytype = "data";
       
        else
          mytype = "unknown";
       
        ep.setType(mytype);
       
        if(parameter.getFormat().getFileTypes() != null){
          String formatString="";
          List<FileType> fileTypes = parameter.getFormat().getFileTypes().getFileTypes();
          for(FileType ft : fileTypes){
            formatString += "," + ft.getName();
           
          }
          formatString = formatString.substring(1);
          toolData.setFormat(formatString);
        }
       
        context.getDatabase().addMapping(parameter.getId(), context.getParentStepId(), toolData.getName());
        return new Pair(new Pair<ExternalOutput, Data>(ep,toolData), null);
      }
     
    };
  }
}
TOP

Related Classes of LONI.visitor.LoniToGalaxyConverter

TOP
Copyright © 2018 www.massapi.com. All rights reserved.
All source code are property of their respective owners. Java is a trademark of Sun Microsystems, Inc and owned by ORACLE Inc. Contact coftware#gmail.com.