114{
  117 
  119 
  121  string          usr;
  122  string          pwd;
  123  string          cookie;
  124  string          inputFile;
  126  string          detid;
  127  JRange_t        UTC;
  129  double          Tmin_s;
  131 
  132  try {
  133 
  134    JParser<> zap(
"Example program to plot quality data from data base or input file.");
 
  135    
  140    zap[
'f'] = 
make_field(inputFile,  
"Optional input file instead of database.")       = 
"";
 
  141    zap[
'o'] = 
make_field(
outputFile, 
"ROOT file with histograms and n-tuple or ASCII file with QA/QC data.") = 
"monitor.root";
 
  142    zap[
'D'] = 
make_field(detid,      
"detector identifier");
 
  143    zap[
'S'] = 
make_field(source,     
"GIT versions")               = 
getGITTags(TRegexp(
"v[0-9]*\\.[0-9]*\\.[0-9]*$"), JGITTags_t::key_type(
"2019-04-12"));
 
  145    zap[
'T'] = 
make_field(Tmin_s,     
"minimal run duration [s]")   = 60;
 
  147 
  148    zap(argc, argv);
  149  }
  150  catch(const exception &error) {
  151    FATAL(error.what() << endl);
 
  152  }
  153 
  154 
  157 
  158  try {
  159 
  160    JDB::reset(usr, pwd, cookie);
  161 
  162    const int ID = getDetector<int   >(detid);
 
  163    detid        = getDetector<string>(detid);
  164 
  165    
  166 
  167    NOTICE(
"Extracting run information from database... " << flush);
 
  168      
  170 
  171    for (
JRuns parameters; rs >> parameters; ) {
 
  172 
  173      parameters.DETID = 
ID;
 
  174 
  175      if (UTC(parameters.getRunStartTime())) {
  176        runs.insert(parameters);
  177      }
  178    }
  179 
  180    rs.Close();
  181 
  183 
  184    if (runs.empty()) {
  185      FATAL(
"No runs for detector " << detid << endl);
 
  186    }
  187 
  188    NOTICE(
"Run range " << runs.begin()->RUN << 
' ' << runs.rbegin()->RUN << endl);
 
  189 
  190    if (inputFile == "") {                    
  191 
  192      
  193 
  194      for (vector<string>::const_iterator git = source.begin(); git != source.end(); ++git) {
  195 
  198 
  199        map_type zmap;
  200 
  202 
  203        selector.add(&JRunSummaryNumbers::SOURCE_NAME, *git);
  204 
  205        try {
  206 
  207          NOTICE(
"Extracting run summmary information with source " << *git << 
" from database... " << flush);
 
  208 
  209          ResultSet& rs  = 
getResultSet(getTable<JRunSummaryNumbers>(), selector);
 
  210 
  212            zmap[parameters.RUN].insert(make_pair(parameters.PARAMETER_NAME, parameters.DATA_VALUE));
  213          }
  214        
  215          rs.Close();
  216 
  218        }
  219        catch(
const exception& error) { 
NOTICE(endl); }
 
  220 
  221        for (map_type::const_iterator run = zmap.begin(); run != zmap.end(); ++run) {
  222 
  224 
  227          quality.
run      = run->first;
 
  228 
  229          for (data_type::const_iterator p = run->second.begin(); p != run->second.end(); ++p) {
  230            quality.
put(p->first, p->second);
 
  231          }
  232 
  233          if (UTC(TTimeStamp(quality.
UTCMin_s, 0)) &&
 
  234              UTC(TTimeStamp(quality.
UTCMax_s, 0))) {
 
  235            buffer.insert(quality);
  236          }
  237        }
  238      }
  239 
  240    } else {                                  
  241 
  243 
  245 
  246      in >> comment;
  247 
  249        if (UTC(TTimeStamp(quality.UTCMin_s, 0)) &&
  250            UTC(TTimeStamp(quality.UTCMax_s, 0))) {
  251          buffer.insert(quality);
  252        }
  253      }
  254 
  255      in.close();
  256    }
  257  }
  258  catch(const exception& error) {
  259    FATAL(error.what() << endl);
 
  260  }
  261 
  262 
  263  if (getFilenameExtension(
outputFile) == ROOT_FILE_FORMAT) {
 
  264 
  265    
  266 
  268 
  269    X.push_back(runs. begin()->getRunStartTime());    
  270 
  272      X.push_back(quality->UTCMin_s);
  273      X.push_back(quality->UTCMax_s);
  274    }
  275 
  276    X.push_back(runs.rbegin()->getRunStartTime());    
  277 
  278    sort(X.begin(), X.end());
  279 
  280    struct Xmin {
  281      Xmin(double xmin) : 
  283      {}
  284 
  285      bool operator()(const double x1, const double x2) 
  286      {
  287        return x2 - x1 <= 
xmin;
 
  288      }
  289 
  291    };
  292 
  293    X.erase(unique(X.begin(), X.end(), Xmin(Tmin_s)), X.end());
  294 
  295    TH1D h0("livetime_s", NULL, X.size() - 1, X.data());
  296    TH1D h1("QAQC",       NULL, X.size() - 1, X.data());
  297 
  299 
  301 
  302      if (
debug >= debug_t) {
 
  303 
  304        cout << "Run " 
  305             << setw(8) << i->RUN                                        << ' ' 
  306             << TTimeStamp((time_t) i->UNIXSTARTTIME/1000).AsString("c") << ' ';
  307 
  308        if (quality != buffer.end())
  309          cout << "[" << TTimeStamp((time_t) quality->UTCMin_s).AsString("c") << "," << TTimeStamp((time_t) quality->UTCMax_s).AsString("c") << "]";
  310        else
  311          cout << "missing QA/QC data";
  312 
  313        cout << endl;
  314      }
  315 
  316      h1.Fill(i->getRunStartTime() + Tmin_s, (quality != buffer.end() ? 1.0 : -1.0));
  317    }
  318 
  319    JManager<string, TH1D> H1(new TH1D("H[%]", NULL, X.size() - 1, X.data()));  
  320    JManager<string, TH1D> 
