KaliVeda
Toolkit for HIC analysis
KVDataSet.cpp
1 /*
2 $Id: KVDataSet.cpp,v 1.41 2009/03/11 14:22:41 franklan Exp $
3 $Revision: 1.41 $
4 $Date: 2009/03/11 14:22:41 $
5 $Author: franklan $
6 */
7 
8 #include "TMethodCall.h"
9 #include "KVDataSet.h"
10 #include "KVDataRepository.h"
11 #include "KVDataRepositoryManager.h"
12 #include "KVDataSetManager.h"
13 #include "TSystem.h"
14 #include "TObjArray.h"
15 #include "TObjString.h"
16 #include "KVDBSystem.h"
17 #include "KVDBRun.h"
18 #include "TEnv.h"
19 #include "KVAvailableRunsFile.h"
20 #include "KVNumberList.h"
21 #include "TPluginManager.h"
22 #include "TClass.h"
23 #include "KVRunFile.h"
24 
25 using namespace std;
26 
28 
29 KVDataSet* gDataSet;
30 
31 
34 
36 {
37  //Default constructor
38  fRepository = nullptr;
39  fDataBase = nullptr;
40  fAllTasks.SetOwner(kTRUE);
41  fTasks.SetOwner(kFALSE);
42 }
43 
44 
45 
50 
52 {
53  // \param type name of data type ('raw', 'recon', ...)
54  // \returns pointer to available runs file object for given data type
55  // \note if no data repository is associated with dataset, returns nullptr
56  if (!fRepository) return nullptr;
57  KVAvailableRunsFile* avrf =
58  (KVAvailableRunsFile*) fAvailableRuns.FindObjectByName(type);
59  if (!avrf) {
60  avrf = fRepository->NewAvailableRunsFile(type, this);
61  fAvailableRuns.Add(avrf);
62  }
63  return avrf;
64 }
65 
66 
67 
82 
84 {
85  //Returns name of file containing database for dataset.
86  //
87  //This is fixed as `DataBase.root.M.mm` where
88  // - `M` is the current major version number
89  // - `m` is the current minor version number
90  //
91  //(fixed to be consistent with CMake function INSTALL_KALIVEDA_DATASETS which sets up
92  //the Makefile for each dataset which automatically triggers rebuilding of the ROOT file
93  //when source files change: thus we must have the right file name!)
94  //
95  //This in order to avoid problems if several different versions of KaliVeda
96  //use the same working directory (in user's `$HOME/.kaliveda`) to write the
97  //database files, which are often incompatible between versions
98 
99  TString n = "DataBase.root";
100  n.Append(Form(".%d.%d", GetKVMajorVersion(),
101  GetKVMinorVersion()));
102  return n;
103 }
104 
105 
106 
111 
113 {
114  //\returns name of database object in database file.
115  //
116  //If this is not set explicitly with SetDBName(), we use the name of the dataset by default
117 
118  return (fDBName != "" ? fDBName.Data() : GetName());
119 }
120 
121 
122 
123 
126 
127 void KVDataSet::OpenDBFile(const Char_t* full_path_to_dbfile) const
128 {
129  //Open the database from a file on disk.
130 
131  TDirectory* work_dir = gDirectory; //keep pointer to current directory
132  fDBase.reset(new TFile(full_path_to_dbfile, "READ"));
133 
134  if (fDBase->IsOpen()) {
135  fDataBase = dynamic_cast<KVExpDB*>(fDBase->Get(GetDBName()));
136  if (!fDataBase) {
137  Error("OpenDBFile", "%s not found in file %s", GetDBName().Data(),
138  GetDBFileName().Data());
139  }
140  else {
141  fDataBase->ReadObjects(fDBase.get()); // read any associated objects
142  }
143  work_dir->cd(); //back to initial working directory
144  }
145 }
146 
147 
148 
149 
152 
154 {
155  // \returns full path to file where database is written on disk
156 
157  TString dbfile = GetDBFileName();
158  TString dbfile_fullpath;
159  TString tmp;
160 
161  // If this dataset is just an alias for another dataset i.e. if DataSet.Directory
162  // is set with just the name of another dataset (not a full path to dataset files)
163  // then the database file should be written/found under the name of the alias.
164  TString dataset_alias = GetDataSetEnv("DataSet.Directory", GetName());
165  TString db_alias = GetName();
166  if (!gSystem->IsAbsoluteFileName(dataset_alias)) db_alias = dataset_alias;
167 
168  AssignAndDelete(tmp, gSystem->ConcatFileName(GetDATABASEFilePath(), db_alias.Data()));
169  AssignAndDelete(dbfile_fullpath, gSystem->ConcatFileName(tmp.Data(), dbfile.Data()));
170  return dbfile_fullpath;
171 }
172 
173 
174 
177 
179 {
180  //Check configuration variables to see if the task parameters have been "tweaked" for the dataset.
181 
182  KVString envar = GetDataSetEnv(Form("%s.DataAnalysisTask.Title", t->GetName()));
183  if (envar != "") t->SetTitle(envar);
184  envar = GetDataSetEnv(Form("%s.DataAnalysisTask.Analyser", t->GetName()));
185  if (envar != "") t->SetDataAnalyser(envar);
186  envar = GetDataSetEnv(Form("%s.DataAnalysisTask.UserClass.Base", t->GetName()));
187  if (envar != "") t->SetUserBaseClass(envar);
188  envar = GetDataSetEnv(Form("%s.DataAnalysisTask.Prereq", t->GetName()));
189  if (envar != "") t->SetPrereq(envar);
190  envar = GetDataSetEnv(Form("%s.DataAnalysisTask.UserClass.ExtraACliCIncludes", t->GetName()));
191  if (envar != "") t->SetExtraAClicIncludes(envar);
192  Int_t nev = (Int_t)GetDataSetEnv(Form("%s.DataAnalysisTask.StatusUpdateInterval", t->GetName()), 0.0);
193  if (nev > 0) t->SetStatusUpdateInterval(nev);
194 }
195 
196 
197 
198 
202 
204 {
205  // Write the experiment database for this dataset to disk (ROOT file), creating and setting
206  // permissions for any required directories
207 
208  TString dbfile_fullpath = GetFullPathToDB();
209  TString tmp = gSystem->DirName(dbfile_fullpath.Data()); //full path to directory $KVROOT/db/[dataset name]
210 
211  if (gSystem->AccessPathName(tmp.Data())) { // directory $KVROOT/db/[dataset name] does not exist
212 
213  if (gSystem->mkdir(tmp.Data()) == -1) { // problem creating $KVROOT/db/[dataset name]
214 
215  TString tmp2 = gSystem->DirName(tmp.Data());// full path to directory $KVROOT/db
216 
217  if (gSystem->AccessPathName(tmp2.Data())) { // directory $KVROOT/db does not exist
218 
219  if (gSystem->mkdir(tmp2.Data()) == -1) { // problem creating $KVROOT/db
220  Error("SaveDataBase", "Cannot create directory %s required to save database",
221  tmp2.Data());
222  return;
223  }
224  gSystem->Chmod(tmp2.Data(), 0775);
225  }
226  else {
227  Error("SaveDataBase", "Cannot create directory %s required to save database, even though %s exists: check disk space ?",
228  tmp.Data(), tmp2.Data());
229  return;
230  }
231  //try again
232  if (gSystem->mkdir(tmp.Data()) == -1) {
233  Error("SaveDataBase", "Cannot create directory %s required to save database",
234  tmp.Data());
235  return;
236  }
237  else {
238  gSystem->Chmod(tmp.Data(), 0775);
239  }
240  }
241  else {
242  gSystem->Chmod(tmp.Data(), 0775);
243  }
244  }
245 
246  WriteDBFile(dbfile_fullpath.Data());
247 }
248 
249 
250 
251 
254 
255 void KVDataSet::WriteDBFile(const Char_t* full_path_to_dbfile) const
256 {
257  //Write the database to disk.
258 
259  TDirectory* work_dir = gDirectory; //keep pointer to current directory
260  if (!fDataBase) {
261  Error("WriteDBFile", "Database has not been built");
262  return;
263  }
264  fDBase.reset(new TFile(full_path_to_dbfile, "recreate"));
265  fDBase->cd(); //set as current directory (maybe not necessary)
266  fDataBase->Write(GetDBName()); //write database to file with given name
267  fDataBase->WriteObjects(fDBase.get()); //write any associated objects
268  fDBase->Write(); // write file header etc.
269  fDBase->Close(); // close file
270  gSystem->Chmod(full_path_to_dbfile, 0664); // set permissions to rw-rw-r--
271  work_dir->cd(); //back to initial working directory
272 }
273 
274 
275 
286 
288 {
289  //\returns pointer to database associated with this dataset.
290  //
291  //Opens, updates or creates database file if necessary
292  //(the database is automatically rebuilt if the source files are
293  //more recent than the last database file).
294  //
295  //\param[in] opt optional option string:
296  // - if opt="update": force regeneration of the database from source files in dataset directory
297  // - if opt="minimal": if database not built/out of date, only build runs/systems database
298 
299  OpenDataBase(opt);
300  return fDataBase;
301 }
302 
303 
304 
315 
316 void KVDataSet::OpenDataBase(const TString& opt) const
317 {
318  //Open the database for this dataset.
319  //
320  //If the database does not exist or is older than the source files
321  //the database is automatically rebuilt (see DataBaseNeedUpdate()).
322  //
323  //\param[in] opt build option
324  //
325  // - if opt="update" we force rebuilding of the database
326  // - if opt="minimal" only a minimal database of runs & systems for the dataset is built
327 
328  TString _opt(opt);
329  _opt.ToUpper();
330  auto update = (_opt=="UPDATE");
331  auto minimal = (_opt=="MINIMAL");
332 
333  auto rebuild_database = [&]()
334  {
335  Info("OpenDataBase", "Updating database file");
336  fDataBaseUpdateInProgress = true;
337  //check if it is the currently active database (gDataBase),
338  //in which case we must 'cd()' to it after rebuilding
339  auto is_glob_db = (fDataBase == gExpDB);
340  if (fDataBase) {
341  delete fDataBase;
342  fDataBase = 0;
343  }
344  fDataBase = KVExpDB::MakeDataBase(GetDBName(), GetDataSetDir(), minimal);
345  if (!fDataBase) {
346  // no database defined for dataset
347  Info("OpenDataBase", "No database defined for dataset");
348  fDataBaseUpdateInProgress = false;
349  return;
350  }
351  SaveDataBase();
352  if (fDataBase && is_glob_db) fDataBase->cd();
353  fDataBaseUpdateInProgress = false;
354  };
355 
356  if (update || DataBaseNeedsUpdate())
357  {
358  //if option="update" or database out of date or does not exist, (re)build the database
359  rebuild_database();
360  }
361  else if (!fDataBase) {
362  // if database is not in memory at this point, we need to
363  // open the database file and read in the database
364 
365  //load plugin for database
366  if (!LoadPlugin("KVExpDB", GetDBName())) {
367  Error("GetDataBase", "Cannot load required plugin library");
368  return;
369  }
370  //look for database file in dataset subdirectory
371  TString dbfile_fullpath = GetFullPathToDB();
372  //open database file
373  OpenDBFile(dbfile_fullpath.Data());
374 
375  // if the previously built database was minimal but nobody asked for
376  // a minimal database (=> they want the full monty), we rebuild a full database
377  if(fDataBase && fDataBase->IsMinimal() && !minimal)
378  rebuild_database();
379  }
380  else if(fDataBase && fDataBase->IsMinimal() && !minimal)
381  {
382  // database is already open, but was only a minimal build
383  // now we want the full monty!
384  rebuild_database();
385  }
386 }
387 
388 
389 
390 
393 
395 {
396  //Print dataset information
397  cout << "Dataset name=" << GetName() << " (" << GetTitle() << ")";
398  if (IsAvailable()) {
399  cout << " [ AVAILABLE: ";
400  cout << fDatatypes.Data();
401  cout << "]";
402  }
403  else
404  cout << " [UNAVAILABLE]";
405  cout << endl;
406 }
407 
408 
409 
416 
417 void KVDataSet::Print(Option_t* opt) const
418 {
419  //Print dataset information
420  //
421  //param[in] opt select optional output formats:
422  // - if string contains "tasks", print numbered list of tasks that can be performed
423  // - if string contains "data", print list of available data types
424 
425  TString Sopt(opt);
426  Sopt.ToUpper();
427  if (Sopt.Contains("TASK")) {
428  if (!GetNtasks()) {
429  cout << " *** No available analysis tasks ***"
430  << endl;
431  return;
432  }
433  else {
434  for (int i = 1; i <= GetNtasks(); i++) {
435  KVDataAnalysisTask* dat = GetAnalysisTask(i);
436  cout << "\t" << i << ". " << dat->GetTitle() << endl;
437  }
438  }
439  cout << endl;
440  }
441  else if (Sopt.Contains("DATA")) {
442  cout << "Available data types: " << fDatatypes.Data() << endl;
443  }
444  else {
445  ls(opt);
446  }
447 }
448 
449 
450 
459 
461 {
462  //Check if this data set is physically present and available for analysis.
463  //
464  //In other words we check if the value of GetDataPathSubdir() is a subdirectory
465  //of the current data repository.
466  //If so, we proceed to check for the existence of sudirectories corresponding
467  // to any of the datatypes associated with the dataset.
468  //
469 
470  if (!fRepository) // for a stand-alone KVDataSetManager not linked to a KVDataRepository,
471  SetAvailable(); // all known datasets are 'available'
472  else
473  SetAvailable(fRepository->CheckSubdirExists(GetDataPathSubdir()));
474  if (!IsAvailable())
475  return;
476  //check subdirectories
477  KVString data_types = GetDataSetEnv("KVDataSet.DataTypes", "");
478  if (data_types == "") {
479  Warning("CheckAvailable", "No datatypes defined for this dataset: %s\nCheck value of KVDataSet.DataTypes or %s.KVDataSet.DataTypes",
480  GetName(), GetName());
481  SetAvailable(kFALSE);
482  }
483  fDatatypes = "";
484  // loop over data types
485  data_types.Begin(" ");
486  while (!data_types.End()) {
487  KVString type = data_types.Next(kTRUE);
488  if (!fRepository ||
489  (fRepository && fRepository->CheckSubdirExists(GetDataPathSubdir(), GetDataTypeSubdir(type.Data())))
490  ) {
491  AddAvailableDataType(type.Data());
492  }
493  }
494  //check at least one datatype exists
495  SetAvailable(fDatatypes != "");
496  //check user name against allowed groups
497  if (!CheckUserCanAccess()) {
498  SetAvailable(kFALSE);
499  return;
500  }
501 }
502 
503 
504 
506 
508 {
509  if (fDatatypes != "") fDatatypes += " ";
510  KVString _type = type;
511  _type.Remove(TString::kBoth, ' '); //strip whitespace
512  fDatatypes += _type;
513 }
514 
515 
516 
523 
525 {
526  // Add to fAllTasks list any data analysis task in list 'task_list'
527  //
528  // Add to fTasks list any data analysis task in list 'task_list' whose pre-requisite datatype is present for this dataset.
529  //
530  // Any dataset-specific "tweaking" of the task (including the prerequisite datatype) is done here.
531 
532  TString availables = gEnv->GetValue(Form("%s.DataAnalysisTask", GetName()), "");
533  fAllTasks.Clear();
534  fTasks.Clear();
535  TIter nxt(task_list);
536  KVDataAnalysisTask* dat;
537  while ((dat = (KVDataAnalysisTask*) nxt())) {
538  //make new copy of default analysis task
539  if (availables == "" || availables.Contains(dat->GetName())) {
540  KVDataAnalysisTask* new_task = new KVDataAnalysisTask(*dat);
541  //check if any dataset-specific parameters need to be changed
542  SetDataSetSpecificTaskParameters(new_task);
543  fAllTasks.Add(new_task);
544  // add tasks with available prerequisite data to fTasks
545  if (HasDataType(new_task->GetPrereq())) {
546  fTasks.Add(new_task);
547  }
548  }
549  }
550 }
551 
552 
553 
557 
559 {
560  //Returns the number of tasks associated to dataset which are compatible
561  //with the available data
562 
563  return fTasks.GetSize();
564 }
565 
566 
567 
572 
574 {
575  //Return kth analysis task in list of available tasks.
576  //
577  //\param[in] k task number in range [1, GetNtasks()]. Corresponds to the number shown next to the title of the task when Print("tasks") is called
578  return (KVDataAnalysisTask*) fTasks.At(k - 1);
579 }
580 
581 
582 
587 
589 {
590  //\returns list of available systems for this dataset and the given datatype
591  //
592  //\param[in] datatype type of data
593 
594  if (!GetAvailableRunsFile(datatype)) {
595  Error("GetListOfAvailableSystems(const Char_t*)",
596  "No available runs file for type %s", datatype.Data());
597  return {};
598  }
599  return GetAvailableRunsFile(datatype)->GetListOfAvailableSystems();
600 }
601 
602 
603 
608 
610 {
611  //\returns list of available systems for this dataset and the prerequisite datatype for the given analysis task
612  //
613  //\param[in] datan data analysis task
614 
615  return GetListOfAvailableSystems(datan->GetPrereq());
616 }
617 
618 
619 
627 
629 {
630  //\returns list of available runfiles for this dataset and the given datatype and system.
631  //
632  //\param[in] datatype type of data
633  //\param[in] systol pointer to system
634  //
635  //If no systems are defined for the dataset then we return a list of available runfiles for the given datatype
636 
637  if (!GetAvailableRunsFile(datatype)) {
638  Error("GetListOfAvailableSystems(const Char_t*)",
639  "No available runs file for type %s", datatype.Data());
640  return {};
641  }
642  return GetAvailableRunsFile(datatype)->GetListOfAvailableRunFilesForSystem(systol);
643 }
644 
645 
646 
654 
656 {
657  //\returns list of available runfiles for this dataset, given system, and the prerequisite datatype for the given analysis task
658  //
659  //\param[in] datan data analysis task
660  //\param[in] pointer to system
661  //
662  //If no systems are defined for the dataset then we return a list of available runfiles for the given datatype
663 
664  return GetListOfAvailableRunFilesForSystem(datan->GetPrereq(), systol);
665 }
666 
667 
668 
671 
673 {
674  // \returns the list of systems corresponding to the given list of runfiles & datatype
675 
676  if (!GetAvailableRunsFile(datatype)) {
677  Error("GetSystemsForRunFiles",
678  "No available runs file for type %s", datatype.Data());
679  return {};
680  }
681  return GetAvailableRunsFile(datatype)->GetSystemsForRunFiles(rl);
682 }
683 
684 
685 
706 
707 void KVDataSet::SetName(const char* name)
708 {
709  // Set name of dataset
710  //
711  // Also sets path to directory containing database informations
712  // for this dataset, i.e. list of runs, systems, calibration files etc.
713  //
714  // By default, just the name of the dataset is used, i.e.
715  // `[DATADIR]/name`
716  // (where `DATADIR` = path given by KVBase::GetDATADIRFilePath())
717  //
718  // However, if the variable
719  //~~~
720  // [name].DataSet.Directory: [path]
721  //~~~
722  // has been set, the value of `[path]` will be used:
723  // - if [path] is an absolute path name, it will be used as such
724  // - if [path] is an incomplete or relative path, it will be prepended with `[DATADIR]/`
725  //
726  // This allows to use one dataset as an alias for another, by setting `DataSet.Directory`
727  // to the name of an existing dataset
729  TString path = GetDataSetEnv("DataSet.Directory", name);
730  if (gSystem->IsAbsoluteFileName(path)) fCalibDir = path;
731  else {
732  // in this case (not an absolute path but just the name of another dataset)
733  // this dataset is an alias for another dataset.
734  fCalibDir = GetDATADIRFilePath(path);
735  // the name of the database object is the name of the "true" dataset
736  SetDBName(path);
737  }
738 }
739 
740 
741 
744 
746 {
747  //\returns full path to directory containing database and calibration/identification parameters etc. for this dataset.
748 
749  return fCalibDir.Data();
750 }
751 
752 
753 
766 
767 void KVDataSet::cd() const
768 {
769  // Makes this dataset the "currently active" or default dataset.
770  //
771  //At the same time, the database and data repository associated with
772  //this dataset also become the "currently active" ones:
773  //
774  // | global pointer | represents | base class |
775  // |----------------|------------|------------|
776  // | `gDataSet` | active dataset | KVDataSet |
777  // | `gExpDB` | associated experimental database | KVExpDB |
778  // | `gDataRepository` | repository containing runfiles | KVDataRepository |
779  //
780 
781  gDataSet = const_cast<KVDataSet*>(this);
782  if (fRepository) fRepository->cd();
783  KVExpDB* db = GetDataBase();
784  if (db) db->cd();
785 }
786 
787 
788 
816 
818 {
819  // Open file containing data of given datatype for given run number of this dataset.
820  //
821  // \returns a pointer to the opened file; if the file is not available, we return nullptr.
822  //
823  // The user must cast the returned pointer to the correct class, which will
824  // depend on the data type and the dataset
825  //
826  // **SPECIAL CASE: MFM data with EBYEDAT frames**
827  //
828  // If the variable
829  //
830  //~~~~~~~~~~~~~~~~~~~~~~~~~
831  // [dataset].MFM.WithEbyedat: yes
832  //~~~~~~~~~~~~~~~~~~~~~~~~~
833  //
834  // is set, then we expect to find the necessary `ACTIONS_*` files in the dataset directory
835  // in subdirectory `ebyedat` (they should have the same names as the data files prefixed by
836  // `ACTIONS_[expname].CHC_PAR.`).
837  //
838  // If in addition the variable
839  //
840  //~~~~~~~~~~~~~~~~~~~~~~~~~
841  // [dataset].MFM.EbyedatActionsExpName: [expname]
842  //~~~~~~~~~~~~~~~~~~~~~~~~~
843  //
844  // is set, then we use the same `ACTIONS` file for all runs, with name `ACTIONS_[expname].CHC_PAR`
845 
846 
847  if (!strcmp(type, "raw") && !strcmp(GetDataSetEnv("MFM.WithEbyedat", ""), "yes")) {
848  TString ebydir = GetDataSetDir();
849  ebydir += "/ebyedat";
850  gEnv->SetValue("KVMFMDataFileReader.ActionsDirectory", ebydir);
851  if (strcmp(GetDataSetEnv("MFM.EbyedatActionsExpName", ""), ""))
852  gEnv->SetValue("KVMFMDataFileReader.ActionsExpName", GetDataSetEnv("MFM.EbyedatActionsExpName", ""));
853  TObject* f = GetRepository()->OpenDataSetRunFile(this, type, run, GetName());
854  // reset in case another dataset opens a raw MFM file without EBYEDAT data
855  gEnv->SetValue("KVMFMDataFileReader.ActionsDirectory", "");
856  gEnv->SetValue("KVMFMDataFileReader.ActionsExpName", "");
857  return f;
858  }
859  return GetRepository()->OpenDataSetRunFile(this, type, run, GetName());
860 }
861 
862 
863 
864 
868 
870  const run_index_t& run) const
871 {
872  //\return full path to file containing data of given datatype for given run/index of this dataset
873  // \note only works for available run files, if their is no file in the repository for this run, the returned path will be empty
874 
875  TString file("");
876  if (fRepository) file = GetRunfileName(type, run);
877  if (file == "")
878  return file.Data();
879  return fRepository->GetFullPathToOpenFile(this, type, file.Data());
880 }
881 
882 
883 
884 
888 
890 {
891  //\return name of file containing data of given datatype for given run/index of this dataset
892  //\note only works for available run files, if there is no file in the repository for this run, the returned path will be empty
893 
894  if (!HasDataType(type)) {
895  Error("GetRunfileName",
896  "No data of type \"%s\" available for dataset %s", (const char*)type,
897  GetName());
898  return 0;
899  }
900  //get name of file from available runs file
901  return GetAvailableRunsFile(type)->GetFileName(run);
902 }
903 
904 
905 
906 
912 
913 std::optional<TDatime> KVDataSet::GetRunfileDate(const KVString& type, const run_index_t& run)
914 {
915  //\return date of file containing data of given datatype for given run/index of this dataset
916  //
917  //\note only works for available runfiles, if there is no file in the repository for this run/index,
918  //an error will be printed and std::optional will not contain a value
919 
920  if (!HasDataType(type)) {
921  Error("GetRunfileDate",
922  "No data of type \"%s\" available for dataset %s", (const char*)type,
923  GetName());
924  return std::nullopt;
925  }
926  //get date of file from available runs file
927  TDatime date;
929  if (!GetAvailableRunsFile(type)->GetRunInfo(run, date, filename)) {
930  Error("GetRunfileDate",
931  "Runfile not found for run %d index %d (data type: %s)", run.run(), run.index(), (const char*)type);
932  return std::nullopt;
933  }
934  return date;
935 }
936 
937 
938 
961 
962 std::optional<run_index_t> KVDataSet::GetRunNumberFromFileName(const TString& datatype, const TString& filename)
963 {
964  // \returns run number and eventual index by parsing the name of a runfile for given datatype. if filename does not have correct format, returns std::nullopt
965  //
966  // If the runfile in question was generated using an index multiplier, e.g. if it contains the number
967  // '17001' when the index multiplier defined for the dataset is 1000, we return '17' as the
968  // run number and '1' as the index.
969  //
970  // Usage examples (using global pointer gDataSet to currently 'active' dataset):
971  //~~~{.cpp}
972  //auto run = gDataSet->GetRunNumberFromFileName(filename);
973  //
974  //if(!run) // no value (std::nullopt) returned
975  //{
976  // std::cerr << "Filename " << filename << " is not right format\n";
977  //}
978  //else
979  //{
980  // std::cout << "Filename " << filename << " corresponds to run number " << run.value().run();
981  // if(run.has_index()) std::cout << ", file index = " << run.index();
982  // std::cout << std::endl;
983  //}
984  //~~~
985 
986  auto arf = GetAvailableRunsFile(datatype);
987  auto v = arf->IsRunFileName(filename);
988  if (!v) return v;
989  // if the returned value has a non-null index, there is nothing more to do
990  if (v.value().has_index()) return v;
991  int r = v.value().run();
992  // check if returned run number actually consists of run*multiplier+index
993  if (GetDataBase()->HasIndexMultiplier() && r > GetDataBase()->GetIndexMultiplier()) {
994  r /= GetDataBase()->GetIndexMultiplier();
995  int i = v.value().run() % GetDataBase()->GetIndexMultiplier();
996  return run_index_t{r, i};
997  }
998  return v;
999 }
1000 
1001 
1002 
1003 
1008 
1010 {
1011  //We check the availability of the run by looking in the available runs file associated
1012  //with the given datatype.
1013 
1014  //check data type is available
1015  if (!HasDataType(type)) {
1016  Error("CheckRunfileAvailable",
1017  "No data of type \"%s\" available for dataset %s", (const char*)type,
1018  GetName());
1019  return 0;
1020  }
1021  return GetAvailableRunsFile(type)->CheckAvailable(run);
1022 }
1023 
1024 
1025 
1026 
1041 
1042 const Char_t* KVDataSet::GetBaseFileName(const Char_t* type, const run_index_t& run) const
1043 {
1044  //PRIVATE METHOD: Returns base name of data file containing data for the run of given datatype.
1045  //The filename corresponds to one of the formats defined in $KVROOT/KVFiles/.kvrootrc
1046  //by variables like:
1047  //
1048  //~~~
1049  //[dataset].DataSet.RunFileName.[type]: run%R.dat
1050  //~~~
1051  //
1052  //%R will be replaced with the run number
1053  //
1054  //IF the format contains '%D' it will be replaced with the current date and time
1055  //
1056  // Any index will be appended at the end: ".index"
1057 
1058  static TString tmp;
1059  //get format string
1060  TString fmt = GetDataSetEnv(Form("DataSet.RunFileName.%s", type));
1061  TString run_num(Form("%d", run.run()));
1062  KVDatime now;
1063  TString date(now.AsSQLString());
1064  tmp = fmt;
1065  tmp.ReplaceAll("%R", run_num);
1066  if (fmt.Contains("%D")) {
1067  tmp.ReplaceAll("%D", date);
1068  }
1069  if (run.has_index()) tmp += Form(".%d", run.index());
1070  return tmp.Data();
1071 }
1072 
1073 
1074 
1075 
1085 
1087 {
1088  //Update list of available runs for given data 'type'
1089  //
1090  //As we never clear the sqlite database of any previously existing runfiles
1091  //beforehand, it is possible that newer versions of said files have been
1092  //added and that we will therefore end up with multiple copies of files in the
1093  //database. Therefore we perform an automatic 'CleanRunfileDataBase' afterwards,
1094  //but only to remove runfiles which no longer physically exist
1095 
1096  //check data type is available
1097  if (!HasDataType(type)) {
1098  Error("UpdateAvailableRuns",
1099  "No data of type \"%s\" available for dataset %s", (const char*)type,
1100  GetName());
1101  }
1102  KVAvailableRunsFile* a = GetAvailableRunsFile(type);
1103  a->Update();
1104  CleanRunfileDataBase(type);
1105 }
1106 
1107 
1108 
1109 
1114 
1116 {
1117  // Create a new runfile for the dataset of given datatype.
1118  // (only if this dataset is associated with a data repository)
1119  // Once the file has been filled, use CommitRunfile to submit it to the repository.
1120 
1121  if (!fRepository) return nullptr;
1122  TString tmp = GetBaseFileName(type, run);
1123  //turn any spaces into "_"
1124  tmp.ReplaceAll(" ", "_");
1125  return fRepository->CreateNewFile(this, type, tmp.Data());
1126 }
1127 
1128 
1129 
1130 
1139 
1140 void KVDataSet::DeleteRunfile(const KVString& type, const run_index_t& run, Bool_t confirm)
1141 {
1142  // Delete the file for the given run/index of data type "type" from the repository.
1143  // By default, confirm=kTRUE, which means that the user will be asked to confirm
1144  // that the file should be deleted. If confirm=kFALSE, no confirmation will be asked
1145  // for and the file will be deleted straight away.
1146  //
1147  // WARNING: this really does DELETE files in the repository, they cannot be
1148  // retrieved once they have been deleted.
1149 
1150  if (!fRepository) return;
1151 
1152  //get name of file to delete
1153  TString filename = GetAvailableRunsFile(type)->GetFileName(run);
1154  if (filename == "") {
1155  Error("DeleteRunfile", "Run %s of type %s does not exist.",
1156  run.as_string().Data(), (const char*)type);
1157  return;
1158  }
1159  //delete file
1160  //prevent accidental deletion of certain types of runfiles
1161  KVString doNotDelete = GetDataSetEnv("DataSet.RunFile.DoNotDelete", "all");
1162  if (doNotDelete == "all" || doNotDelete.Contains(type)) {
1163  Error("DeleteRunFile", "%s files cannot be deleted", (const char*)type);
1164  return;
1165  }
1166  fRepository->DeleteFile(this, type, filename.Data(), confirm);
1167  //was file deleted ? if so, remove entry from available runs file
1168  if (!fRepository->CheckFileStatus(this, type, filename.Data()))
1169  GetAvailableRunsFile(type)->Remove(run);
1170 }
1171 
1172 
1173 
1174 
1186 
1187 void KVDataSet::DeleteRunfiles(const Char_t* type, const run_index_list& nl, Bool_t confirm)
1188 {
1189  // Delete files corresponding to a list of runs/index of data type "type" from the repository.
1190  //
1191  // By default, confirm=kTRUE, which means that the user will be asked to confirm
1192  // that each file should be deleted.
1193  //
1194  // If confirm=kFALSE, no confirmation will be asked for and the file will be deleted straight away.
1195  //
1196  // if "nl" is empty (default value) all runs of the dataset corresponding to the given type will be deleted
1197  //
1198  // WARNING: this really does DELETE files in the repository, they cannot be retrieved once they have been deleted.
1199 
1200  auto NL = nl;
1201  if (NL.IsEmpty()) NL = GetRunList(type);
1202  if (NL.IsEmpty()) return;
1203  for (auto& r : NL)
1204  DeleteRunfile(type, r, confirm);
1205 }
1206 
1207 
1208 
1209 
1217 
1218 run_index_list KVDataSet::GetRunList_DateSelection(const TString& type, const KVUnownedList& systems, std::optional<KVDatime> min_date, std::optional<KVDatime> max_date)
1219 {
1220  // Prints out and returns list of runs after date / time selection
1221  //
1222  // Runs generated between ]min;max[ are selected
1223  // - if min=NULL runs with date <max are selected
1224  // - if max=NULL runs with date >min are selected
1225  // - if max and min are NULL returns empty list
1226 
1227  if (!min_date && !max_date) return {};
1228 
1229  if (min_date) printf("date minimum %s\n", min_date.value().AsString());
1230  if (max_date) printf("date maximum %s\n", max_date.value().AsString());
1231 
1232  run_index_list numb;
1233 
1234  for (auto _sys : systems) {
1235  auto sys = (KVDBSystem*)_sys;
1236  auto lrun = GetListOfAvailableRunFilesForSystem(type, sys);
1237 
1238  for (auto _run : lrun) {
1239  auto run = (KVRunFile*)_run;
1240 
1241  if (min_date && max_date) {
1242  if (min_date.value() < run->GetFileWrittenDatime() && run->GetFileWrittenDatime() < max_date.value()) {
1243  numb.Add(run->GetRunIndex());
1244  }
1245  }
1246  else if (min_date) {
1247  if (min_date.value() < run->GetFileWrittenDatime()) {
1248  numb.Add(run->GetRunIndex());
1249  }
1250  }
1251  else if (max_date) {
1252  if (run->GetFileWrittenDatime() < max_date.value()) {
1253  numb.Add(run->GetRunIndex());
1254  }
1255  }
1256  }
1257  }
1258  return numb;
1259 
1260 }
1261 
1262 
1263 
1264 
1271 
1273 {
1274  // Returns list of runs which are present for data type "base_type" but not for "other_type"
1275  //
1276  // If pointer to system is given, only runs for the system are considered.
1277  //
1278  // If OnlyCol=kTRUE (kFALSE default) only systems with KVDBSystem::IsCollision()=kTRUE are considered
1279 
1280  run_index_list manquant;
1281  auto ll = GetListOfAvailableSystems(ref_type);
1282  if (ll.IsEmpty()) {
1283  //numb.Clear();
1284  Info("GetRunList_StageSelection", "No data available of type \"%s\"", ref_type.Data());
1285  return manquant;
1286  }
1287  if (system && !ll.FindObject(system)) {
1288  Info("GetRunList_StageSelection", "No data available of type \"%s\" for system %s", ref_type.Data(), system->GetName());
1289  return manquant;
1290  }
1291 
1292  Info("GetRunList_StageSelection", "Liste des runs presents dans \"%s\" mais absent dans \"%s\"", ref_type.Data(), type.Data());
1293 
1294  KVDBSystem* sys = 0;
1295 
1296  for (Int_t nl = 0; nl < ll.GetEntries(); nl += 1) {
1297 
1298  sys = (KVDBSystem*)ll.At(nl);
1299  if (system && sys != system) continue;
1300  if (OnlyCol && !sys->IsCollision()) continue;
1301  auto nsys = GetRunList(type, sys);
1302  auto nsys_ref = GetRunList(ref_type, sys);
1303  Int_t nref = nsys_ref.GetNValues();
1304 
1305  nsys_ref.Remove(nsys);
1306 
1307  Info("GetRunList_StageSelection", "\nKVDBSystem : %s --> %d runs manquants sur %d : %s",
1308  sys->GetName(),
1309  nsys_ref.GetNValues(),
1310  nref,
1311  nsys_ref.AsString().Data()
1312  );
1313  manquant.Add(nsys_ref);
1314  }
1315  return manquant;
1316 }
1317 
1318 
1319 
1325 
1326 run_index_list KVDataSet::GetRunList_StageSelection(const TString& type, const TString& ref_type, const KVUnownedList& systems, Bool_t OnlyCol)
1327 {
1328  // \returns list of runfiless which are present for data type "base_type" but not for "other_type"
1329  // for the systems (KVDBSystem pointers) in the list.
1330  //
1331  // If OnlyCol=kTRUE (kFALSE default) only systems with KVDBSystem::IsCollision()=kTRUE are considered
1332 
1333  run_index_list manquant;
1334  auto ll = GetListOfAvailableSystems(ref_type);
1335  if (ll.IsEmpty()) {
1336  //numb.Clear();
1337  Info("GetRunList_StageSelection", "No data available of type \"%s\"", ref_type.Data());
1338  return manquant;
1339  }
1340 
1341  Info("GetRunList_StageSelection", "Liste des runs presents dans \"%s\" mais absent dans \"%s\"", ref_type.Data(), type.Data());
1342 
1343  KVDBSystem* sys = 0;
1344 
1345  for (Int_t nl = 0; nl < ll.GetEntries(); nl += 1) {
1346 
1347  sys = (KVDBSystem*)ll.At(nl);
1348  if (!systems.Contains(sys)) continue;
1349  if (OnlyCol && !sys->IsCollision()) continue;
1350  auto nsys = GetRunList(type, sys);
1351  auto nsys_ref = GetRunList(ref_type, sys);
1352  Int_t nref = nsys_ref.GetNValues();
1353 
1354  nsys_ref.Remove(nsys);
1355 
1356  Info("GetRunList_StageSelection", "\nKVDBSystem : %s --> %d runs manquants sur %d : %s",
1357  sys->GetName(),
1358  nsys_ref.GetNValues(),
1359  nref,
1360  nsys_ref.AsString().Data()
1361  );
1362  manquant.Add(nsys_ref);
1363  }
1364  return manquant;
1365 }
1366 
1367 
1368 
1373 
1375 {
1376  // Returns list of runs of given type that were created with the given version of KaliVeda.
1377  //
1378  // If system!="" then only runs for the given system are considered
1379 
1380  run_index_list runs;
1381  if (sys) {
1382  auto lrun = GetListOfAvailableRunFilesForSystem(type, sys);
1383  TIter next(&lrun);
1384  KVRunFile* run;
1385  while ((run = (KVRunFile*)next())) {
1386  if (!strcmp(run->GetVersion(), version)) runs.Add(run->GetRunIndex());
1387  }
1388  return runs;
1389  }
1390  auto ll = GetListOfAvailableSystems(type);
1391  if (ll.IsEmpty()) {
1392  //numb.Clear();
1393  Info("GetRunList_VersionSelection", "No data available of type \"%s\"", type.Data());
1394  return runs;
1395  }
1396  Int_t nsys = ll.GetEntries();
1397  for (Int_t nl = 0; nl < nsys; nl += 1) {
1398  sys = (KVDBSystem*)ll.At(nl);
1399  auto lrun = GetListOfAvailableRunFilesForSystem(type, sys);
1400  TIter next(&lrun);
1401  KVRunFile* run;
1402  while ((run = (KVRunFile*)next())) {
1403  if (!strcmp(run->GetVersion(), version)) runs.Add(run->GetRunIndex());
1404  }
1405  }
1406  return runs;
1407 }
1408 
1409 
1410 
1415 
1416 void KVDataSet::CommitRunfile(const KVString& type, const run_index_t& run, TFile* file)
1417 {
1418  // Commit a runfile previously created with NewRunfile() to the repository.
1419  // Any previous version of the runfile will be deleted.
1420  // The available runs list for this data 'type' is updated.
1421 
1422  if (!fRepository) return;
1423 
1424  //keep name of file for updating available runs list
1425  TString newfile = gSystem->BaseName(file->GetName());
1426 
1427  fRepository->CommitFile(file, type, this);
1428  //update list of available datatypes of dataset,
1429  //in case this addition has created a new subdirectory
1430  CheckAvailable();
1431  //check if previous version of file exists
1432  //get name of file from available runs file
1433  //note that when the file is the first of a new subdirectory, GetAvailableRunsFile->GetFileName
1434  //will cause the available runs file to be created, and it will contain one entry:
1435  //the new file!
1436  TString oldfile = GetAvailableRunsFile(type)->GetFileName(run);
1437  if (oldfile != "" && oldfile != newfile) {
1438  //delete previous version - no confirmation
1439  fRepository->DeleteFile(this, type, oldfile.Data(),
1440  kFALSE);
1441  //was file deleted ? if so, remove entry from available runs file
1442  if (!fRepository->CheckFileStatus(this, type, oldfile.Data()))
1443  GetAvailableRunsFile(type)->Remove(run);
1444  }
1445  if (oldfile != newfile) {
1446  //add entry for new run in available runs file
1447  GetAvailableRunsFile(type)->Add(run, newfile.Data());
1448  }
1449 }
1450 
1451 
1452 
1453 
1459 
1461 {
1462  //if fUserGroups has been set with SetUserGroups(), we check that the current user's name
1463  //(gSystem->GetUserInfo()->fUser) appears in at least one of the groups in the list.
1464  //Returns kFALSE if user's name is not found in any of the groups.
1465  //if fUserGroups="" (default), we return kTRUE for all users.
1466 
1467  if (fUserGroups == "")
1468  return kTRUE; /* no groups set, all users have access */
1469 
1470  //split into array of group names
1471  unique_ptr<TObjArray> toks(fUserGroups.Tokenize(' '));
1472  TObjString* group_name;
1473  TIter next_name(toks.get());
1474  while ((group_name = (TObjString*) next_name())) {
1475  //for each group_name, we check if the user's name appears in the group
1476  if (!fRepository || (fRepository && fRepository->GetDataSetManager()->
1477  CheckUser(group_name->String().Data()))
1478  ) {
1479  return kTRUE;
1480  }
1481  }
1482  return kFALSE;
1483 }
1484 
1485 
1486 
1487 
1490 
1492 {
1493  //Set pointer to data repository in which dataset is stored
1494  fRepository = dr;
1495 }
1496 
1497 
1498 
1499 
1502 
1504 {
1505  //Get pointer to data repository in which dataset is stored
1506  return fRepository;
1507 }
1508 
1509 
1510 
1511 
1516 
1518 {
1519  //Check all runs for a given datatype and make sure that only one version
1520  //exists for each runfile. If not, we print a report on the runfiles which occur
1521  //multiple times, with the associated date and file name.
1522 
1523  auto doubles = GetAvailableRunsFile(data_type)->CheckMultiRunfiles();
1524  if (doubles.empty()) {
1525  cout << "OK. No runs appear more than once." << endl;
1526  }
1527  else {
1528  cout << "Runs which appear more than once: " << endl << endl;
1529  //print dates and filenames for each run
1530 
1531  for (auto& rr : doubles) {
1532  KVList filenames, dates;
1533 
1534  //get infos for current run
1535  GetAvailableRunsFile(data_type)->GetRunInfos(rr, dates, filenames);
1536 
1537  cout << "Run " << rr << " : " << dates.GetEntries() << " files >>>>>>" << endl;
1538  for (int i = 0; i < dates.GetEntries(); i++) {
1539 
1540  cout << "\t" << ((TObjString*) filenames.At(i))->String().
1541  Data() << "\t" << ((TObjString*) dates.At(i))->String().
1542  Data() << endl;
1543 
1544  }
1545  }
1546  }
1547 }
1548 
1549 
1550 
1551 
1562 
1563 void KVDataSet::CleanMultiRunfiles(const Char_t* data_type, Bool_t confirm)
1564 {
1565  // Check all runs for a given datatype and make sure that only one version
1566  // exists for each run. If not, we print a report on the runfiles which occur
1567  // multiple times, with the associated date and file name, and then we
1568  // destroy all but the most recent version of the file in the repository, and
1569  // update the runlist accordingly.
1570  //
1571  // By default, we ask for confirmation before deleting each file.
1572  //
1573  // Call with confirm=kFALSE to delete WITHOUT CONFIRMATION (DANGER!! WARNING!!!)
1574 
1575  if (!fRepository) return;
1576 
1577  KVAvailableRunsFile* ARF = GetAvailableRunsFile(data_type);
1578  auto doubles = ARF->CheckMultiRunfiles();
1579  if (doubles.empty()) {
1580  cout << "OK. No runs appear more than once." << endl;
1581  }
1582  else {
1583  cout << "Runs which appear more than once: " << endl << endl;
1584  //print dates and filenames for each run
1585 
1586  KVList filenames, dates;
1587  for (auto& rr : doubles) {
1588  //get infos for current run
1589  ARF->GetRunInfos(rr, dates, filenames);
1590  TDatime most_recent("1998-12-25 00:00:00");
1591  Int_t i_most_recent = 0;
1592  cout << "Run " << rr << " : " << dates.GetEntries() << " files >>>>>>" << endl;
1593  for (int i = 0; i < dates.GetEntries(); i++) {
1594  //check if run is most recent
1595  TDatime rundate(((TObjString*) dates.At(i))->String().Data());
1596  if (rundate > most_recent) {
1597  most_recent = rundate;
1598  i_most_recent = i;
1599  }
1600  }
1601  //Now, we loop over the list again, this time we destroy all but the most recent
1602  //version of the runfile
1603  for (int i = 0; i < dates.GetEntries(); i++) {
1604  if (i == i_most_recent) {
1605  cout << "KEEP : ";
1606  }
1607  else {
1608  cout << "DELETE : ";
1609  }
1610  cout << "\t" << ((TObjString*) filenames.At(i))->String().
1611  Data() << "\t" << ((TObjString*) dates.At(i))->String().
1612  Data() << endl;
1613  if (i != i_most_recent) {
1614  //delete file from repository forever and ever
1615  fRepository->DeleteFile(this, data_type,
1616  ((TObjString*) filenames.At(i))->
1617  String().Data(), confirm);
1618  //remove file entry from available runlist
1619  ARF->Remove(rr,
1620  ((TObjString*) filenames.At(i))->String());
1621  }
1622  }
1623  }
1624  }
1625 }
1626 
1627 
1628 
1633 
1635 {
1636  // Similar to CleanMultiRunfiles(), but here the aim is only to remove from the
1637  // sqlite database any runfiles which are no longer physically present in the
1638  // repository i.e. they have already been deleted but our database was not updated.
1639 
1640  if (!fRepository) return;
1641 
1642  Info("CleanRunfileDataBase", "Checking for spurious duplicates (non-existent files)...");
1643 
1644  KVAvailableRunsFile* ARF = GetAvailableRunsFile(data_type);
1645 
1646  auto doubles = ARF->CheckMultiRunfiles();
1647  if (!doubles.empty()) {
1648  for (auto& ri : doubles) {
1649  // for each run/index, get full list of available files
1650  KVList dates, files;
1651  ARF->GetRunInfos(ri, dates, files);
1652  // now check that each file is physically present
1653  for (auto f : files) {
1654  TString fname = dynamic_cast<TObjString*>(f)->GetString();
1655  if (!fRepository->CheckFileStatus(this, data_type, fname)) {
1656  Info("CleanRunfileDataBase", "File %s does not exist : remove from database...", fname.Data());
1657  ARF->Remove(ri, fname);
1658  }
1659  }
1660  }
1661  }
1662  else
1663  Info("CleanRunfileDataBase", "Database is apparently consistent");
1664 }
1665 
1666 
1667 
1668 
1675 
1677  KVDataRepository* other_repos)
1678 {
1679  //Use this method to check whether the file of type "data_type" for run number "run"
1680  //in the data repository "other_repos" is more recent than the file contained in the data
1681  //repository corresponding to this dataset.
1682  //
1683  //Returns kFALSE if file in other repository is more recent.
1684 
1685  if (!other_repos)
1686  return kTRUE;
1687  //get dataset with same name as this one from dataset manager of other repository
1688  KVDataSet* ds = other_repos->GetDataSetManager()->GetDataSet(GetName());
1689  if (!ds) {
1690  Error("CheckRunfileUpToDate",
1691  "Dataset \"%s\" not found in repository \"%s\"", GetName(),
1692  other_repos->GetName());
1693  return kFALSE;
1694  }
1695  //compare dates of the two runfiles
1696  if (GetRunfileDate(data_type, run) < ds->GetRunfileDate(data_type, run))
1697  return kFALSE;
1698  return kTRUE;
1699 }
1700 
1701 
1702 
1703 
1710 
1712  const KVString& other_repos)
1713 {
1714  //Use this method to check whether the file of type "data_type" for run number "run"
1715  //in the data repository "other_repos" is more recent than the file contained in the data
1716  //repository corresponding to this dataset.
1717  //Returns kTRUE if no repository with name "other_repos" exists.
1718  //Returns kFALSE if file in other repository is more recent.
1719 
1720  KVDataRepository* _or =
1721  gDataRepositoryManager->GetRepository(other_repos);
1722  if (_or)
1723  return CheckRunfileUpToDate(data_type, run, _or);
1724  Error("CheckRunfileUpToDate",
1725  "No data repository known with this name : %s", (const char*) other_repos);
1726  return kTRUE;
1727 }
1728 
1729 
1730 
1731 
1735 
1736 void KVDataSet::CheckUpToDate(const Char_t* data_type,
1737  const Char_t* other_repos)
1738 {
1739  //Check whether all files of type "data_type" for run number "run" in the data repository
1740  //are up to date (i.e. at least as recent) as compared to the files in data repository "other_repos".
1741 
1742  if (!fRepository) return;
1743 
1744  KVDataRepository* _or =
1745  gDataRepositoryManager->GetRepository(other_repos);
1746  if (!_or) {
1747  Error("CheckUpToDate",
1748  "No data repository known with this name : %s", other_repos);
1749  return;
1750  }
1751  auto runlist = GetAvailableRunsFile(data_type)->GetRunList();
1752  Int_t need_update = 0;
1753  for (auto& rr : runlist) {
1754  //check run
1755  if (!CheckRunfileUpToDate(data_type, rr, _or)) {
1756  cout << " *** run " << rr << " needs update ***" <<
1757  endl;
1758  cout << "\t\tREPOSITORY: " << fRepository->
1759  GetName() << "\tDATE: " << GetRunfileDate(data_type, rr).value().AsString() << endl;
1760  cout << "\t\tREPOSITORY: " << other_repos << "\tDATE: " << _or->
1761  GetDataSetManager()->GetDataSet(GetName())->
1762  GetRunfileDate(data_type, rr).value().AsString() << endl;
1763  need_update++;
1764  }
1765  }
1766  if (!need_update) {
1767  cout << " *** All runfiles are up to date for data type " <<
1768  data_type << endl;
1769  }
1770 }
1771 
1772 
1773 
1774 
1778 
1780  const Char_t* other_repos)
1781 {
1782  //Returns list of all runs of type "data_type" which may be updated
1783  //from the repository named "other_repos". See CheckUpToDate().
1784 
1785  run_index_list updates;
1786  if (!fRepository) return updates;
1787 
1788  KVDataRepository* _or =
1789  gDataRepositoryManager->GetRepository(other_repos);
1790  if (!_or) {
1791  Error("CheckUpToDate",
1792  "No data repository known with this name : %s", other_repos);
1793  return updates;
1794  }
1795  auto runlist = GetAvailableRunsFile(data_type)->GetRunList();
1796  for (auto& rr : runlist) {
1797  //check run
1798  if (!CheckRunfileUpToDate(data_type, rr, _or)) {
1799  //run is out of date
1800  updates.Add(rr);
1801  }
1802  }
1803  return updates;
1804 }
1805 
1806 
1807 
1808 
1813 
1815  const KVDBSystem* system) const
1816 {
1817  //Returns list of all files available for given "data_type"
1818  //
1819  //If a pointer to a reaction system is given, only files for the given system will be included in the list.
1820 
1821  if (!fRepository || !HasDataType(data_type)) {
1822  Error("GetRunList",
1823  "No data of type %s available. Runlist will be empty.",
1824  data_type);
1825  return {};
1826  }
1827 
1828  return GetAvailableRunsFile(data_type)->GetRunList(system);
1829 }
1830 
1831 
1832 
1833 
1864 
1866 {
1867  //This method returns a pointer to the available analysis task whose description (title) contains
1868  //all of the whitespace-separated keywords (which may be regular expressions)
1869  //given in the string "keywords". The comparison is case-insensitive.
1870  //
1871  //WARNING: this method can only be used to access analysis tasks that are
1872  //available for this dataset, i.e. for which the corresponding prerequisite data type
1873  //is available in the repository.
1874  //For unavailable data/tasks, use GetAnalysisTaskAny(const Char_t*).
1875  //
1876  //EXAMPLES
1877  //Let us suppose that the current dataset has the following list of tasks:
1878  //~~~
1879  // root [2] gDataSet->Print("tasks")
1880  // 1. Event reconstruction from raw data (raw->recon)
1881  // 2. Analysis of raw data
1882  // 3. Identification of reconstructed events (recon->ident)
1883  // 4. Analysis of reconstructed events (recon)
1884  // 5. Analysis of partially identified & calibrated reconstructed events (ident)
1885  // 6. Analysis of fully calibrated physical data (root)
1886  //~~~
1887  //Then the following will occur:
1888  //~~~
1889  // root [14] gDataSet->GetAnalysisTask("raw->recon")->Print()
1890  // KVDataAnalysisTask : Event reconstruction from raw data (raw->recon)
1891  //
1892  // root [10] gDataSet->GetAnalysisTask("analysis root")->Print()
1893  // KVDataAnalysisTask : Analysis of fully calibrated physical data (root)
1894  //~~~
1895 
1896  //case-insensitive search for matches in list based on 'title' attribute
1897  return (KVDataAnalysisTask*)fTasks.FindObjectAny("title", keywords, kTRUE, kFALSE);
1898 }
1899 
1900 
1901 
1902 
1904 
1906 {
1907  if (!dat->WithUserClass()) {
1908  Error("MakeAnalysisClass",
1909  "No user class required for analysis task \"%s\"", dat->GetTitle());
1910  return false;
1911  }
1912 
1913  //all analysis base classes must define a static Make(const Char_t * classname)
1914  //which generates the skeleton class files.
1915 
1916  TClass* cl = nullptr;
1917  //has the user base class for the task been compiled and loaded ?
1919  else
1920  return false;
1921 
1922  //set up call to static Make method
1923  unique_ptr<TMethodCall> methcall(new TMethodCall(cl, "Make", Form("\"%s\"", classname)));
1924 
1925  if (!methcall->IsValid()) {
1926  Error("MakeAnalysisClass", "static Make(const Char_t*) method for class %s is not valid",
1927  cl->GetName());
1928  return false;
1929  }
1930 
1931  //generate skeleton class
1932  methcall->Execute();
1933 
1934  return true;
1935 }
1936 
1937 
1938 
1951 
1952 bool KVDataSet::MakeAnalysisClass(const Char_t* task, const Char_t* classname)
1953 {
1954  //Create a skeleton analysis class to be used for analysis of the data belonging to this dataset.
1955  //
1956  // task = keywords contained in title of analysis task (see GetAnalysisTask(const Char_t*))
1957  // (you do not need to include 'analysis', it is added automatically)
1958  // classname = name of new analysis class
1959  //
1960  //Example:
1961  // MakeAnalysisClass("raw", "MyRawDataAnalysis")
1962  // --> make skeleton raw data analysis class in files MyRawDataAnalysis.cpp & MyRawDataAnalysis.h
1963  // MakeAnalysisClass("fully calibrated", "MyDataAnalysis")
1964  // --> make skeleton data analysis class in files MyDataAnalysis.cpp & MyDataAnalysis.h
1965 
1966  KVString _task = task;
1967  if (!_task.Contains("nalysis")) _task += " analysis";
1968  //We want to be able to write analysis classes even when we don't have any data
1969  //to analyse. Therefore we use GetAnalysisTaskAny.
1970  auto dat = GetAnalysisTaskAny(_task.Data());
1971  if (!dat) {
1972  Error("MakeAnalysisClass",
1973  "called for unknown or unavailable analysis task : %s", _task.Data());
1974  return false;
1975  }
1976  return make_analysis_class(dat, classname);
1977 }
1978 
1979 
1980 
1987 
1988 bool KVDataSet::MakeAnalysisClass(int task, const Char_t* classname)
1989 {
1990  //Create a skeleton analysis class to be used for analysis of the data belonging to this dataset.
1991  //
1992  // task = index of analysis task as shown in KVDataSet::Print("tasks")
1993  // classname = name of new analysis class
1994  //
1995 
1996  auto dat = GetAnalysisTask(task);
1997  if (!dat) {
1998  Error("MakeAnalysisClass",
1999  "called for unknown or unavailable analysis task index : %d", task);
2000  return false;
2001  }
2002  return make_analysis_class(dat, classname);
2003 }
2004 
2005 
2006 
2007 
2011 
2012 Bool_t KVDataSet::OpenDataSetFile(const Char_t* filename, ifstream& file)
2013 {
2014  // Look for (and open for reading, if found) the named file in the directory which
2015  // contains the files for this dataset (given by GetDataSetDir())
2016 
2017  return OpenDataSetFile(GetName(), filename, file);
2018 }
2019 
2020 
2021 
2025 
2026 Bool_t KVDataSet::OpenDataSetFile(const TString& dataset, const Char_t* filename, ifstream& file)
2027 {
2028  // Static method to look for (and open for reading, if found) the named file in the directory which
2029  // contains the files for the dataset
2030 
2031  TString datasetdir = KVBase::GetDataSetEnv(dataset, "DataSet.Directory", dataset);
2032  if (gSystem->IsAbsoluteFileName(datasetdir)) {
2033  // dataset directory is outside of standard KV installation directories
2034  // use absolute path to search for file
2035  TString abspath;
2036  abspath.Form("%s/%s", datasetdir.Data(), filename);
2037  return SearchAndOpenKVFile(abspath, file);
2038  }
2039  // dataset directory is a subdirectory of GetDATADIRFilePath()
2040  return SearchAndOpenKVFile(filename, file, datasetdir);
2041 }
2042 
2043 
2044 
2048 
2050 {
2051  // Find a file in the dataset directory (given by GetDataSetDir())
2052  // Returns full path to file if found, empty string if not
2053 
2054  return GetFullPathToDataSetFile(GetName(), filename);
2055 }
2056 
2057 
2058 
2062 
2064 {
2065  // Static method to find a file in the dataset directory (given by GetDataSetDir())
2066  // Returns full path to file if found, empty string if not
2067 
2068  TString fullpath;
2069  TString datasetdir = KVBase::GetDataSetEnv(dataset, "DataSet.Directory", dataset);
2070  if (!SearchKVFile(filename, fullpath, datasetdir)) {
2071  ::Warning("KVDataSet::GetFullPathToDataSetFile", "File %s not found in dataset subdirectory %s", filename, datasetdir.Data());
2072  fullpath = "";
2073  }
2074  return fullpath;
2075 }
2076 
2077 
2078 
2082 
2083 Bool_t KVDataSet::FindDataSetFile(const TString& dataset, const Char_t* filename)
2084 {
2085  // Static method to find a file in the dataset directory (given by GetDataSetDir())
2086  // Returns kTRUE if found, kFALSE if not
2087 
2088  TString fullpath;
2089  TString datasetdir = KVBase::GetDataSetEnv(dataset, "DataSet.Directory", dataset);
2090  return SearchKVFile(filename, fullpath, datasetdir);
2091 }
2092 
2093 
2094 
2098 
2100 {
2101  // Find a file in the dataset directory (given by GetDataSetDir())
2102  // Returns kTRUE if found, kFALSE if not
2103 
2104  return FindDataSetFile(GetName(), filename);
2105 }
2106 
2107 
2108 
2109 
2118 
2120 {
2121  //This method returns the analysis task whose description (title) contains
2122  //all of the whitespace-separated keywords (which may be regular expressions)
2123  //given in the string "keywords". The comparison is case-insensitive.
2124  //The analysis task does not need to be "available", i.e. the associated prerequisite
2125  //data type does not have to be present in the repository (see GetAnalysisTask).
2126  //
2127  // If no task is found, returns nullptr
2128 
2129  KVDataAnalysisTask* tsk = (KVDataAnalysisTask*)fAllTasks.FindObjectAny("title", keywords, kTRUE, kFALSE);
2130  if (!tsk) {
2131  Error("GetAnalysisTaskAny", "No task found with the following keywords in its title : %s", keywords);
2132  }
2133  return tsk;
2134 }
2135 
2136 
2137 
2138 
2145 
2147 {
2148  // Returns kTRUE if database needs to be regenerated from source files,
2149  // i.e. if source files are more recent than DataBase.root
2150  //
2151  // In case no directory exists for dataset (dataset added 'on the fly')
2152  // we create the directory and fill it with dummy files (Makefile, Runlist.csv, Systems.dat)
2153 
2154  TString pwd = gSystem->pwd();
2155 
2156  TString path = "";
2157  if (!SearchKVFile(GetDataSetDir(), path)) {
2158  // dataset directory doesn't exist - create it
2159  Info("DataBaseNeedsUpdate", "%s: Creating new dataset directory %s",
2160  GetName(), GetDataSetDir());
2161  if (gSystem->mkdir(GetDataSetDir())) {
2162  // problem creating directory
2163  Error("DataBaseNeedsUpdate",
2164  "%s: Dataset directory %s does not exist and cannot be created ?",
2165  GetName(), GetDataSetDir());
2166  return kFALSE;
2167  }
2168  // create dummy files
2169  SearchKVFile(GetDataSetDir(), path); // get full path
2170  path += "/";
2171  TString filename = path + "Makefile";
2172  ofstream of1(filename.Data());
2173  of1 << "$(KV_WORK_DIR)/db/" << GetName() << "/DataBase.root : Runlist.csv Systems.dat" << endl;
2174  of1 << "\t@echo Database needs update" << endl;
2175  of1.close();
2176  filename = path + "Runlist.csv";
2177  ofstream of2(filename.Data());
2178  of2 << "# Automatically generated dummy Runlist.csv file" << endl;
2179  of2.close();
2180  filename = path + "Systems.dat";
2181  ofstream of3(filename.Data());
2182  of3 << "# Automatically generated dummy Systems.dat file" << endl;
2183  of3.close();
2184  }
2185  gSystem->cd(GetDataSetDir());
2186  TString cmd = "make -q";
2187  Int_t ret = gSystem->Exec(cmd.Data());
2188  gSystem->cd(pwd.Data());
2189  return (ret != 0);
2190 }
2191 
2192 
2193 
2210 
2212 {
2213  // Returns name of output repository for given task.
2214  // By default it is the name of the repository associated with this dataset,
2215  // but can be changed by the following environment variables:
2216  //
2217  // [repository].DefaultOutputRepository: [other repository]
2218  // - this means that all tasks carried out on data in [repository]
2219  // will have their output files placed in [other repository]
2220  //
2221  // [taskname].DataAnalysisTask.OutputRepository: [other repository]
2222  // - this means that for [taskname], any output files will
2223  // be placed in [other repository]
2224  //
2225  // [dataset].[taskname].DataAnalysisTask.OutputRepository: [other repository]
2226  // - this means that for given [dataset] & [taskname],
2227  // any output files will be placed in [other repository]
2228 
2229  if (gEnv->Defined(Form("%s.DataRepository.DefaultOutputRepository", GetRepository()->GetName())))
2230  return TString(gEnv->GetValue(Form("%s.DataRepository.DefaultOutputRepository", GetRepository()->GetName()), ""));
2231  TString orep = GetDataSetEnv(Form("%s.DataAnalysisTask.OutputRepository", taskname), GetRepository()->GetName());
2232  return orep;
2233 }
2234 
2235 
2236 
2237 
2240 
2241 void KVDataSet::CopyRunfilesFromRepository(const Char_t* type, const run_index_list& runs, const Char_t* destdir)
2242 {
2243  // Copies the runfiles of given "type" into the local directory "destdir".
2244 
2245  KVDataRepository* repo = GetRepository();
2246  for (auto& run : runs) {
2247  TString filename = GetRunfileName(type, run);
2248  TString destpath;
2249  AssignAndDelete(destpath, gSystem->ConcatFileName(destdir, filename));
2250  repo->CopyFileFromRepository(this, type, filename, destpath);
2251  }
2252 }
2253 
2254 
2255 
2256 
2260 
2261 void KVDataSet::CopyRunfilesToRepository(const Char_t* type, const run_index_list& runs, const Char_t* destrepo)
2262 {
2263  // Copies the runfiles of given "type" from the data repository associated
2264  // with this dataset into the local repository "destrepo".
2265 
2266  KVDataRepository* repo = GetRepository();
2267  KVDataRepository* dest_repo = gDataRepositoryManager->GetRepository(destrepo);
2268 
2269  if (!dest_repo) {
2270  Error("CopyRunfilesToRepository", "Unknown destination repository : %s", destrepo);
2271  gDataRepositoryManager->Print();
2272  return;
2273  }
2274 
2275  KVDataSet* dest_ds = dest_repo->GetDataSetManager()->GetDataSet(GetName());
2276  dest_repo->CreateAllNeededSubdirectories(dest_ds, type);
2277  for (auto& run : runs) {
2278  TString filename = GetRunfileName(type, run);
2279  TString destpath = dest_repo->GetFullPathToTransferFile(dest_ds, type, filename);
2280  repo->CopyFileFromRepository(this, type, filename, destpath);
2281  }
2282 }
2283 
2284 
int Int_t
ROOT::R::TRInterface & r
#define f(i)
bool Bool_t
char Char_t
constexpr Bool_t kFALSE
constexpr Bool_t kTRUE
const char Option_t
#define gDirectory
R__EXTERN TEnv * gEnv
Option_t Option_t TPoint TPoint const char GetTextMagnitude GetFillStyle GetLineColor GetLineWidth GetMarkerStyle GetTextAlign GetTextColor GetTextSize void char Point_t Rectangle_t WindowAttributes_t Float_t Float_t Float_t Int_t Int_t UInt_t UInt_t Rectangle_t Int_t Int_t Window_t TString Int_t GCValues_t GetPrimarySelectionOwner GetDisplay GetScreen GetColormap GetNativeEvent const char const char dpyName wid window const char font_name cursor keysym reg const char only_if_exist regb h Point_t winding char text const char depth char const char Int_t count const char ColorStruct_t color const char filename
Option_t Option_t TPoint TPoint const char GetTextMagnitude GetFillStyle GetLineColor GetLineWidth GetMarkerStyle GetTextAlign GetTextColor GetTextSize void char Point_t Rectangle_t WindowAttributes_t Float_t Float_t Float_t Int_t Int_t UInt_t UInt_t Rectangle_t Int_t Int_t Window_t TString Int_t GCValues_t GetPrimarySelectionOwner GetDisplay GetScreen GetColormap GetNativeEvent const char const char dpyName wid window const char font_name cursor keysym reg const char only_if_exist regb h Point_t winding char text const char depth char const char Int_t count const char ColorStruct_t color const char Pixmap_t Pixmap_t PictureAttributes_t attr const char char ret_data h unsigned char height h Atom_t Int_t ULong_t ULong_t unsigned char prop_list Atom_t Atom_t Atom_t Time_t type
char name[80]
char * Form(const char *fmt,...)
void AssignAndDelete(TString &target, char *tobedeleted)
R__EXTERN TSystem * gSystem
Handles lists of available runs for different datasets and types of data.
void GetRunInfos(const run_index_t &run, KVList &dates, KVList &names)
virtual void Remove(const run_index_t &run, const KVString &filename="")
Remove from the db ALL entries corresponding to the given run/index (and filename if given)
std::forward_list< run_index_t > CheckMultiRunfiles()
Returns a list with all run/indexes for which more than one file is in the available runs db.
virtual void Add(const run_index_t &run, const KVString &filename)
static ValType GetDataSetEnv(const KVString &dataset, const KVString &type, const ValType &defval)
Definition: KVBase.h:304
Database class used to store information on different colliding systems studied during an experiment....
Definition: KVDBSystem.h:51
Bool_t IsCollision() const
retourne kTRUE, si le systeme est une collision ie projectile+cible
Definition: KVDBSystem.cpp:101
Define and manage data analysis tasks.
virtual void SetDataAnalyser(const Char_t *d)
virtual Bool_t WithUserClass() const
virtual void SetPrereq(const Char_t *p)
virtual void SetStatusUpdateInterval(Long64_t n)
virtual const Char_t * GetUserBaseClass() const
virtual Bool_t CheckUserBaseClassIsLoaded() const
void SetExtraAClicIncludes(const KVString &list)
virtual const Char_t * GetPrereq() const
virtual void SetUserBaseClass(const Char_t *d)
KVDataRepository * GetRepository(const Char_t *name) const
void Print(Option_t *opt="") const
Base class for managing repositories of experimental data.
virtual KVDataSetManager * GetDataSetManager() const
Return pointer to data set manager for this repository.
virtual void CopyFileFromRepository(const KVDataSet *dataset, const Char_t *datatype, const Char_t *filename, const Char_t *destination)
void CreateAllNeededSubdirectories(const KVDataSet *DataSet, const Char_t *DataType)
virtual const Char_t * GetFullPathToTransferFile(const KVDataSet *dataset, const Char_t *datatype, const Char_t *runfile)
KVDataSet * GetDataSet(Int_t) const
Return pointer to DataSet using index in list of all datasets, index>=0.
Manage an experimental dataset corresponding to a given experiment or campaign.
Definition: KVDataSet.h:146
std::optional< TDatime > GetRunfileDate(const KVString &type, const run_index_t &run)
Definition: KVDataSet.cpp:913
TString GetFullPathToRunfile(const KVString &type, const run_index_t &run) const
Definition: KVDataSet.cpp:869
TString GetFullPathToDB() const
Definition: KVDataSet.cpp:153
void ls(Option_t *opt="") const override
Print dataset information.
Definition: KVDataSet.cpp:394
TString GetOutputRepository(const Char_t *taskname) const
Definition: KVDataSet.cpp:2211
virtual void OpenDBFile(const Char_t *full_path_to_dbfile) const
Open the database from a file on disk.
Definition: KVDataSet.cpp:127
TString GetDBName() const
Definition: KVDataSet.cpp:112
void CheckMultiRunfiles(const Char_t *data_type)
Definition: KVDataSet.cpp:1517
Bool_t CheckRunfileAvailable(const KVString &type, const run_index_t &run)
Definition: KVDataSet.cpp:1009
virtual const Char_t * GetBaseFileName(const Char_t *type, const run_index_t &run) const
Definition: KVDataSet.cpp:1042
void CleanRunfileDataBase(const Char_t *data_type)
Definition: KVDataSet.cpp:1634
void CheckUpToDate(const Char_t *data_type, const Char_t *other_repos)
Definition: KVDataSet.cpp:1736
run_index_list GetRunList(const Char_t *data_type, const KVDBSystem *sys=0) const
Definition: KVDataSet.cpp:1814
virtual void OpenDataBase(const TString &="") const
Definition: KVDataSet.cpp:316
TString GetFullPathToDataSetFile(const Char_t *filename) const
Definition: KVDataSet.cpp:2049
void CopyRunfilesFromRepository(const Char_t *type, const run_index_list &runs, const Char_t *destdir)
Copies the runfiles of given "type" into the local directory "destdir".
Definition: KVDataSet.cpp:2241
KVDataRepository * GetRepository() const
Get pointer to data repository in which dataset is stored.
Definition: KVDataSet.cpp:1503
run_index_list GetRunList_DateSelection(const TString &type, const KVUnownedList &systems, std::optional< KVDatime > min_date=std::nullopt, std::optional< KVDatime > max_date=std::nullopt)
Definition: KVDataSet.cpp:1218
const Char_t * GetDataSetDir() const
Definition: KVDataSet.cpp:745
void CommitRunfile(const KVString &type, const run_index_t &run, TFile *file)
Definition: KVDataSet.cpp:1416
virtual void AddAvailableDataType(const Char_t *)
Definition: KVDataSet.cpp:507
KVUniqueNameList GetSystemsForRunFiles(const TString &datatype, const run_index_list &) const
Definition: KVDataSet.cpp:672
bool make_analysis_class(const KVDataAnalysisTask *, const Char_t *classname)
Definition: KVDataSet.cpp:1905
KVDataAnalysisTask * GetAnalysisTask(Int_t) const
Definition: KVDataSet.cpp:573
KVAvailableRunsFile * GetAvailableRunsFile(const TString &type) const
Definition: KVDataSet.cpp:51
virtual void SaveDataBase() const
Definition: KVDataSet.cpp:203
virtual KVDataAnalysisTask * GetAnalysisTaskAny(const Char_t *keywords) const
Definition: KVDataSet.cpp:2119
virtual void SetAnalysisTasks(const KVSeqCollection *)
Definition: KVDataSet.cpp:524
TFile * NewRunfile(const KVString &type, const run_index_t &run)
Definition: KVDataSet.cpp:1115
KVList GetListOfAvailableRunFilesForSystem(const TString &datatype, KVDBSystem *systol)
Definition: KVDataSet.cpp:628
Bool_t CheckRunfileUpToDate(const KVString &data_type, const run_index_t &run, KVDataRepository *other_repos)
Definition: KVDataSet.cpp:1676
virtual void CheckAvailable()
Definition: KVDataSet.cpp:460
void DeleteRunfile(const KVString &type, const run_index_t &run, Bool_t confirm=kTRUE)
Definition: KVDataSet.cpp:1140
virtual Int_t GetNtasks() const
Definition: KVDataSet.cpp:558
run_index_list GetRunList_VersionSelection(const TString &type, const TString &version, KVDBSystem *sys=0)
Definition: KVDataSet.cpp:1374
KVExpDB * GetDataBase(const TString &opt="") const
Definition: KVDataSet.cpp:287
void DeleteRunfiles(const Char_t *type, const run_index_list &lrun={}, Bool_t confirm=kTRUE)
Definition: KVDataSet.cpp:1187
TObject * open_runfile(const KVString &type, const run_index_t &run)
Definition: KVDataSet.cpp:817
void CopyRunfilesToRepository(const Char_t *type, const run_index_list &runs, const Char_t *destrepo)
Definition: KVDataSet.cpp:2261
KVString GetRunfileName(const KVString &type, const run_index_t &run) const
Definition: KVDataSet.cpp:889
virtual Bool_t DataBaseNeedsUpdate() const
Definition: KVDataSet.cpp:2146
Bool_t OpenDataSetFile(const Char_t *filename, std::ifstream &file)
void SetDataSetSpecificTaskParameters(KVDataAnalysisTask *) const
Check configuration variables to see if the task parameters have been "tweaked" for the dataset.
Definition: KVDataSet.cpp:178
run_index_list GetRunList_StageSelection(const TString &other_type, const TString &base_type, KVDBSystem *sys=0, Bool_t OnlyCol=kFALSE)
Definition: KVDataSet.cpp:1272
void cd() const
Definition: KVDataSet.cpp:767
virtual void WriteDBFile(const Char_t *full_path_to_dbfile) const
Write the database to disk.
Definition: KVDataSet.cpp:255
void Print(Option_t *opt="") const override
Definition: KVDataSet.cpp:417
void SetName(const char *name) override
Definition: KVDataSet.cpp:707
virtual Bool_t CheckUserCanAccess()
Definition: KVDataSet.cpp:1460
void UpdateAvailableRuns(const KVString &type)
Definition: KVDataSet.cpp:1086
run_index_list GetUpdatableRuns(const Char_t *data_type, const Char_t *other_repos)
Definition: KVDataSet.cpp:1779
void SetRepository(KVDataRepository *)
Set pointer to data repository in which dataset is stored.
Definition: KVDataSet.cpp:1491
bool MakeAnalysisClass(const Char_t *task, const Char_t *classname)
Definition: KVDataSet.cpp:1952
KVDataSet()
Default constructor.
Definition: KVDataSet.cpp:35
std::optional< run_index_t > GetRunNumberFromFileName(const TString &datatype, const TString &filename)
Definition: KVDataSet.cpp:962
void CleanMultiRunfiles(const Char_t *data_type, Bool_t confirm=kTRUE)
Definition: KVDataSet.cpp:1563
static Bool_t FindDataSetFile(const TString &dataset, const Char_t *filename)
Definition: KVDataSet.cpp:2083
KVUnownedList GetListOfAvailableSystems(const TString &datatype)
Definition: KVDataSet.cpp:588
TString GetDBFileName() const
Definition: KVDataSet.cpp:83
Extension of TDatime to handle various useful date formats.
Definition: KVDatime.h:33
Base class to describe database of an experiment ,,.
Definition: KVExpDB.h:61
virtual void cd()
Definition: KVExpDB.cpp:576
static KVExpDB * MakeDataBase(const Char_t *name, const Char_t *datasetdir, Bool_t minimal=false)
Definition: KVExpDB.cpp:597
Extended TList class which owns its objects by default.
Definition: KVList.h:22
Description of an individual data file in an experimental dataset.
Definition: KVRunFile.h:19
const Char_t * GetVersion() const
Definition: KVRunFile.h:84
const run_index_t & GetRunIndex() const
Definition: KVRunFile.h:56
KaliVeda extensions to ROOT collection classes.
TObject * At(Int_t idx) const override
Extension of ROOT TString class which allows backwards compatibility with ROOT v3....
Definition: KVString.h:73
void Begin(TString delim) const
Definition: KVString.cpp:565
Bool_t End() const
Definition: KVString.cpp:634
KVString Next(Bool_t strip_whitespace=kFALSE) const
Definition: KVString.cpp:695
Optimised list in which named objects can only be placed once.
Extended TList class which does not own its objects by default.
Definition: KVUnownedList.h:20
static TClass * GetClass(Bool_t load=kTRUE, Bool_t silent=kFALSE)
virtual Int_t GetEntries() const
Bool_t Contains(const char *name) const
const char * AsSQLString() const
virtual Bool_t cd()
virtual const char * GetValue(const char *name, const char *dflt) const
virtual void SetValue(const char *name, const char *value, EEnvLevel level=kEnvChange, const char *type=nullptr)
Bool_t Defined(const char *name) const
TObject * FindObject(const char *name) const override
virtual void SetTitle(const char *title="")
const char * GetName() const override
const char * GetTitle() const override
virtual void SetName(const char *name)
TString & String()
const char * Data() const
void ToUpper()
void Form(const char *fmt,...)
TString & Remove(EStripType s, char c)
Bool_t Contains(const char *pat, ECaseCompare cmp=kExact) const
TString & ReplaceAll(const char *s1, const char *s2)
Bool_t cd(const char *path)
const char * pwd()
virtual int Chmod(const char *file, UInt_t mode)
virtual const char * DirName(const char *pathname)
virtual char * ConcatFileName(const char *dir, const char *name)
virtual int mkdir(const char *name, Bool_t recursive=kFALSE)
virtual Int_t Exec(const char *shellcmd)
virtual Bool_t AccessPathName(const char *path, EAccessMode mode=kFileExists)
virtual const char * BaseName(const char *pathname)
virtual Bool_t IsAbsoluteFileName(const char *dir)
List of runfiles specified by run number and file index ,.
Int_t GetEntries() const
void Add(const run_index_t &r)
Specifies a runfile according to run number and file index ,.
Definition: run_index.h:31
int run() const
Definition: run_index.h:50
TString as_string() const
Definition: run_index.h:95
int index(int no_index=-1) const
Definition: run_index.h:55
bool has_index() const
Definition: run_index.h:59
const Int_t n
void Error(const char *location, const char *fmt,...)
void Info(const char *location, const char *fmt,...)
void Warning(const char *location, const char *fmt,...)
void update(const LAYERDATA &prevLayerData, LAYERDATA &currLayerData, double factorWeightDecay, EnumRegularization regularization)
const char * String
v
TArc a
ClassImp(TPyArg)