3838#include " base/itertools.hh"
3939#include " base/time_util.hh"
4040#include " file_collection.hh"
41+ #include " log_format.hh"
4142#include " logfile.hh"
4243#include " robin_hood/robin_hood.h"
4344#include " vtab_module.hh"
@@ -52,14 +53,16 @@ CREATE TABLE all_opids (
5253 latest DATETIME, -- The latest time this ID was seen
5354 errors INTEGER, -- The number of error messages associated with this ID
5455 warnings INTEGER, -- The number of warning messages associated with this ID
55- total INTEGER -- The total number of messages associated with this ID
56+ total INTEGER, -- The total number of messages associated with this ID
57+ description TEXT -- A description of the operation
5658);
5759)" ;
5860
5961 struct cursor {
6062 struct opid_time_pair {
6163 std::string otp_opid;
6264 opid_time_range otp_range;
65+ std::string otp_description;
6366
6467 bool operator <(const opid_time_pair& rhs) const
6568 {
@@ -84,11 +87,31 @@ CREATE TABLE all_opids (
8487 auto key_str = key.to_string ();
8588 auto gather_iter = gather_map.find (key_str);
8689 if (gather_iter == gather_map.end ()) {
87- gather_map[key_str].otp_opid = key_str;
88- gather_map[key_str].otp_range = om;
90+ auto emplace_res = gather_map.emplace (
91+ key_str, opid_time_pair{key_str, om});
92+ gather_iter = emplace_res.first ;
8993 } else {
9094 gather_iter->second .otp_range |= om;
9195 }
96+ if (gather_iter->second .otp_description .empty ()) {
97+ auto format = lf->get_format ();
98+ if (om.otr_description .lod_id .has_value ()) {
99+ auto desc_iter
100+ = format->lf_opid_description_def ->find (
101+ om.otr_description .lod_id .value ());
102+ if (desc_iter
103+ != format->lf_opid_description_def ->end ())
104+ {
105+ gather_iter->second .otp_description
106+ = desc_iter->second .to_string (
107+ om.otr_description .lod_elements );
108+ }
109+ } else if (!om.otr_description .lod_elements .empty ()) {
110+ gather_iter->second .otp_description
111+ = om.otr_description .lod_elements .front ()
112+ .second ;
113+ }
114+ }
92115 }
93116 }
94117 for (const auto & [key, value] : gather_map) {
@@ -156,10 +179,52 @@ CREATE TABLE all_opids (
156179 vc.c_iter ->otp_range .otr_level_stats .lls_total_count );
157180 break ;
158181 }
182+ case 6 : {
183+ if (vc.c_iter ->otp_description .empty ()) {
184+ sqlite3_result_null (ctx);
185+ } else {
186+ to_sqlite (ctx, vc.c_iter ->otp_description );
187+ }
188+ break ;
189+ }
159190 }
160191
161192 return SQLITE_OK ;
162193 }
194+
195+ int delete_row (sqlite3_vtab* tab, sqlite3_int64 rowid)
196+ {
197+ tab->zErrMsg = sqlite3_mprintf (
198+ " Rows cannot be deleted from the all_opids table" );
199+ return SQLITE_ERROR ;
200+ }
201+
202+ int insert_row (sqlite3_vtab* tab, sqlite3_int64& rowid_out)
203+ {
204+ tab->zErrMsg = sqlite3_mprintf (
205+ " Rows cannot be inserted into the all_opids table" );
206+ return SQLITE_ERROR ;
207+ }
208+
209+ int update_row (sqlite3_vtab* tab,
210+ sqlite3_int64& index,
211+ string_fragment opid,
212+ string_fragment earliest,
213+ string_fragment latest,
214+ int64_t errors,
215+ int64_t warnings,
216+ int64_t total,
217+ std::optional<string_fragment> description)
218+ {
219+ if (description) {
220+ const auto & active_files = injector::get<file_collection&>();
221+
222+ for (const auto & lf : active_files.fc_files ) {
223+ lf->set_opid_description (opid, description.value ());
224+ }
225+ }
226+ return SQLITE_OK ;
227+ }
163228};
164229
165230struct all_thread_ids {
@@ -286,7 +351,7 @@ CREATE TABLE all_thread_ids (
286351};
287352
288353auto all_vtabs_binder = injector::bind_multiple<vtab_module_base>()
289- .add<vtab_module<tvt_no_update< all_opids> >>()
354+ .add<vtab_module<all_opids>>()
290355 .add<vtab_module<tvt_no_update<all_thread_ids>>>();
291356
292357} // namespace
0 commit comments