| // Copyright 2020 The Fuchsia Authors. All rights reserved. |
| // Use of this source code is governed by a BSD-style license that can be |
| // found in the LICENSE file. |
| |
| #include "src/local_aggregation_1_1/aggregation_procedures/select_most_common_aggregation_procedure.h" |
| |
| #include "src/logger/encoder.h" |
| #include "src/pb/observation.pb.h" |
| #include "src/public/lib/statusor/status_macros.h" |
| |
| namespace cobalt::local_aggregation { |
| |
| SelectMostCommonAggregationProcedure::SelectMostCommonAggregationProcedure( |
| const MetricDefinition &metric, const ReportDefinition &report) |
| : AggregationProcedure(metric, report) {} |
| |
| void SelectMostCommonAggregationProcedure::UpdateAggregateData( |
| const logger::EventRecord &event_record, AggregateData &aggregate_data, |
| AggregationPeriodBucket & /*bucket*/) { |
| // TODO(fxbug.dev/53775): Handle the case where event_record is malformed. |
| aggregate_data.set_count(aggregate_data.count() + |
| event_record.event()->occurrence_event().count()); |
| } |
| |
| void SelectMostCommonAggregationProcedure::MergeAggregateData(AggregateData &merged_aggregate_data, |
| const AggregateData &aggregate_data) { |
| merged_aggregate_data.set_count(merged_aggregate_data.count() + aggregate_data.count()); |
| } |
| |
| std::string SelectMostCommonAggregationProcedure::DebugString() const { |
| return "SELECT_MOST_COMMON"; |
| } |
| |
| lib::statusor::StatusOr<std::unique_ptr<Observation>> |
| SelectMostCommonAggregationProcedure::GenerateSingleObservation( |
| const std::vector<AggregateDataToGenerate> &buckets, |
| const std::set<std::vector<uint32_t>> &event_vectors, const util::TimeInfo & /*time_info*/) { |
| std::vector<std::tuple<std::vector<uint32_t>, int64_t>> data; |
| if (event_vectors.empty()) { |
| return {nullptr}; |
| } |
| data.reserve(1); |
| |
| uint32_t max_count = 0; |
| std::vector<uint32_t> selected_event_vector = {}; |
| |
| for (const std::vector<uint32_t> &event_vector : event_vectors) { |
| uint32_t event_vector_count = 0; |
| |
| for (const AggregateDataToGenerate &bucket : buckets) { |
| for (const EventCodesAggregateData &aggregate_data : bucket.aggregate_data) { |
| if (std::equal(aggregate_data.event_codes().begin(), aggregate_data.event_codes().end(), |
| event_vector.begin(), event_vector.end())) { |
| event_vector_count += aggregate_data.data().count(); |
| continue; |
| } |
| } |
| } |
| if (event_vector_count >= max_count) { |
| selected_event_vector = event_vector; |
| max_count = event_vector_count; |
| } |
| } |
| |
| data.emplace_back(std::make_tuple(selected_event_vector, 1)); |
| |
| return logger::Encoder::EncodeIntegerObservation(data); |
| } |
| |
| } // namespace cobalt::local_aggregation |