merge_request_spec.rb 6.4 KB
Newer Older
D
Dmitriy Zaporozhets 已提交
1 2 3 4
# == Schema Information
#
# Table name: merge_requests
#
D
Dmitriy Zaporozhets 已提交
5 6 7 8 9 10 11
#  id                :integer          not null, primary key
#  target_branch     :string(255)      not null
#  source_branch     :string(255)      not null
#  source_project_id :integer          not null
#  author_id         :integer
#  assignee_id       :integer
#  title             :string(255)
D
Dmitriy Zaporozhets 已提交
12 13
#  created_at        :datetime
#  updated_at        :datetime
D
Dmitriy Zaporozhets 已提交
14 15 16 17 18
#  milestone_id      :integer
#  state             :string(255)
#  merge_status      :string(255)
#  target_project_id :integer          not null
#  iid               :integer
D
Dmitriy Zaporozhets 已提交
19
#  description       :text
D
Dmitriy Zaporozhets 已提交
20
#  position          :integer          default(0)
D
Dmitriy Zaporozhets 已提交
21
#  locked_at         :datetime
S
Stan Hu 已提交
22
#  updated_by_id     :integer
D
Dmitriy Zaporozhets 已提交
23 24
#

D
Dmitriy Zaporozhets 已提交
25 26 27
require 'spec_helper'

describe MergeRequest do
28 29
  subject { create(:merge_request) }

R
Robert Speicher 已提交
30 31 32 33 34 35 36
  describe 'associations' do
    it { is_expected.to belong_to(:target_project).with_foreign_key(:target_project_id).class_name('Project') }
    it { is_expected.to belong_to(:source_project).with_foreign_key(:source_project_id).class_name('Project') }

    it { is_expected.to have_one(:merge_request_diff).dependent(:destroy) }
  end

37 38 39 40 41 42 43 44 45 46 47
  describe 'modules' do
    subject { described_class }

    it { is_expected.to include_module(InternalId) }
    it { is_expected.to include_module(Issuable) }
    it { is_expected.to include_module(Referable) }
    it { is_expected.to include_module(Sortable) }
    it { is_expected.to include_module(Taskable) }
  end

  describe 'validation' do
48 49
    it { is_expected.to validate_presence_of(:target_branch) }
    it { is_expected.to validate_presence_of(:source_branch) }
D
Dmitriy Zaporozhets 已提交
50 51
  end

R
Robert Speicher 已提交
52
  describe 'respond to' do
53 54 55
    it { is_expected.to respond_to(:unchecked?) }
    it { is_expected.to respond_to(:can_be_merged?) }
    it { is_expected.to respond_to(:cannot_be_merged?) }
56
  end
A
Andrey Kumanyaev 已提交
57

58 59 60 61 62 63 64 65 66
  describe '#to_reference' do
    it 'returns a String reference to the object' do
      expect(subject.to_reference).to eq "!#{subject.iid}"
    end

    it 'supports a cross-project reference' do
      cross = double('project')
      expect(subject.to_reference(cross)).to eq "#{subject.source_project.to_reference}!#{subject.iid}"
    end
67
  end
68 69

  describe "#mr_and_commit_notes" do
70
    let!(:merge_request) { create(:merge_request) }
71 72

    before do
73
      allow(merge_request).to receive(:commits) { [merge_request.source_project.repository.commit] }
D
Dmitriy Zaporozhets 已提交
74 75
      create(:note, commit_id: merge_request.commits.first.id, noteable_type: 'Commit', project: merge_request.project)
      create(:note, noteable: merge_request, project: merge_request.project)
76 77 78
    end

    it "should include notes for commits" do
79 80
      expect(merge_request.commits).not_to be_empty
      expect(merge_request.mr_and_commit_notes.count).to eq(2)
81
    end
82 83 84 85 86 87

    it "should include notes for commits from target project as well" do
      create(:note, commit_id: merge_request.commits.first.id, noteable_type: 'Commit', project: merge_request.target_project)
      expect(merge_request.commits).not_to be_empty
      expect(merge_request.mr_and_commit_notes.count).to eq(3)
    end
88
  end
