artdaq_demo_hdf5  v1_00_00
HDFFileOutput_module.cc
1 #define TRACE_NAME "HDFFileOutput"
2 
3 #include "artdaq-demo-hdf5/HDF5/MakeDatasetPlugin.hh"
4 
5 #include "art/Framework/Core/ModuleMacros.h"
6 #include "art/Framework/Core/OutputModule.h"
7 #include "art/Framework/IO/FileStatsCollector.h"
8 #include "art/Framework/IO/PostCloseFileRenamer.h"
9 #include "art/Framework/Principal/EventPrincipal.h"
10 #include "art/Framework/Principal/Handle.h"
11 #include "art/Framework/Principal/RunPrincipal.h"
12 #include "art/Framework/Principal/SubRunPrincipal.h"
13 #include "art/Persistency/Common/GroupQueryResult.h"
14 #include "canvas/Utilities/DebugMacros.h"
15 #include "canvas/Utilities/Exception.h"
16 #include "fhiclcpp/ParameterSet.h"
17 
18 #include "artdaq/DAQdata/Globals.hh"
19 
20 #include <stdio.h>
21 #include <unistd.h>
22 #include <fstream>
23 #include <iomanip>
24 #include <iostream>
25 #include <memory>
26 #include <sstream>
27 #include <string>
28 #include <vector>
29 
30 namespace art {
31 class HDFFileOutput;
32 }
33 
34 using art::HDFFileOutput;
35 using fhicl::ParameterSet;
36 
40 class art::HDFFileOutput final : public OutputModule
41 {
42 public:
54  explicit HDFFileOutput(ParameterSet const& ps);
55 
59  virtual ~HDFFileOutput();
60 
61 private:
62  void beginJob() override;
63 
64  void endJob() override;
65 
66  void write(EventPrincipal&) override;
67 
68  void writeRun(RunPrincipal&) override{};
69  void writeSubRun(SubRunPrincipal&) override{};
70 
71 private:
72  std::string name_ = "HDFFileOutput";
73  art::FileStatsCollector fstats_;
74 
75  std::unique_ptr<artdaq::hdf5::FragmentDataset> ntuple_;
76 };
77 
78 art::HDFFileOutput::HDFFileOutput(ParameterSet const& ps)
79  : OutputModule(ps)
80  , fstats_{name_, processName()}
81 {
82  TLOG(TLVL_DEBUG) << "Begin: HDFFileOutput::HDFFileOutput(ParameterSet const& ps)\n";
83  ntuple_ = artdaq::hdf5::MakeDatasetPlugin(ps, "dataset");
84  TLOG(TLVL_DEBUG)
85  << "End: HDFFileOutput::HDFFileOutput(ParameterSet const& ps)\n";
86 }
87 
88 art::HDFFileOutput::~HDFFileOutput() { TLOG(TLVL_DEBUG) << "Begin/End: HDFFileOutput::~HDFFileOutput()\n"; }
89 
90 void art::HDFFileOutput::beginJob()
91 {
92  TLOG(TLVL_DEBUG) << "Begin: HDFFileOutput::beginJob()\n";
93  TLOG(TLVL_DEBUG) << "End: HDFFileOutput::beginJob()\n";
94 }
95 
96 void art::HDFFileOutput::endJob()
97 {
98  TLOG(TLVL_DEBUG) << "Begin: HDFFileOutput::endJob()\n";
99  TLOG(TLVL_DEBUG) << "End: HDFFileOutput::endJob()\n";
100 }
101 
102 void art::HDFFileOutput::write(EventPrincipal& ep)
103 {
104  TLOG(TLVL_TRACE) << "Begin: HDFFileOutput::write(EventPrincipal& ep)";
105  using RawEvent = artdaq::Fragments;
106  using RawEvents = std::vector<RawEvent>;
107  using RawEventHandle = art::Handle<RawEvent>;
108  using RawEventHeaderHandle = art::Handle<artdaq::detail::RawEventHeader>;
109 
110  auto hdr_found = false;
111  auto sequence_id = artdaq::Fragment::InvalidSequenceID;
112 
113  TLOG(5) << "write: Retrieving event Fragments";
114  {
115  auto result_handles = std::vector<art::GroupQueryResult>();
116  auto const& wrapped = art::WrappedTypeID::make<RawEvent>();
117 #if ART_HEX_VERSION >= 0x30000
118  ModuleContext const mc{moduleDescription()};
119  ProcessTag const processTag{"", mc.moduleDescription().processName()};
120 
121  result_handles = ep.getMany(mc, wrapped, art::MatchAllSelector{}, processTag);
122 #else
123  result_handles = ep.getMany(wrapped, art::MatchAllSelector{});
124 #endif
125 
126  for (auto const& result_handle : result_handles)
127  {
128  auto const raw_event_handle = RawEventHandle(result_handle);
129 
130  if (raw_event_handle.isValid() && raw_event_handle.product()->size() > 0)
131  {
132  TLOG(10) << "raw_event_handle labels: branchName:" << raw_event_handle.provenance()->branchName();
133  TLOG(10) << "raw_event_handle labels: friendlyClassName:" << raw_event_handle.provenance()->friendlyClassName();
134  TLOG(10) << "raw_event_handle labels: inputTag:" << raw_event_handle.provenance()->inputTag();
135  TLOG(10) << "raw_event_handle labels: moduleLabel:" << raw_event_handle.provenance()->moduleLabel();
136  TLOG(10) << "raw_event_handle labels: processName:" << raw_event_handle.provenance()->processName();
137  sequence_id = (*raw_event_handle).front().sequenceID();
138 
139  TLOG(5) << "write: Writing to dataset";
140  ntuple_->insertMany(*raw_event_handle);
141  }
142  }
143  }
144  TLOG(5) << "write: Retrieving Event Header";
145  {
146  auto result_handles = std::vector<art::GroupQueryResult>();
147  auto const& wrapped = art::WrappedTypeID::make<artdaq::detail::RawEventHeader>();
148 #if ART_HEX_VERSION >= 0x30000
149  ModuleContext const mc{moduleDescription()};
150  ProcessTag const processTag{"", mc.moduleDescription().processName()};
151 
152  result_handles = ep.getMany(mc, wrapped, art::MatchAllSelector{}, processTag);
153 #else
154  result_handles = ep.getMany(wrapped, art::MatchAllSelector{});
155 #endif
156 
157  for (auto const& result_handle : result_handles)
158  {
159  auto const raw_event_header_handle = RawEventHeaderHandle(result_handle);
160 
161  if (raw_event_header_handle.isValid())
162  {
163  auto const& header = *raw_event_header_handle;
164 
165  auto evt_sequence_id = header.sequence_id;
166  TLOG(TLVL_TRACE) << "HDFFileOutput::write header seq=" << evt_sequence_id;
167 
168  ntuple_->insertHeader(header);
169 
170  hdr_found = true;
171  TLOG(5) << "HDFFileOutput::write header seq=" << evt_sequence_id << " done errno=" << errno;
172  }
173  }
174  }
175  if (!hdr_found)
176  {
177  TLOG(5) << "write: Header not found, autogenerating";
178  artdaq::detail::RawEventHeader hdr(ep.run(), ep.subRun(), ep.event(), sequence_id);
179  hdr.is_complete = true;
180 
181  ntuple_->insertHeader(hdr);
182  }
183 
184 #if ART_HEX_VERSION < 0x30000
185  fstats_.recordEvent(ep.id());
186 #else
187  fstats_.recordEvent(ep.eventID());
188 #endif
189  TLOG(TLVL_TRACE) << "End: HDFFileOUtput::write(EventPrincipal& ep)";
190  return;
191 }
192 
193 DEFINE_ART_MODULE(art::HDFFileOutput)
The HDFFileOutput module streams art Events to a binary file, bypassing ROOT.
virtual ~HDFFileOutput()
HDFFileOutput Destructor.
HDFFileOutput(ParameterSet const &ps)
HDFFileOutput Constructor.