Commit d399e1ae authored by Felipe Artur's avatar Felipe Artur

Allow enabling and disabling commit and MR events for JIRA

parent 88479f7f
......@@ -17,6 +17,8 @@ module ServicesHelper
"Event will be triggered when a build status changes"
when "wiki_page"
"Event will be triggered when a wiki page is created/updated"
when "commit"
"Event will be triggered when a commit is created/updated"
end
end
......
# == Schema Information
#
# Table name: services
#
# id :integer not null, primary key
# type :string(255)
# title :string(255)
# project_id :integer
# created_at :datetime
# updated_at :datetime
# active :boolean default(FALSE), not null
# properties :text
# template :boolean default(FALSE)
# push_events :boolean default(TRUE)
# issues_events :boolean default(TRUE)
# merge_requests_events :boolean default(TRUE)
# tag_push_events :boolean default(TRUE)
# note_events :boolean default(TRUE), not null
# build_events :boolean default(FALSE), not null
#
class JiraService < IssueTrackerService
include Gitlab::Routing.url_helpers
......@@ -30,6 +9,10 @@ class JiraService < IssueTrackerService
before_update :reset_password
def supported_events
%w(commit merge_request)
end
# {PROJECT-KEY}-{NUMBER} Examples: JIRA-1, PROJECT-1
def reference_pattern
@reference_pattern ||= %r{(?<issue>\b([A-Z][A-Z0-9_]+-)\d+)}
......@@ -137,12 +120,16 @@ class JiraService < IssueTrackerService
end
def create_cross_reference_note(mentioned, noteable, author)
unless can_cross_reference?(noteable)
return "Events for #{noteable.model_name.plural.humanize(capitalize: false)} are disabled."
end
jira_issue = jira_request { client.Issue.find(mentioned.id) }
return false unless jira_issue.present?
return unless jira_issue.present?
project = self.project
noteable_name = noteable.class.name.underscore.downcase
noteable_name = noteable.model_name.singular
noteable_id = if noteable.is_a?(Commit)
noteable.id
else
......@@ -193,8 +180,16 @@ class JiraService < IssueTrackerService
private
def can_cross_reference?(noteable)
case noteable
when Commit then commit_events
when MergeRequest then merge_requests_events
else true
end
end
def close_issue(entity, issue)
return if issue.nil? || issue.resolution.present?
return if issue.nil? || issue.resolution.present? || !jira_issue_transition_id.present?
commit_id = if entity.is_a?(Commit)
entity.id
......
......@@ -8,6 +8,7 @@ class Service < ActiveRecord::Base
default_value_for :push_events, true
default_value_for :issues_events, true
default_value_for :confidential_issues_events, true
default_value_for :commit_events, true
default_value_for :merge_requests_events, true
default_value_for :tag_push_events, true
default_value_for :note_events, true
......
---
title: Allow enabling and disabling commit and MR events for JIRA
merge_request:
author:
class AddCommitEventsToServices < ActiveRecord::Migration
include Gitlab::Database::MigrationHelpers
DOWNTIME = false
disable_ddl_transaction!
def up
add_column_with_default(:services, :commit_events, :boolean, default: true, allow_null: false)
end
def down
remove_column(:services, :commit_events)
end
end
......@@ -11,7 +11,7 @@
#
# It's strongly recommended that you check this file into your version control system.
ActiveRecord::Schema.define(version: 20161117114805) do
ActiveRecord::Schema.define(version: 20161118183841) do
# These are extensions that must be enabled in order to support this database
enable_extension "plpgsql"
......@@ -1023,6 +1023,7 @@ ActiveRecord::Schema.define(version: 20161117114805) do
t.boolean "wiki_page_events", default: true
t.boolean "pipeline_events", default: false, null: false
t.boolean "confidential_issues_events", default: true, null: false
t.boolean "commit_events", default: true, null: false
end
add_index "services", ["project_id"], name: "index_services_on_project_id", using: :btree
......
......@@ -258,6 +258,7 @@ Service:
- template
- push_events
- issues_events
- commit_events
- merge_requests_events
- tag_push_events
- note_events
......@@ -339,4 +340,4 @@ LabelPriority:
- label_id
- priority
- created_at
- updated_at
\ No newline at end of file
- updated_at
......@@ -83,7 +83,8 @@ describe JiraService, models: true do
url: 'http://jira.example.com',
username: 'gitlab_jira_username',
password: 'gitlab_jira_password',
project_key: 'GitLabProject'
project_key: 'GitLabProject',
jira_issue_transition_id: "custom-id"
)
# These stubs are needed to test JiraService#close_issue.
......@@ -177,11 +178,10 @@ describe JiraService, models: true do
end
it "calls the api with jira_issue_transition_id" do
@jira_service.jira_issue_transition_id = 'this-is-a-custom-id'
@jira_service.execute(merge_request, ExternalIssue.new("JIRA-123", project))
expect(WebMock).to have_requested(:post, @transitions_url).with(
body: /this-is-a-custom-id/
body: /custom-id/
).once
end
......
......@@ -59,10 +59,14 @@ describe MergeRequests::MergeService, services: true do
include JiraServiceHelper
let(:jira_tracker) { project.create_jira_service }
let(:jira_issue) { ExternalIssue.new('JIRA-123', project) }
let(:commit) { double('commit', safe_message: "Fixes #{jira_issue.to_reference}") }
before do
project.update_attributes!(has_external_issue_tracker: true)
jira_service_settings
stub_jira_urls(jira_issue.id)
allow(merge_request).to receive(:commits).and_return([commit])
end
it 'closes issues on JIRA issue tracker' do
......@@ -76,6 +80,18 @@ describe MergeRequests::MergeService, services: true do
service.execute(merge_request)
end
context "when jira_issue_transition_id is not present" do
before { allow_any_instance_of(JIRA::Resource::Issue).to receive(:resolution).and_return(nil) }
it "does not close issue" do
allow(jira_tracker).to receive_messages(jira_issue_transition_id: nil)
expect_any_instance_of(JiraService).not_to receive(:transition_issue)
service.execute(merge_request)
end
end
context "wrong issue markdown" do
it 'does not close issues on JIRA issue tracker' do
jira_issue = ExternalIssue.new('#JIRA-123', project)
......
......@@ -536,7 +536,7 @@ describe SystemNoteService, services: true do
let(:project) { create(:jira_project) }
let(:author) { create(:user) }
let(:issue) { create(:issue, project: project) }
let(:mergereq) { create(:merge_request, :simple, target_project: project, source_project: project) }
let(:merge_request) { create(:merge_request, :simple, target_project: project, source_project: project) }
let(:jira_issue) { ExternalIssue.new("JIRA-1", project)}
let(:jira_tracker) { project.jira_service }
let(:commit) { project.commit }
......@@ -545,7 +545,31 @@ describe SystemNoteService, services: true do
before { stub_jira_urls(jira_issue.id) }
context 'in issue' do
noteable_types = ["merge_requests", "commit"]
noteable_types.each do |type|
context "when noteable is a #{type}" do
it "blocks cross reference when #{type.underscore}_events is false" do
jira_tracker.update("#{type}_events" => false)
noteable = type == "commit" ? commit : merge_request
result = described_class.cross_reference(jira_issue, noteable, author)
expect(result).to eq("Events for #{noteable.class.to_s.underscore.humanize.pluralize.downcase} are disabled.")
end
it "blocks cross reference when #{type.underscore}_events is true" do
jira_tracker.update("#{type}_events" => true)
noteable = type == "commit" ? commit : merge_request
result = described_class.cross_reference(jira_issue, noteable, author)
expect(result).to eq(success_message)
end
end
end
context 'in JIRA issue tracker' do
before { jira_service_settings }
describe "new reference" do
......
......@@ -6,7 +6,8 @@ module JiraServiceHelper
properties = {
title: "JIRA tracker",
url: JIRA_URL,
project_key: "JIRA"
project_key: "JIRA",
jira_issue_transition_id: '1'
}
jira_tracker.update_attributes(properties: properties, active: true)
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment