Exemple #1
0
void ProcessRunner::run()
{
  if (!process)
    process = new QProcess();
#ifdef WIN32
  QProcessEnvironment env = env.systemEnvironment();
  env.insert("CYGWIN", "nodosfilewarning");
  process->setProcessEnvironment(env);
#endif

  connect(process, SIGNAL(readyReadStandardError()), this, SLOT(updateError()), Qt::DirectConnection);
  connect(process, SIGNAL(readyReadStandardOutput()), this, SLOT(updateText()), Qt::DirectConnection);

  if(arguments)
    process->start(program, *arguments);
  else
    process->start(program);

  interact(process);
  process->waitForFinished(-1); // no timeout

  process->close();

  disconnect(process, SIGNAL(readyReadStandardError()), this, SLOT(updateError()));
  disconnect(process, SIGNAL(readyReadStandardOutput()), this, SLOT(updateText()));
}
  ExitCodes main_(int, const char **) override
  {
    //-------------------------------------------------------------
    // Parsing parameters
    //-------------------------------------------------------------

    String in = getStringOption_("in");
    String out_sirius = getStringOption_("out_sirius");
    String out_csifingerid = getStringOption_("out_fingerid");

    // needed for counting
    int number_compounds = getIntOption_("number"); 

    // Parameter for Sirius3
    QString executable = getStringOption_("executable").toQString();
    const QString profile = getStringOption_("profile").toQString();
    const QString elements = getStringOption_("elements").toQString();
    const QString database = getStringOption_("database").toQString();
    const QString isotope = getStringOption_("isotope").toQString();
    const QString noise = QString::number(getIntOption_("noise"));
    const QString ppm_max = QString::number(getIntOption_("ppm_max"));
    const QString candidates = QString::number(getIntOption_("candidates"));

    bool auto_charge = getFlag_("auto_charge");
    bool no_recalibration = getFlag_("no_recalibration");
    bool iontree = getFlag_("iontree");

    //-------------------------------------------------------------
    // Determination of the Executable
    //-------------------------------------------------------------

    // Parameter executable not provided
    if (executable.isEmpty())
    {
      const QProcessEnvironment env;
      const QString & qsiriuspathenv = env.systemEnvironment().value("SIRIUS_PATH");
      if (qsiriuspathenv.isEmpty())
      {
        writeLog_( "FATAL: Executable of Sirius could not be found. Please either use SIRIUS_PATH env variable or provide with -executable");
        return MISSING_PARAMETERS;
      }
      executable = qsiriuspathenv;
    }
    // Normalize file path
    QFileInfo file_info(executable);
    executable = file_info.canonicalFilePath();

    writeLog_("Executable is: " + executable);
    const QString & path_to_executable = File::path(executable).toQString();

    //-------------------------------------------------------------
    // Calculations
    //-------------------------------------------------------------
    PeakMap spectra;
    MzMLFile f;
    f.setLogType(log_type_);
    f.load(in, spectra);
    std::vector<String> subdirs;

    QString tmp_base_dir = File::getTempDirectory().toQString();
    QString tmp_dir = QDir(tmp_base_dir).filePath(File::getUniqueName().toQString());

    String tmp_ms_file = QDir(tmp_base_dir).filePath((File::getUniqueName() + ".ms").toQString());
    String out_dir = QDir(tmp_dir).filePath("sirius_out");

    //Write msfile
    SiriusMSFile::store(spectra, tmp_ms_file);

    // Assemble SIRIUS parameters
    QStringList process_params;
    process_params << "-p" << profile
                   << "-e" << elements
                   << "-d" << database
                   << "-s" << isotope
                   << "--noise" << noise
                   << "--candidates" << candidates
                   << "--ppm-max" << ppm_max
                   << "--quiet"
                   << "--output" << out_dir.toQString(); //internal output folder for temporary SIRIUS output file storage

    // Add flags
    if (no_recalibration)
    {
      process_params << "--no-recalibration";
    }
    if (!out_csifingerid.empty())
    {
      process_params << "--fingerid";
    }
    if (iontree)
    {
      process_params << "--iontree";
    }
    if (auto_charge)
    {
      process_params << "--auto-charge";
    }

    process_params << tmp_ms_file.toQString();

    // The actual process
    QProcess qp;
    qp.setWorkingDirectory(path_to_executable); //since library paths are relative to sirius executable path
    qp.start(executable, process_params); // does automatic escaping etc... start
    std::stringstream ss;
    ss << "COMMAND: " << executable.toStdString();
    for (QStringList::const_iterator it = process_params.begin(); it != process_params.end(); ++it)
    {
        ss << " " << it->toStdString();
    }
    LOG_DEBUG << ss.str() << endl;
    writeLog_("Executing: " + String(executable));
    writeLog_("Working Dir is: " + path_to_executable);
    const bool success = qp.waitForFinished(-1); // wait till job is finished
    qp.close();

    if (success == false || qp.exitStatus() != 0 || qp.exitCode() != 0)
    {
      writeLog_( "FATAL: External invocation of Sirius failed. Standard output and error were:");
      const QString sirius_stdout(qp.readAllStandardOutput());
      const QString sirius_stderr(qp.readAllStandardOutput());
      writeLog_(sirius_stdout);
      writeLog_(sirius_stderr);
      writeLog_(String(qp.exitCode()));

      return EXTERNAL_PROGRAM_ERROR;
    }

    //-------------------------------------------------------------
    // writing output
    //-------------------------------------------------------------

    //Extract path to subfolders (sirius internal folder structure)
    QDirIterator it(out_dir.toQString(), QDir::Dirs | QDir::NoDotAndDotDot, QDirIterator::NoIteratorFlags);
    while (it.hasNext())
    {
      subdirs.push_back(it.next());
    }

    //sort vector path list
    std::sort(subdirs.begin(), subdirs.end(), sortByScanIndex);

    //Convert sirius_output to mztab and store file
    MzTab sirius_result;
    MzTabFile siriusfile;
    SiriusMzTabWriter::read(subdirs, number_compounds, sirius_result);
    siriusfile.store(out_sirius, sirius_result);

    //Convert sirius_output to mztab and store file
    if (out_csifingerid.empty() == false)
    {
      MzTab csi_result;
      MzTabFile csifile;
      CsiFingerIdMzTabWriter::read(subdirs, number_compounds, csi_result);
      csifile.store(out_csifingerid, csi_result);
    }

    //clean tmp directory if debug level < 2
    if (debug_level_ >= 2)
    {
      writeDebug_("Keeping temporary files in directory '" + String(tmp_dir) + " and msfile at this location "+ tmp_ms_file + ". Set debug level to 1 or lower to remove them.", 2);
    }
    else
    {
      if (tmp_dir.isEmpty() == false)
      {
        writeDebug_("Deleting temporary directory '" + String(tmp_dir) + "'. Set debug level to 2 or higher to keep it.", 0);
        File::removeDir(tmp_dir);
      }
      if (tmp_ms_file.empty() == false)
      {
        writeDebug_("Deleting temporary msfile '" + tmp_ms_file + "'. Set debug level to 2 or higher to keep it.", 0);
        File::remove(tmp_ms_file); // remove msfile
      }
    }

    return EXECUTION_OK;
  }