2020-01-20 18:08:44 +00:00
|
|
|
# frozen_string_literal: true
|
|
|
|
|
|
|
|
# Creates a link in Sentry between a Sentry issue and a GitLab issue.
|
|
|
|
# If the link already exists, no changes will occur.
|
|
|
|
# If a link to a different GitLab issue exists, a new link
|
|
|
|
# will still be created, but will not be visible in Sentry
|
|
|
|
# until the prior link is deleted.
|
2020-02-19 18:09:10 +00:00
|
|
|
class ErrorTrackingIssueLinkWorker # rubocop:disable Scalability/IdempotentWorker
|
2020-01-20 18:08:44 +00:00
|
|
|
include ApplicationWorker
|
2021-04-30 18:10:09 +00:00
|
|
|
|
2021-07-21 12:09:35 +00:00
|
|
|
data_consistency :always
|
|
|
|
|
2021-04-30 18:10:09 +00:00
|
|
|
sidekiq_options retry: 3
|
2020-01-20 18:08:44 +00:00
|
|
|
include ExclusiveLeaseGuard
|
|
|
|
include Gitlab::Utils::StrongMemoize
|
|
|
|
|
|
|
|
feature_category :error_tracking
|
|
|
|
worker_has_external_dependencies!
|
|
|
|
|
|
|
|
LEASE_TIMEOUT = 15.minutes
|
|
|
|
|
|
|
|
attr_reader :issue
|
|
|
|
|
|
|
|
def perform(issue_id)
|
|
|
|
@issue = Issue.find_by_id(issue_id)
|
|
|
|
|
2020-01-22 15:08:48 +00:00
|
|
|
return unless valid?
|
2020-01-20 18:08:44 +00:00
|
|
|
|
|
|
|
try_obtain_lease do
|
|
|
|
logger.info("Linking Sentry issue #{sentry_issue_id} to GitLab issue #{issue.id}")
|
|
|
|
|
|
|
|
sentry_client.create_issue_link(integration_id, sentry_issue_id, issue)
|
2021-03-04 15:11:19 +00:00
|
|
|
rescue ErrorTracking::SentryClient::Error => e
|
2020-03-12 18:09:28 +00:00
|
|
|
logger.info("Failed to link Sentry issue #{sentry_issue_id} to GitLab issue #{issue.id} with error: #{e.message}")
|
2020-01-20 18:08:44 +00:00
|
|
|
end
|
|
|
|
end
|
|
|
|
|
|
|
|
private
|
|
|
|
|
2020-01-22 15:08:48 +00:00
|
|
|
def valid?
|
|
|
|
issue && error_tracking && sentry_issue_id
|
|
|
|
end
|
|
|
|
|
2020-01-20 18:08:44 +00:00
|
|
|
def error_tracking
|
|
|
|
strong_memoize(:error_tracking) do
|
|
|
|
issue.project.error_tracking_setting
|
|
|
|
end
|
|
|
|
end
|
|
|
|
|
|
|
|
def sentry_issue_id
|
|
|
|
strong_memoize(:sentry_issue_id) do
|
|
|
|
issue.sentry_issue.sentry_issue_identifier
|
|
|
|
end
|
|
|
|
end
|
|
|
|
|
|
|
|
def sentry_client
|
|
|
|
error_tracking.sentry_client
|
|
|
|
end
|
|
|
|
|
|
|
|
def integration_id
|
|
|
|
strong_memoize(:integration_id) do
|
|
|
|
repo&.integration_id
|
|
|
|
end
|
|
|
|
end
|
|
|
|
|
|
|
|
def repo
|
|
|
|
sentry_client
|
|
|
|
.repos(organization_slug)
|
|
|
|
.find { |repo| repo.project_id == issue.project_id && repo.status == 'active' }
|
2021-03-04 15:11:19 +00:00
|
|
|
rescue ErrorTracking::SentryClient::Error => e
|
2020-03-19 00:09:27 +00:00
|
|
|
logger.info("Unable to retrieve Sentry repo for organization #{organization_slug}, id #{sentry_issue_id}, with error: #{e.message}")
|
|
|
|
|
|
|
|
nil
|
2020-01-20 18:08:44 +00:00
|
|
|
end
|
|
|
|
|
|
|
|
def organization_slug
|
|
|
|
error_tracking.organization_slug
|
|
|
|
end
|
|
|
|
|
|
|
|
def project_url
|
|
|
|
::Gitlab::Routing.url_helpers.project_url(issue.project)
|
|
|
|
end
|
|
|
|
|
|
|
|
def lease_key
|
|
|
|
"link_sentry_issue_#{sentry_issue_id}_gitlab_#{issue.id}"
|
|
|
|
end
|
|
|
|
|
|
|
|
def lease_timeout
|
|
|
|
LEASE_TIMEOUT
|
|
|
|
end
|
|
|
|
end
|