Mantid
Loading...
Searching...
No Matches
FindFilesWorker.cpp
Go to the documentation of this file.
1// Mantid Repository : https://github.com/mantidproject/mantid
2//
3// Copyright © 2018 ISIS Rutherford Appleton Laboratory UKRI,
4// NScD Oak Ridge National Laboratory, European Spallation Source,
5// Institut Laue - Langevin & CSNS, Institute of High Energy Physics, CAS
6// SPDX - License - Identifier: GPL - 3.0 +
15
16#include <Poco/File.h>
17#include <QApplication>
18#include <boost/algorithm/string.hpp>
19
20#include <utility>
21
22using namespace Mantid::Kernel;
23using namespace Mantid::API;
24using namespace MantidQt::API;
25
32 : QRunnable(), m_parameters(std::move(parameters)) {
33 qRegisterMetaType<MantidQt::API::FindFilesSearchResults>("FindFilesSearchResults");
34}
35
49 // Reset result member vars.
50 std::string error;
51 std::vector<std::string> filenames;
52 QString valueForProperty;
53
54 if (m_parameters.searchText.empty()) {
56 error = "";
57 else
58 error = "No files specified.";
59
60 const auto result = createFindFilesSearchResult(error, filenames, valueForProperty.toStdString());
61 finishSearching(result);
62 return;
63 }
64
66
67 try {
68 // Use the property of the algorithm to find files, if one has been
69 // specified.
70 if (m_parameters.algorithmName.length() != 0 && m_parameters.algorithmProperty.length() != 0) {
71 auto searchResult = getFilesFromAlgorithm();
72 filenames = std::get<0>(searchResult);
73 valueForProperty = QString::fromStdString(std::get<1>(searchResult));
74 }
75 // Else if we are loading run files, then use findRuns.
76 else if (m_parameters.isForRunFiles) {
77 filenames = fileSearcher.findRuns(m_parameters.searchText, m_parameters.extensions);
78 valueForProperty = "";
79 for (auto &filename : filenames) {
80 valueForProperty += QString::fromStdString(filename) + ",";
81 }
82 valueForProperty.chop(1);
83 }
84 // Else try to run a simple parsing on the string, and find the full paths
85 // individually.
86 else {
87 // Tokenise on ","
88 std::vector<std::string> filestext;
89 filestext = boost::split(filestext, m_parameters.searchText, boost::is_any_of(","));
90
91 // Iterate over tokens.
92 auto it = filestext.begin();
93 for (; it != filestext.end(); ++it) {
94 boost::algorithm::trim(*it);
95 std::string result = fileSearcher.getFullPath(*it);
96 Poco::File test(result);
97 if ((!result.empty()) && test.exists()) {
98 filenames.emplace_back(*it);
99 valueForProperty += QString::fromStdString(*it) + ",";
100 } else {
101 throw std::invalid_argument("File \"" + (*it) + "\" not found");
102 }
103 }
104 valueForProperty.chop(1);
105 }
106 } catch (std::exception &exc) {
107 error = exc.what();
108 filenames.clear();
109 } catch (...) {
110 error = "An unknown error occurred while trying to locate the file(s). "
111 "Please contact the development team";
112 filenames.clear();
113 }
114
115 auto result = createFindFilesSearchResult(error, filenames, valueForProperty.toStdString());
116 finishSearching(result);
117}
118
125std::pair<std::vector<std::string>, std::string> FindFilesWorker::getFilesFromAlgorithm() {
126 std::vector<std::string> filenames;
129
130 if (!algorithm)
131 throw std::invalid_argument("Cannot create algorithm " + m_parameters.algorithmName + ".");
132
133 algorithm->initialize();
134 const std::string propName = m_parameters.algorithmProperty;
135 algorithm->setProperty(propName, m_parameters.searchText);
136
137 Property *prop = algorithm->getProperty(propName);
138 std::string valueForProperty = prop->value();
139
140 auto *fileProp = dynamic_cast<FileProperty *>(prop);
141 auto *multiFileProp = dynamic_cast<MultipleFileProperty *>(prop);
142
143 if (fileProp) {
144 filenames.emplace_back(fileProp->value());
145 } else if (multiFileProp) {
146 // This flattens any summed files to a set of single files so that you lose
147 // the information about
148 // what was summed
149 std::vector<std::vector<std::string>> propertyFilenames = algorithm->getProperty(propName);
150 filenames = VectorHelper::flattenVector(propertyFilenames);
151 }
152
153 return std::make_pair(filenames, valueForProperty);
154}
155
161 // Before emitting our search results, we need to check if we have recieved
162 // a signal to disconnect as this search is no longer relevent. By calling
163 // process events here we ensure that if the result is no longer needed the
164 // emitted signal is just ignored.
165 QCoreApplication::processEvents();
166 emit finished(result);
167 QCoreApplication::sendPostedEvents();
168}
169
181 const std::vector<std::string> &filenames,
182 const std::string &valueForProperty) {
184 results.error = error;
185 results.filenames = filenames;
186 results.valueForProperty = valueForProperty;
187 return results;
188}
189
190void FindFilesWorker::disconnectWorker() { this->disconnect(); }
double error
Definition: IndexPeaks.cpp:133
FindFilesWorker(FindFilesSearchParameters parameters)
Constructor.
std::pair< std::vector< std::string >, std::string > getFilesFromAlgorithm()
Use the specified algorithm and property to find files instead of using the FileFinder.
FindFilesSearchParameters m_parameters
Struct to hold the parameters of the search.
void finished(const FindFilesSearchResults &)
Signal emitted after the search is finished, regardless of whether any file was found.
FindFilesSearchResults createFindFilesSearchResult(const std::string &error, const std::vector< std::string > &filenames, const std::string &valueForProperty)
Helper method to create a search result object.
virtual void run() override
Override parent class run().
void finishSearching(const FindFilesSearchResults &result)
Emit search result if required.
This class finds data files given an instrument name (optionally) and a run number.
Definition: FileFinder.h:36
std::string getFullPath(const std::string &filename, const bool ignoreDirs=false) const
Return the full path to the file given its name.
Definition: FileFinder.cpp:105
std::vector< std::string > findRuns(const std::string &hintstr, const std::vector< std::string > &exts={}, const bool useExtsOnly=false) const
Find a list of files file given a hint.
Definition: FileFinder.cpp:527
A specialized class for dealing with file properties.
Definition: FileProperty.h:42
A property to allow a user to specify multiple files to load.
Base class for properties.
Definition: Property.h:94
virtual std::string value() const =0
Returns the value of the property as a string.
static T & Instance()
Return a reference to the Singleton instance, creating it if it does not already exist Creation is do...
std::shared_ptr< IAlgorithm > IAlgorithm_sptr
shared pointer to Mantid::API::IAlgorithm
std::vector< T > flattenVector(const std::vector< std::vector< T > > &v)
A convenience function to "flatten" the given vector of vectors into a single vector.
Definition: VectorHelper.h:69
STL namespace.
POD struct to hold details about the parameters of a file search.
bool isForRunFiles
Whether the search is for experimental run data.
std::string algorithmName
The name of the algorithm to load files with.
std::vector< std::string > extensions
any additional extensions that we want to consider
bool isOptional
Whether the search is optional (i.e. a failed search means no error).
std::string algorithmProperty
The name of the property on the algorithm to use for searching.
std::string searchText
The text to use as a hint to search for files.
POD struct to hold details about the results of a file search.
std::vector< std::string > filenames
A list of filenames that matched the search hint.
std::string valueForProperty
The value to set the algorithm property to.
std::string error
A string repsresenting the error message. Empty if the search succeded.