LCOV - code coverage report
Current view: top level - opmonlib/plugins - fileOpMonFacility.cpp (source / functions) Coverage Total Hit
Test: code.result Lines: 84.0 % 50 42
Test Date: 2026-10-11 15:05:20 Functions: 100.0 % 7 7

            Line data    Source code
       1              : /**
       2              :  * @file fileOpMonFacility.cpp
       3              :  *
       4              :  * This is part of the DUNE DAQ Application Framework, copyright 2020.
       5              :  * Licensing/copyright details are in the COPYING file that you should have
       6              :  * received with this code.
       7              :  */
       8              : 
       9              : #include "fileOpMonFacility.hpp"
      10              : #include "opmonlib/Utils.hpp"
      11              : #include <iostream>
      12              : #include <thread>
      13              : 
      14              : #include "logging/Logging.hpp"
      15              : 
      16              : namespace dunedaq::opmonlib {
      17              : 
      18           12 : fileOpMonFacility::fileOpMonFacility(std::string uri, OptionalOrigin o)
      19           12 :   : JSonOpMonFacility(uri)
      20              : {
      21              : 
      22           12 :   std::string hook = "://";
      23           12 :   auto sep = uri.find(hook);
      24           12 :   std::string fname;
      25           12 :   if (sep == std::string::npos) { // assume filename
      26            0 :     fname = uri;
      27              :   } else {
      28           12 :     fname = uri.substr(sep + hook.size());
      29              :   }
      30              : 
      31           12 :   if (o) {
      32           11 :     auto slash_pos = fname.find_last_of('/');
      33           11 :     auto dot_pos = slash_pos == std::string::npos ? fname.find_first_of('.') : fname.find_first_of('.', slash_pos);
      34              : 
      35           11 :     auto origin = to_string(o.value());
      36           11 :     if (dot_pos == std::string::npos) {
      37            1 :       fname += '.' + origin + ".json";
      38              :     } else {
      39           10 :       fname.insert(dot_pos, '.' + origin);
      40              :     }
      41           11 :   }
      42              : 
      43           12 :   m_ofs.open(fname, std::ios::out | std::ios::app);
      44           12 :   if (!m_ofs.is_open()) {
      45            1 :     throw BadFile(ERS_HERE, fname);
      46              :   }
      47           16 : }
      48              : 
      49           22 : fileOpMonFacility::~fileOpMonFacility()
      50              : {
      51              : 
      52           11 :   std::chrono::milliseconds max_delay(m_writing_counter.load());
      53              : 
      54           11 :   m_stop_request.store(true);
      55              : 
      56           11 :   std::unique_lock<std::mutex> lock(m_mutex);
      57           22 :   auto ret = m_writing_variable.wait_for(lock, max_delay, [&]() { return m_writing_counter.load() == 0; });
      58           11 :   if (!ret) {
      59            0 :     ers::error(FileClosedBeforeWritingComplete(ERS_HERE, max_delay.count(), m_writing_counter.load()));
      60              :   }
      61           22 : }
      62              : 
      63              : void
      64         1507 : fileOpMonFacility::publish(opmon::OpMonEntry&& e) const
      65              : {
      66              : 
      67         1507 :   if (m_stop_request.load()) {
      68            0 :     throw OpMonPublishFailure(
      69            0 :       ERS_HERE, get_URI(), e.measurement(), to_string(e.origin()), FacilityStopRequested(ERS_HERE));
      70              :   }
      71              : 
      72         1506 :   ++m_writing_counter;
      73         1508 :   std::thread(&fileOpMonFacility::write, this, std::move(e)).detach();
      74         1507 : }
      75              : 
      76              : void
      77         1508 : fileOpMonFacility::write(opmon::OpMonEntry&& e) const noexcept
      78              : {
      79         1508 :   std::string json;
      80         1508 :   google::protobuf::util::MessageToJsonString(e, &json, get_json_options());
      81              : 
      82         1508 :   std::unique_lock<std::mutex> lock(m_mutex);
      83         1508 :   m_writing_variable.wait(lock, [&]() { return m_writing_counter.load() > 0; });
      84              : 
      85         1508 :   try {
      86         1508 :     m_ofs << json << std::endl << std::flush;
      87            0 :   } catch (const std::ios_base::failure& except) {
      88            0 :     ers::error(OpMonPublishFailure(
      89            0 :       ERS_HERE, get_URI(), e.measurement(), to_string(e.origin()), WritingFailed(ERS_HERE, json, except)));
      90            0 :   }
      91              : 
      92         1508 :   --m_writing_counter;
      93         1508 :   m_writing_variable.notify_one();
      94         1508 : }
      95              : 
      96              : } // namespace dunedaq::opmonlib
      97              : 
      98           14 : DEFINE_DUNE_OPMON_FACILITY(dunedaq::opmonlib::fileOpMonFacility)
        

Generated by: LCOV version 2.0-1