// Copyright 2018 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.
syntax = "proto3";

package cobalt;

import "observation_batch.proto";

// A row of output for a report of type SIMPLE_OCCURRENCE_COUNT.
//
// Gives the total daily, fleet-wide count of the number of occurrences of an
// event with a particular event code, on a particular day, considering only
// devices matching a particular system profile.
message SimpleOccurrenceCountReportRow {
  // The date on which the logged events occurred, as measured on the device.
  // This is a string in yyyy-mm-dd format.
  string date = 1;

  // A profile of the system from which the events were logged. This will be
  // populated with only the fields that are specified in the
  // |system_profile_field| entry in the ReportDefinition for this report.
  SystemProfile system_profile = 2;

  // The label for the event code associated with the events that occurred. If
  // the event_code has not been assigned a label (in the event_codes field of
  // the MetricDefinition) then this will be a string of the form
  // "<event-code-42>".
  string event_code = 3;

  // The total count of the event occurrence on the |date|, over all reporting
  // devices with the |system_profile|. Unless |local_privacy_noise_level| in
  // the Reportdefintion is set to NONE, this value is an estimate.
  float count = 4;

  // An estimate of the standard error in the value of the |count|. This will
  // be zero if |local_privacy_noise_level| in the Reportdefintion is NONE.
  // Multiply this value by z_{alpha/2} to obtain the radius of an approximate
  // 100(1 - alpha)% confidence interval. For example an approximate 95%
  // confidence interval for the count is given by
  // (count_estimate - 1.96*std_error, count_estimate + 1.96 * std_error)
  // because 1.96 ~= z_{.025} meaning that P(Z > 1.96) ~= 0.025 where
  // Z ~ Normal(0, 1).
  float std_err = 5;
}

// A row of output for a report of type EVENT_COMPONENT_OCCURRENCE_COUNT.
//
// Gives the total daily fleet-wide count of the number of occurrences of an
// event with a particular event code, for a particular component, on a
// particular day, considering only devices matching a particular system
// profile.
message EventComponentOccurrenceCountReportRow {
  // The date on which the logged events occurred, as measured on the device.
  // This is a string in yyyy-mm-dd format.
  string date = 1;

  // A profile of the system from which the events were logged. This will be
  // populated with only the fields that are specified in the
  // |system_profile_field| entry in the ReportDefinition for this report.
  SystemProfile system_profile = 2;

  // The label for the event code associated with the events that occurred. If
  // the event code has not been assigned a label (in the event_codes field of
  // the MetricDefinition) then this will be a string of the form
  // "<event-code-42>".
  string event_code = 3;

  // The component string associated with the events that occurred. This string
  // must have been pre-registered in the ReportDefinition (using the
  // |candidate_list| or |candidate_file| fields). There are also two special
  // values of |component|.
  // "<NONE>" is the component associated with logged events that
  // contained an empty component string.
  // "<OTHER>" is the component associated with logged events that contained
  // a non-empty component string that was not pre-registered.
  string component = 4;

  // The total sum of the event occurrence counts for events with the
  // |event_code| and |component|, on the |date|, over all
  // reporting devices with the |system_profile|.
  int64 sum = 5;

  // The count of Observations that contributed to the |sum|.
  int64 count = 6;
}

// A row of output for a report of type INT_RANGE_HISTOGRAM.
//
// Gives the value for one bucket of an integer range histogram, aggregated
// over the fleet, for a particular event code, a particular component, on a
// particular day, considering only devices matching a particular system
// profile.
message IntRangeHistogramReportRow {
  // The date on which the logged events occurred, as measured on the device.
  // This is a string in yyyy-mm-dd format.
  string date = 1;

  // A profile of the system from which the events were logged. This will be
  // populated with only the fields that are specified in the
  // |system_profile_field| entry in the ReportDefinition for this report.
  SystemProfile system_profile = 2;

  // The label for the event code associated with the events that occurred. If
  // the event code has not been assigned a label (in the event_codes field of
  // the MetricDefinition) then this will be a string of the form
  // "<event-code-42>".
  string event_code = 3;

  // The component string associated with the events that occurred. This string
  // must have been pre-registered in the ReportDefinition (using the
  // |candidate_list| or |candidate_file| fields). There are also two special
  // values of |component|.
  // "<NONE>" is the component associated with logged events that
  // contained an empty component string.
  // "<OTHER>" is the component associated with logged events that contained
  // a non-empty component string that was not pre-registered.
  string component = 4;

  // String describing the interval of integers for this bucket, such as
  // "10-15".
  string bucket_name = 5;

  // The count for this bucket.
  int64 bucket_count = 6;
}