89 90 91

  describe '#is_being_reassigned?' do
    it 'returns true if the merge_request assignee has changed' do
92
      subject.assignee = create(:user)
93
      expect(subject.is_being_reassigned?).to be_truthy
94 95
    end
    it 'returns false if the merge request assignee has not changed' do
96
      expect(subject.is_being_reassigned?).to be_falsey
97 98
    end
  end
I
Izaak Alpert 已提交
99 100 101

  describe '#for_fork?' do
    it 'returns true if the merge request is for a fork' do
D
Dmitriy Zaporozhets 已提交
102 103
      subject.source_project = create(:project, namespace: create(:group))
      subject.target_project = create(:project, namespace: create(:group))
I
Izaak Alpert 已提交
104

105
      expect(subject.for_fork?).to be_truthy
I
Izaak Alpert 已提交
106
    end
D
Dmitriy Zaporozhets 已提交
107

I
Izaak Alpert 已提交
108
    it 'returns false if is not for a fork' do
109
      expect(subject.for_fork?).to be_falsey
I
Izaak Alpert 已提交
110 111 112
    end
  end

113 114 115
  describe 'detection of issues to be closed' do
    let(:issue0) { create :issue, project: subject.project }
    let(:issue1) { create :issue, project: subject.project }
S
skv 已提交
116 117 118
    let(:commit0) { double('commit0', closes_issues: [issue0]) }
    let(:commit1) { double('commit1', closes_issues: [issue0]) }
    let(:commit2) { double('commit2', closes_issues: [issue1]) }
119 120

    before do
121
      allow(subject).to receive(:commits).and_return([commit0, commit1, commit2])
122 123 124
    end

    it 'accesses the set of issues that will be closed on acceptance' do
125 126
      allow(subject.project).to receive(:default_branch).
        and_return(subject.target_branch)
127

128
      expect(subject.closes_issues).to eq([issue0, issue1].sort_by(&:id))
129 130 131
    end

    it 'only lists issues as to be closed if it targets the default branch' do
132
      allow(subject.project).to receive(:default_branch).and_return('master')
133 134
      subject.target_branch = 'something-else'

135
      expect(subject.closes_issues).to be_empty
136
    end
137 138 139

    it 'detects issues mentioned in the description' do
      issue2 = create(:issue, project: subject.project)
140
      subject.description = "Closes #{issue2.to_reference}"
141 142
      allow(subject.project).to receive(:default_branch).
        and_return(subject.target_branch)
143

144
      expect(subject.closes_issues).to include(issue2)
145
    end
146 147
  end

148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173
  describe "#work_in_progress?" do
    it "detects the 'WIP ' prefix" do
      subject.title = "WIP #{subject.title}"
      expect(subject).to be_work_in_progress
    end

    it "detects the 'WIP: ' prefix" do
      subject.title = "WIP: #{subject.title}"
      expect(subject).to be_work_in_progress
    end

    it "detects the '[WIP] ' prefix" do
      subject.title = "[WIP] #{subject.title}"
      expect(subject).to be_work_in_progress
    end

    it "doesn't detect WIP for words starting with WIP" do
      subject.title = "Wipwap #{subject.title}"
      expect(subject).not_to be_work_in_progress
    end

    it "doesn't detect WIP by default" do
      expect(subject).not_to be_work_in_progress
    end
  end

174 175 176 177 178 179 180 181 182 183 184
  describe "#hook_attrs" do
    it "has all the required keys" do
      attrs = subject.hook_attrs
      attrs = attrs.to_h
      expect(attrs).to include(:source)
      expect(attrs).to include(:target)
      expect(attrs).to include(:last_commit)
      expect(attrs).to include(:work_in_progress)
    end
  end

185
  it_behaves_like 'an editable mentionable' do
186
    subject { create(:merge_request) }
187

188 189
    let(:backref_text) { "merge request #{subject.to_reference}" }
    let(:set_mentionable_text) { ->(txt){ subject.description = txt } }
190
  end
V
Vinnie Okada 已提交
191 192

  it_behaves_like 'a Taskable' do
193
    subject { create :merge_request, :simple }
V
Vinnie Okada 已提交
194
  end
D
Dmitriy Zaporozhets 已提交
195
end