summaryrefslogtreecommitdiff
path: root/lib/atlassian/jira_connect/client.rb
diff options
context:
space:
mode:
Diffstat (limited to 'lib/atlassian/jira_connect/client.rb')
-rw-r--r--lib/atlassian/jira_connect/client.rb73
1 files changed, 71 insertions, 2 deletions
diff --git a/lib/atlassian/jira_connect/client.rb b/lib/atlassian/jira_connect/client.rb
index da24d0e20ee..c67fe24d456 100644
--- a/lib/atlassian/jira_connect/client.rb
+++ b/lib/atlassian/jira_connect/client.rb
@@ -16,11 +16,15 @@ module Atlassian
common = { project: project, update_sequence_id: update_sequence_id }
dev_info = args.slice(:commits, :branches, :merge_requests)
build_info = args.slice(:pipelines)
+ deploy_info = args.slice(:deployments)
+ ff_info = args.slice(:feature_flags)
responses = []
responses << store_dev_info(**common, **dev_info) if dev_info.present?
responses << store_build_info(**common, **build_info) if build_info.present?
+ responses << store_deploy_info(**common, **deploy_info) if deploy_info.present?
+ responses << store_ff_info(**common, **ff_info) if ff_info.present?
raise ArgumentError, 'Invalid arguments' if responses.empty?
responses.compact
@@ -28,11 +32,47 @@ module Atlassian
private
+ def store_ff_info(project:, feature_flags:, **opts)
+ return unless Feature.enabled?(:jira_sync_feature_flags, project)
+
+ items = feature_flags.map { |flag| ::Atlassian::JiraConnect::Serializers::FeatureFlagEntity.represent(flag, opts) }
+ items.reject! { |item| item.issue_keys.empty? }
+
+ return if items.empty?
+
+ r = post('/rest/featureflags/0.1/bulk', {
+ flags: items,
+ properties: { projectId: "project-#{project.id}" }
+ })
+
+ handle_response(r, 'feature flags') do |data|
+ failed = data['failedFeatureFlags']
+ if failed.present?
+ errors = failed.flat_map do |k, errs|
+ errs.map { |e| "#{k}: #{e['message']}" }
+ end
+ { 'errorMessages' => errors }
+ end
+ end
+ end
+
+ def store_deploy_info(project:, deployments:, **opts)
+ return unless Feature.enabled?(:jira_sync_deployments, project)
+
+ items = deployments.map { |d| ::Atlassian::JiraConnect::Serializers::DeploymentEntity.represent(d, opts) }
+ items.reject! { |d| d.issue_keys.empty? }
+
+ return if items.empty?
+
+ r = post('/rest/deployments/0.1/bulk', { deployments: items })
+ handle_response(r, 'deployments') { |data| errors(data, 'rejectedDeployments') }
+ end
+
def store_build_info(project:, pipelines:, update_sequence_id: nil)
return unless Feature.enabled?(:jira_sync_builds, project)
builds = pipelines.map do |pipeline|
- build = Serializers::BuildEntity.represent(
+ build = ::Atlassian::JiraConnect::Serializers::BuildEntity.represent(
pipeline,
update_sequence_id: update_sequence_id
)
@@ -42,7 +82,8 @@ module Atlassian
end.compact
return if builds.empty?
- post('/rest/builds/0.1/bulk', { builds: builds })
+ r = post('/rest/builds/0.1/bulk', { builds: builds })
+ handle_response(r, 'builds') { |data| errors(data, 'rejectedBuilds') }
end
def store_dev_info(project:, commits: nil, branches: nil, merge_requests: nil, update_sequence_id: nil)
@@ -75,6 +116,34 @@ module Atlassian
{ providerMetadata: { product: "GitLab #{Gitlab::VERSION}" } }
end
+ def handle_response(response, name, &block)
+ data = response.parsed_response
+
+ case response.code
+ when 200 then yield data
+ when 400 then { 'errorMessages' => data.map { |e| e['message'] } }
+ when 401 then { 'errorMessages' => ['Invalid JWT'] }
+ when 403 then { 'errorMessages' => ["App does not support #{name}"] }
+ when 413 then { 'errorMessages' => ['Data too large'] + data.map { |e| e['message'] } }
+ when 429 then { 'errorMessages' => ['Rate limit exceeded'] }
+ when 503 then { 'errorMessages' => ['Service unavailable'] }
+ else
+ { 'errorMessages' => ['Unknown error'], 'response' => data }
+ end
+ end
+
+ def errors(data, key)
+ messages = if data[key].present?
+ data[key].flat_map do |rejection|
+ rejection['errors'].map { |e| e['message'] }
+ end
+ else
+ []
+ end
+
+ { 'errorMessages' => messages }
+ end
+
def user_notes_count(merge_requests)
return unless merge_requests