diff options
author | syasonik <syasonik@gitlab.com> | 2019-04-11 15:36:47 +0300 |
---|---|---|
committer | syasonik <syasonik@gitlab.com> | 2019-04-24 13:23:03 +0300 |
commit | 7eb796e6b1b1c6e3ceeb85746bc7d9e8f9a519de (patch) | |
tree | 8d82f61b46e02b62befa083e28bc8c5f3a546476 | |
parent | 185ec80751c665bdde6f5494d7cb51acbb2784a4 (diff) |
Inject dashboard response with db info
-rw-r--r-- | app/services/metrics_dashboard_processing_service.rb | 88 | ||||
-rw-r--r-- | app/services/metrics_dashboard_service.rb | 8 |
2 files changed, 94 insertions, 2 deletions
diff --git a/app/services/metrics_dashboard_processing_service.rb b/app/services/metrics_dashboard_processing_service.rb new file mode 100644 index 00000000000..2bfeccc2644 --- /dev/null +++ b/app/services/metrics_dashboard_processing_service.rb @@ -0,0 +1,88 @@ +# frozen_string_literal: true + +class MetricsDashboardProcessingService + DEFAULT_PANEL_TYPE = 'area-chart' + + def initialize(dashboard, project) + @dashboard = dashboard.deep_transform_keys(&:to_sym) + @project = project + end + + def process + insert_persisted_metrics! + insert_metric_ids! + @dashboard.to_json + end + + private + + # Inserts project-specific metrics into the dashboard config. + # If there are no project-specific metrics, this will have no effect. + def insert_persisted_metrics! + @project.prometheus_metrics.each do |persisted_metric| + group = find_or_create_group(@dashboard[:panel_groups], persisted_metric) + panel = find_or_create_panel(group[:panels], persisted_metric) + find_or_create_metric(panel[:metrics], persisted_metric) + end + end + + # For each metric in the dashboard config, attempts to find a corresponding + # persisted record. If found, includes the record id in the config. + def insert_metric_ids! + @dashboard[:panel_groups].each do |group| + group[:panels].each do |panel| + panel[:metrics].each do |metric| + metric_record = common_metrics.find {|m| m.identifier == metric[:id] } + metric[:metric_id] = metric_record.id if metric_record + end + end + end + end + + def common_metrics + @common_metrics ||= ::PrometheusMetric.common + end + + def find_or_create_group(panel_groups, metric) + target_group = panel_groups.find { |group| group[:group] == metric.group_title } + + unless target_group + target_group = { + group: metric.group_title, + priority: metric.priority, + panels: [] + } + panel_groups << target_group + end + + target_group + end + + def find_or_create_panel(panels, metric) + panel_identifiers = [DEFAULT_PANEL_TYPE, metric.title, metric.y_label] + target_panel = panels.find { |panel| panel.values_at(:type, :title, :y_label) == panel_identifiers } + + unless target_panel + target_panel = { + type: DEFAULT_PANEL_TYPE, + title: metric.title, + y_label: metric.y_label, + metrics: [] + } + panels << target_panel + end + + target_panel + end + + def find_or_create_metric(metrics, metric) + target_metric = metrics.find { |m| m[:id] == metric.identifier } + + unless target_metric + target_metric = metric.queries.first.merge(metric_id: metric.id) + metrics << target_metric + end + + target_metric + end +end diff --git a/app/services/metrics_dashboard_service.rb b/app/services/metrics_dashboard_service.rb index 2f5c6cb4532..3502c1ca221 100644 --- a/app/services/metrics_dashboard_service.rb +++ b/app/services/metrics_dashboard_service.rb @@ -3,7 +3,11 @@ # Fetches the metrics dashboard layout and supplemented the output with DB info. class MetricsDashboardService SYSTEM_DASHBOARD_NAME = 'system_dashboard' - SYSTEM_DASHBOARD_PATH = Rails.root.join("config/prometheus", "#{SYSTEM_DASHBOARD_NAME}.yml") + SYSTEM_DASHBOARD_PATH = Rails.root.join('config', 'prometheus', "#{SYSTEM_DASHBOARD_NAME}.yml") + + def initialize(project) + @project = project + end # Returns a DB-supplemented json representation of a dashboard config file. def get_dashboard @@ -26,6 +30,6 @@ class MetricsDashboardService # TODO: "Processing" the dashboard needs to include several steps such as # inserting metric ids and alert information. def process_dashboard(dashboard) - dashboard.to_json + MetricsDashboardProcessingService.new(dashboard, @project).process end end |