REST-for-Physics  v2.3
Rare Event Searches ToolKit for Physics
TRestDataBase.cxx
1#include "TRestDataBase.h"
2
3#include <errno.h>
4#include <stdio.h>
5#include <sys/stat.h>
6#include <sys/types.h>
7
8#include "TClass.h"
9#include "TRestStringHelper.h"
10#include "TRestStringOutput.h"
11#include "TRestTools.h"
12#include "TSystem.h"
13#include "TUrl.h"
14
15using namespace std;
16
57
58DBEntry::DBEntry(vector<string> items) {
59 this->runNr = atoi(items[0].c_str());
60 this->type = items[1];
61 this->tag = items[2];
62 this->description = items[3];
63 this->version = items[4];
64}
65
67 fDataEntries.clear();
68 string metaFilename = REST_PATH + "/data/dataURL";
69 if (!TRestTools::fileExists(metaFilename)) {
70 return;
71 } else {
72 vector<int> result;
73 ifstream infile(metaFilename);
74 string s;
75 while (TRestTools::GetLine(infile, s)) {
76 DBEntry info;
77 vector<string> items = Split(s, "\t", true);
78 if (items.size() <= 2) continue;
79 for (auto item : items) {
80 vector<string> pair = Split(item, "=", true);
81 if (pair.size() == 2) {
82 if (pair[0] == "run")
83 info.runNr = atoi(pair[1].c_str());
84 else if (pair[0] == "type")
85 info.type = pair[1];
86 else if (pair[0] == "tag")
87 info.tag = pair[1];
88 else if (pair[0] == "description")
89 info.description = pair[1];
90 else if (pair[0] == "version")
91 info.version = pair[1];
92 else if (pair[0] == "value")
93 info.value = pair[1];
94 }
95 }
96
97 fDataEntries.push_back(info);
98 }
99 }
100}
101
102DBFile DBFile::ParseFile(string _filename) {
103 DBFile file;
104 file.filename = _filename;
105 auto _fullname = TRestTools::ToAbsoluteName(_filename);
106
107 struct stat buf;
108 int result = stat(_fullname.c_str(), &buf);
109
110 if (result != 0) {
111 RESTError << "DBFile::ParseFile: Failed to load file \"" << _fullname << "\"!" << RESTendl;
112 } else {
113 file.fileSize = buf.st_size;
114 file.evtRate = 0;
115 file.quality = true;
116 file.start = buf.st_ctime;
117 file.stop = buf.st_mtime;
118 string sha1result = TRestTools::Execute("sha1sum " + _fullname);
119 string sha1 = Split(sha1result, " ")[0];
120 if (sha1.size() == 40) {
121 for (int i = 0; i < 40; i++) {
122 file.sha1sum[i] = sha1[i];
123 }
124 file.sha1sum[40] = 0;
125 }
126 }
127 return file;
128}
129
130void DBFile::Print() {
131 cout << "----DBFile struct----" << endl;
132 cout << "size: " << fileSize << endl;
133 cout << "event rate: " << evtRate << endl;
134 cout << "sha1sum: " << sha1sum << endl;
135 cout << "quality: " << quality << endl;
136 cout << "start time: " << ToDateTimeString(start) << endl;
137 cout << "stop time: " << ToDateTimeString(stop) << endl;
138}
139
141 auto url = getenv("REST_DBURL");
142 if (url != nullptr) {
143 fConnectionString = url;
144 }
145 Initialize();
146}
147
155 int runNr;
156 string runFilename = REST_USER_PATH + "/runNumber";
157 if (!TRestTools::fileExists(runFilename)) {
158 if (TRestTools::isPathWritable(REST_USER_PATH)) {
159 // we fix the "runNumber" file
160 TRestTools::Execute("echo 1 > " + runFilename);
161 runNr = 1;
162 }
163 } else {
164 ifstream ifs(runFilename);
165 ifs >> runNr;
166 }
167 // the number recorded in "runNumber" file is for the next run, we subtract 1 to get the latest run.
168 return runNr - 1;
169}
170
183int TRestDataBase::set_run(DBEntry info, bool overwrite) {
184 int newRunNr;
185 if (info.runNr == 0) {
186 newRunNr = get_lastrun() + 1;
187 } else if (info.runNr > 0) {
188 newRunNr = info.runNr;
189 } else {
190 return -1;
191 }
192
193 string runFilename = REST_USER_PATH + "/runNumber";
194 if (TRestTools::isPathWritable(REST_USER_PATH)) {
195 TRestTools::Execute("echo " + ToString(newRunNr + 1) + " > " + runFilename);
196 } else {
197 RESTWarning << "runNumber file not writable. auto run number "
198 "increment is disabled"
199 << RESTendl;
200 }
201
202 return newRunNr;
203}
204
209DBEntry TRestDataBase::query_data(DBEntry _info) {
210 vector<DBEntry> match;
211 if (_info.runNr <= 0 && _info.type == "" && _info.tag == "" && _info.description == "" &&
212 _info.version == "")
213 return DBEntry();
214
215 for (unsigned int i = 0; i < fDataEntries.size(); i++) {
216 DBEntry info = fDataEntries[i];
217
218 bool runmatch = (_info.runNr == 0 || info.runNr == 0 || info.runNr == _info.type);
219 bool typematch = (_info.type == "" || info.type == _info.type);
220 bool tagmatch = (_info.tag == "" || info.tag == _info.tag);
221 bool descriptionmatch = (_info.description == "" || info.description == _info.description);
222 bool versionmatch = (_info.version == "" || info.version == _info.version);
223 bool valuematch = (_info.value == "" || info.value == _info.value);
224
225 if (runmatch && typematch && tagmatch && descriptionmatch && versionmatch && valuematch) {
226 match.push_back(info);
227 }
228 }
229
230 if (match.size() == 1) {
231 return match[0];
232 } else if (match.size() > 1) {
233 RESTWarning << "multiple metadata found! returning the first!" << RESTendl;
234 return match[0];
235 } else {
236 return DBEntry();
237 }
238 return DBEntry();
239}
240
241// int TRestDataBase::add_metadata(DBEntry info, string url, bool overwrite) {
242// if (TRestTools::isPathWritable(REST_USER_PATH)) {
243// cout << "error! path not writable" << endl;
244// return -1;
245// }
246//
247// string metaFilename = REST_USER_PATH + "/dataURL";
248//
249// if (info.runNr == 0) {
250// info.runNr = get_lastmetadata();
251// }
252// fDataEntries.push_back({info, url});
253//
254// std::ofstream file(metaFilename, std::ios::app);
255// file << "\"" << info.runNr << "\" ";
256// file << "\"" << info.type << "\" ";
257// file << "\"" << info.tag << "\" ";
258// file << "\"" << info.description << "\" ";
259// file << "\"" << info.version << "\" ";
260// file << "\"" << url << "\" ";
261// file << endl;
262// file.close();
263//
264// return info.runNr;
265//}
266//
virtual void Initialize()
default: read the dataURL file
TRestDataBase()
default constructor, setting fConnectionString according to the env
virtual int get_lastrun()
get the latest run id in database
virtual DBEntry query_data(DBEntry info)
virtual int set_run(DBEntry info, bool overwrite=true)
add/update a run, with run info as struct DBEntry. returns the added run id
static std::string Execute(std::string cmd)
Executes a shell command and returns its output in a string.
static bool fileExists(const std::string &filename)
Returns true if the file (or directory) with path filename exists.
Definition: TRestTools.cxx:728
static bool isPathWritable(const std::string &path)
Returns true if the path given by argument is writable.
Definition: TRestTools.cxx:778
static std::istream & GetLine(std::istream &is, std::string &t)
It reads the next line from the incoming istream and puts it in the string argument t....
static std::string ToAbsoluteName(const std::string &filename)
It takes a path and returns its absolute path.
Definition: TRestTools.cxx:868
std::vector< std::string > Split(std::string in, std::string separator, bool allowBlankString=false, bool removeWhiteSpaces=false, int startPos=-1)
Split the input string according to the given separator. Returning a vector of fragments.
std::string ToDateTimeString(time_t time)
Format time_t into string.