diff options
Diffstat (limited to 'app/services/projects/prometheus/alerts/create_events_service.rb')
-rw-r--r-- | app/services/projects/prometheus/alerts/create_events_service.rb | 75 |
1 files changed, 75 insertions, 0 deletions
diff --git a/app/services/projects/prometheus/alerts/create_events_service.rb b/app/services/projects/prometheus/alerts/create_events_service.rb new file mode 100644 index 00000000000..a29240947ff --- /dev/null +++ b/app/services/projects/prometheus/alerts/create_events_service.rb @@ -0,0 +1,75 @@ +# frozen_string_literal: true + +module Projects + module Prometheus + module Alerts + # Persists a series of Prometheus alert events as list of PrometheusAlertEvent. + class CreateEventsService < BaseService + def execute + create_events_from(alerts) + end + + private + + def create_events_from(alerts) + Array.wrap(alerts).map { |alert| create_event(alert) }.compact + end + + def create_event(payload) + parsed_alert = Gitlab::Alerting::Alert.new(project: project, payload: payload) + + return unless parsed_alert.valid? + + if parsed_alert.gitlab_managed? + create_managed_prometheus_alert_event(parsed_alert) + else + create_self_managed_prometheus_alert_event(parsed_alert) + end + end + + def alerts + params['alerts'] + end + + def find_alert(metric) + Projects::Prometheus::AlertsFinder + .new(project: project, metric: metric) + .execute + .first + end + + def create_managed_prometheus_alert_event(parsed_alert) + alert = find_alert(parsed_alert.metric_id) + payload_key = PrometheusAlertEvent.payload_key_for(parsed_alert.metric_id, parsed_alert.starts_at_raw) + + event = PrometheusAlertEvent.find_or_initialize_by_payload_key(parsed_alert.project, alert, payload_key) + + set_status(parsed_alert, event) + end + + def create_self_managed_prometheus_alert_event(parsed_alert) + payload_key = SelfManagedPrometheusAlertEvent.payload_key_for(parsed_alert.starts_at_raw, parsed_alert.title, parsed_alert.full_query) + + event = SelfManagedPrometheusAlertEvent.find_or_initialize_by_payload_key(parsed_alert.project, payload_key) do |event| + event.environment = parsed_alert.environment + event.title = parsed_alert.title + event.query_expression = parsed_alert.full_query + end + + set_status(parsed_alert, event) + end + + def set_status(parsed_alert, event) + persisted = case parsed_alert.status + when 'firing' + event.fire(parsed_alert.starts_at) + when 'resolved' + event.resolve(parsed_alert.ends_at) + end + + event if persisted + end + end + end + end +end |