lib/pact_broker/webhooks/service.rb in pact_broker-2.79.1 vs lib/pact_broker/webhooks/service.rb in pact_broker-2.80.0
- old
+ new
@@ -1,45 +1,57 @@
-require 'pact_broker/repositories'
-require 'pact_broker/services'
-require 'pact_broker/logging'
-require 'base64'
-require 'securerandom'
-require 'pact_broker/webhooks/job'
-require 'pact_broker/webhooks/triggered_webhook'
-require 'pact_broker/webhooks/status'
-require 'pact_broker/webhooks/webhook_event'
-require 'pact_broker/verifications/placeholder_verification'
-require 'pact_broker/pacts/placeholder_pact'
-require 'pact_broker/api/decorators/webhook_decorator'
-require 'pact_broker/hash_refinements'
-require 'pact_broker/webhooks/execution_configuration'
-require 'pact_broker/messages'
-require 'pact_broker/webhooks/pact_and_verification_parameters'
+require "delegate"
+require "pact_broker/repositories"
+require "pact_broker/services"
+require "pact_broker/logging"
+require "base64"
+require "securerandom"
+require "pact_broker/webhooks/job"
+require "pact_broker/webhooks/triggered_webhook"
+require "pact_broker/webhooks/status"
+require "pact_broker/webhooks/webhook_event"
+require "pact_broker/verifications/placeholder_verification"
+require "pact_broker/pacts/placeholder_pact"
+require "pact_broker/api/decorators/webhook_decorator"
+require "pact_broker/hash_refinements"
+require "pact_broker/webhooks/execution_configuration"
+require "pact_broker/messages"
+require "pact_broker/webhooks/pact_and_verification_parameters"
+require "pact_broker/feature_toggle"
module PactBroker
module Webhooks
- class Service
+ module Service
using PactBroker::HashRefinements
-
- RESOURCE_CREATION = PactBroker::Webhooks::TriggeredWebhook::TRIGGER_TYPE_RESOURCE_CREATION
- USER = PactBroker::Webhooks::TriggeredWebhook::TRIGGER_TYPE_USER
-
+ extend self
+ extend Forwardable
extend Repositories
extend Services
include Logging
extend PactBroker::Messages
+ delegate [
+ :find_by_uuid,
+ :find_all,
+ :update_triggered_webhook_status,
+ :any_webhooks_configured_for_pact?,
+ :find_by_consumer_and_provider,
+ :find_latest_triggered_webhooks_for_pact,
+ :fail_retrying_triggered_webhooks,
+ :find_triggered_webhooks_for_pact,
+ :find_triggered_webhooks_for_verification
+ ] => :webhook_repository
+
# Not actually a UUID. Ah well.
- def self.valid_uuid_format?(uuid)
+ def valid_uuid_format?(uuid)
!!(uuid =~ /^[A-Za-z0-9_\-]{16,}$/)
end
- def self.next_uuid
+ def next_uuid
SecureRandom.urlsafe_base64
end
- def self.errors webhook, uuid = nil
+ def errors webhook, uuid = nil
contract = PactBroker::Api::Contracts::WebhookContract.new(webhook)
contract.validate(webhook.attributes)
messages = contract.errors.messages
if uuid && !valid_uuid_format?(uuid)
@@ -47,132 +59,38 @@
end
OpenStruct.new(messages: messages, empty?: messages.empty?, any?: messages.any?)
end
- def self.create uuid, webhook, consumer, provider
+ def create uuid, webhook, consumer, provider
webhook_repository.create uuid, webhook, consumer, provider
end
- def self.find_by_uuid uuid
- webhook_repository.find_by_uuid uuid
- end
-
- def self.update_by_uuid uuid, params
+ def update_by_uuid uuid, params
webhook = webhook_repository.find_by_uuid(uuid)
maintain_redacted_params(webhook, params)
PactBroker::Api::Decorators::WebhookDecorator.new(webhook).from_hash(params)
webhook_repository.update_by_uuid uuid, webhook
end
- def self.delete_by_uuid uuid
- webhook_repository.delete_triggered_webhooks_by_webhook_uuid uuid
+ def delete_by_uuid uuid
webhook_repository.delete_by_uuid uuid
end
- def self.delete_all_webhhook_related_objects_by_pacticipant pacticipant
- webhook_repository.delete_executions_by_pacticipant pacticipant
- webhook_repository.delete_triggered_webhooks_by_pacticipant pacticipant
- webhook_repository.delete_by_pacticipant pacticipant
+ def delete_all_webhhook_related_objects_by_pacticipant pacticipant
+ webhook_repository.delete_by_pacticipant(pacticipant)
end
- def self.delete_all_webhook_related_objects_by_pact_publication_ids pact_publication_ids
+ def delete_all_webhook_related_objects_by_pact_publication_ids pact_publication_ids
webhook_repository.delete_triggered_webhooks_by_pact_publication_ids pact_publication_ids
end
- def self.delete_all_webhook_related_objects_by_verification_ids verification_ids
+ def delete_all_webhook_related_objects_by_verification_ids verification_ids
webhook_repository.delete_triggered_webhooks_by_verification_ids verification_ids
end
- def self.find_all
- webhook_repository.find_all
- end
-
- def self.test_execution webhook, event_context, execution_configuration
- merged_options = execution_configuration.with_failure_log_message("Webhook execution failed").to_hash
-
- verification = nil
- if webhook.trigger_on_provider_verification_published?
- verification = verification_service.search_for_latest(webhook.consumer_name, webhook.provider_name) || PactBroker::Verifications::PlaceholderVerification.new
- end
-
- pact = pact_service.search_for_latest_pact(consumer_name: webhook.consumer_name, provider_name: webhook.provider_name) || PactBroker::Pacts::PlaceholderPact.new
- webhook.execute(pact, verification, event_context.merge(event_name: "test"), merged_options)
- end
-
- def self.execute_triggered_webhook_now triggered_webhook, webhook_execution_configuration_hash
- webhook_execution_result = triggered_webhook.execute webhook_execution_configuration_hash
- webhook_repository.create_execution triggered_webhook, webhook_execution_result
- webhook_execution_result
- end
-
- def self.update_triggered_webhook_status triggered_webhook, status
- webhook_repository.update_triggered_webhook_status triggered_webhook, status
- end
-
- def self.find_for_pact pact
- webhook_repository.find_for_pact(pact)
- end
-
- def self.find_by_consumer_and_or_provider consumer, provider
- webhook_repository.find_by_consumer_and_or_provider(consumer, provider)
- end
-
- def self.find_by_consumer_and_provider consumer, provider
- webhook_repository.find_by_consumer_and_provider consumer, provider
- end
-
- def self.trigger_webhooks pact, verification, event_name, event_context, options
- webhooks = webhook_repository.find_by_consumer_and_or_provider_and_event_name pact.consumer, pact.provider, event_name
-
- if webhooks.any?
- webhook_execution_configuration = options.fetch(:webhook_execution_configuration).with_webhook_context(event_name: event_name)
- # bit messy to merge in base_url here, but easier than a big refactor
- base_url = options.fetch(:webhook_execution_configuration).webhook_context.fetch(:base_url)
- run_later(webhooks, pact, verification, event_name, event_context.merge(event_name: event_name, base_url: base_url), options.merge(webhook_execution_configuration: webhook_execution_configuration))
- else
- logger.info "No enabled webhooks found for consumer \"#{pact.consumer.name}\" and provider \"#{pact.provider.name}\" and event #{event_name}"
- end
- end
-
- def self.run_later webhooks, pact, verification, event_name, event_context, options
- trigger_uuid = next_uuid
- webhooks.each do | webhook |
- begin
- triggered_webhook = webhook_repository.create_triggered_webhook(trigger_uuid, webhook, pact, verification, RESOURCE_CREATION, event_name, event_context)
- logger.info "Scheduling job for webhook with uuid #{webhook.uuid}"
- logger.debug "Schedule webhook with options #{options}"
- job_data = { triggered_webhook: triggered_webhook }.deep_merge(options)
- # Delay slightly to make sure the request transaction has finished before we execute the webhook
- Job.perform_in(5, job_data)
- rescue StandardError => e
- logger.warn("Error scheduling webhook execution for webhook with uuid #{webhook.uuid}", e)
- end
- end
- end
-
- def self.find_latest_triggered_webhooks_for_pact pact
- webhook_repository.find_latest_triggered_webhooks_for_pact pact
- end
-
- def self.find_latest_triggered_webhooks consumer, provider
- webhook_repository.find_latest_triggered_webhooks consumer, provider
- end
-
- def self.fail_retrying_triggered_webhooks
- webhook_repository.fail_retrying_triggered_webhooks
- end
-
- def self.find_triggered_webhooks_for_pact pact
- webhook_repository.find_triggered_webhooks_for_pact(pact)
- end
-
- def self.find_triggered_webhooks_for_verification verification
- webhook_repository.find_triggered_webhooks_for_verification(verification)
- end
-
- def self.parameters
+ def parameters
PactAndVerificationParameters::ALL.collect do | parameter |
OpenStruct.new(
name: parameter,
description: message("messages.webhooks.parameters.#{parameter}")
)
@@ -183,26 +101,26 @@
# Dirty hack to maintain existing password or Authorization header if it is submitted with value ****
# This is required because the password and Authorization header is **** out in the API response
# for security purposes, so it would need to be re-entered with every response.
# TODO implement proper 'secrets' management.
- def self.maintain_redacted_params(webhook, params)
+ def maintain_redacted_params(webhook, params)
if webhook.request.password && password_key_does_not_exist_or_is_starred?(params)
- params['request']['password'] = webhook.request.password
+ params["request"]["password"] = webhook.request.password
end
- new_headers = params['request']['headers'] ||= {}
+ new_headers = params["request"]["headers"] ||= {}
existing_headers = webhook.request.headers
- starred_new_headers = new_headers.select { |key, value| value =~ /^\**$/ }
- starred_new_headers.each do | (key, value) |
+ starred_new_headers = new_headers.select { |_key, value| value =~ /^\**$/ }
+ starred_new_headers.each do | (key, _value) |
new_headers[key] = existing_headers[key]
end
- params['request']['headers'] = new_headers
+ params["request"]["headers"] = new_headers
params
end
- def self.password_key_does_not_exist_or_is_starred?(params)
- !params['request'].key?('password') || params.dig('request','password') =~ /^\**$/
+ def password_key_does_not_exist_or_is_starred?(params)
+ !params["request"].key?("password") || params.dig("request","password") =~ /^\**$/
end
end
end
end