R1(
new TH1D(
"R[%]", NULL, X.size() - 1, X.data()));  
 
  321 
  323 
  324      const double x = 0.5 * (quality->UTCMin_s + quality->UTCMax_s);
 
  325 
  326      h0.Fill(x, 100.0 * quality->livetime_s / (quality->UTCMax_s - quality->UTCMin_s));
  327 
  328      H1["JDAQEvent"]        -> Fill(x, quality->JDAQEvent);
  329      H1["JTrigger3DShower"] -> Fill(x, quality->JTrigger3DShower);
  330      H1["JTrigger3DMuon"]   -> Fill(x, quality->JTrigger3DMuon);
  331      H1["JTriggerMXShower"] -> Fill(x, quality->JTriggerMXShower);
  332 
  333      if (quality->livetime_s > 0.0) {
  334        R1[
"JDAQEvent"]        -> Fill(x, quality->JDAQEvent        / quality->livetime_s);
 
  335        R1[
"JTrigger3DShower"] -> Fill(x, quality->JTrigger3DShower / quality->livetime_s);
 
  336        R1[
"JTrigger3DMuon"]   -> Fill(x, quality->JTrigger3DMuon   / quality->livetime_s);
 
  337        R1[
"JTriggerMXShower"] -> Fill(x, quality->JTriggerMXShower / quality->livetime_s);
 
  338      }
  339    }
  340 
  341 
  342    Double_t W[2] = { 0.0 };
  343 
  344    W[0] = *X.rbegin() - *X.begin();
  345 
  347      W[1] += quality->livetime_s;
  348    }
  349 
  350    NOTICE(
"Average data taking efficiency  " << 
FIXED(5,1) << 100.0*W[1]/W[0] << 
" %." << endl);
 
  351 
  352 
  353    for (TH1* p : { &h0, &h1 }) {
  354      p->GetXaxis()->SetTimeDisplay(1);
  355      p->GetXaxis()->SetTimeFormat(TIMESTAMP);
  356      p->Sumw2(false);
  357    }
  358 
  359    for (JManager<string, TH1D>::iterator p = H1.begin(); p != H1.end(); ++p) {
  360 
  361      Double_t W = 0.0;
  362    
  363      for (Int_t i = 1; i <= p->second->GetXaxis()->GetNbins(); ++i) {
  364        p->second->SetBinContent(i, (W += p->second->GetBinContent(i)));
  365      }
  366    
  367      p->second->GetXaxis()->SetTimeDisplay(1);
  368      p->second->GetXaxis()->SetTimeFormat(TIMESTAMP);
  369      p->second->Sumw2(false);
  370    }
  371 
  372    for (JManager<string, TH1D>::iterator p = 
R1.begin(); p != 
R1.end(); ++p) {
 
  373 
  374      p->second->GetXaxis()->SetTimeDisplay(1);
  375      p->second->GetXaxis()->SetTimeFormat(TIMESTAMP);
  376      p->second->Sumw2(false);
  377    }
  378 
  380 
  381    out << h0 << h1 << H1 << 
R1;
 
  382 
  383    out.Write();
  384    out.Close();
  385  }
  386 
  387 
  388  if (getFilenameExtension(
outputFile) == ASCII_FILE_FORMAT) {
 
  389 
  390    
  391 
  393 
  394    out.setf(ios::fixed);
  395 
  397 
  399 
  400    out << comment;
  401 
  403      out << *i << endl;
  404    }
  405 
  406    out.close();
  407  }
  408}
#define make_field(A,...)
macro to convert parameter to JParserTemplateElement object
 
Object reading from ASCII file.
 
Object(s) writing to ASCII file.
 
Utility class to parse command line options.
 
ResultSet & getResultSet(const std::string &query)
Get result set.
 
std::vector< JServer > getServernames()
Get list of names of available database servers.
 
std::vector< std::string > getGITTags(const TRegexp ®exp, const JGITTags_t::key_type &date)
Get selection of GIT tags.
 
Auxiliary data structure for floating point format specification.
 
Data structure for measured coincidence rates of all pairs of PMTs in optical module.
 
Auxiliary data structure for data quality.
 
double UTCMin_s
minimal UTC time (from "runs" table)
 
void put(const std::string &key, const std::string &value)
Put value at given key.
 
double UTCMax_s
maximal UTC time (from "runs" table)
 
std::string GIT
GIT version used to write QA/QC data.
 
int detector
detector identifier
 
Wrapper class for server name.
 
Template definition for getting table specific selector.