diff --git a/app/helpers/labels_helper.rb b/app/helpers/labels_helper.rb index 8272c177d59..8036303851b 100644 --- a/app/helpers/labels_helper.rb +++ b/app/helpers/labels_helper.rb @@ -1,6 +1,44 @@ module LabelsHelper include ActionView::Helpers::TagHelper + # Link to a Label + # + # label - Label object to link to + # project - Project object which will be used as the context for the label's + # link. If omitted, defaults to `@project`, or the label's own + # project. + # block - An optional block that will be passed to `link_to`, forming the + # body of the link element. If omitted, defaults to + # `render_colored_label`. + # + # Examples: + # + # # Allow the generated link to use the label's own project + # link_to_label(label) + # + # # Force the generated link to use @project + # @project = Project.first + # link_to_label(label) + # + # # Force the generated link to use a provided project + # link_to_label(label, project: Project.last) + # + # # Customize link body with a block + # link_to_label(label) { "My Custom Label Text" } + # + # Returns a String + def link_to_label(label, project: nil, &block) + project ||= @project || label.project + link = namespace_project_issues_path(project.namespace, project, + label_name: label.name) + + if block_given? + link_to link, &block + else + link_to render_colored_label(label), link + end + end + def project_label_names @project.labels.pluck(:title) end diff --git a/app/views/projects/issues/_discussion.html.haml b/app/views/projects/issues/_discussion.html.haml index 2016f5c709c..48858fa32da 100644 --- a/app/views/projects/issues/_discussion.html.haml +++ b/app/views/projects/issues/_discussion.html.haml @@ -30,5 +30,4 @@ %label Labels .issue-show-labels - @issue.labels.each do |label| - = link_to namespace_project_issues_path(@project.namespace, @project, label_name: label.name) do - = render_colored_label(label) + = link_to_label(label) diff --git a/app/views/projects/issues/_issue.html.haml b/app/views/projects/issues/_issue.html.haml index ef36d1f9547..a4e25e5ce88 100644 --- a/app/views/projects/issues/_issue.html.haml +++ b/app/views/projects/issues/_issue.html.haml @@ -8,8 +8,7 @@ = link_to_gfm issue.title, issue_path(issue), class: "row_title" .issue-labels - issue.labels.each do |label| - = link_to namespace_project_issues_path(issue.project.namespace, issue.project, label_name: label.name) do - = render_colored_label(label) + = link_to_label(label, project: issue.project) .pull-right.light - if issue.closed? %span diff --git a/app/views/projects/labels/_label.html.haml b/app/views/projects/labels/_label.html.haml index 82829452862..c9ac0dbe0c1 100644 --- a/app/views/projects/labels/_label.html.haml +++ b/app/views/projects/labels/_label.html.haml @@ -2,7 +2,7 @@ = render_colored_label(label) .pull-right %strong.append-right-20 - = link_to namespace_project_issues_path(@project.namespace, @project, label_name: label.name) do + = link_to_label(label) do = pluralize label.open_issues_count, 'open issue' - if can? current_user, :admin_label, @project diff --git a/app/views/projects/merge_requests/_discussion.html.haml b/app/views/projects/merge_requests/_discussion.html.haml index 9a2aa9c3de0..eb3dba6858d 100644 --- a/app/views/projects/merge_requests/_discussion.html.haml +++ b/app/views/projects/merge_requests/_discussion.html.haml @@ -27,5 +27,4 @@ %label Labels .merge-request-show-labels - @merge_request.labels.each do |label| - = link_to namespace_project_merge_requests_path(@project.namespace, @project, label_name: label.name) do - = render_colored_label(label) + = link_to_label(label) diff --git a/app/views/projects/merge_requests/_merge_request.html.haml b/app/views/projects/merge_requests/_merge_request.html.haml index 5d5a23b5409..073476b0d27 100644 --- a/app/views/projects/merge_requests/_merge_request.html.haml +++ b/app/views/projects/merge_requests/_merge_request.html.haml @@ -4,8 +4,7 @@ = link_to_gfm merge_request.title, merge_request_path(merge_request), class: "row_title" .merge-request-labels - merge_request.labels.each do |label| - = link_to namespace_project_merge_requests_path(merge_request.project.namespace, merge_request.project, label_name: label.name) do - = render_colored_label(label) + = link_to_label(label, project: merge_request.project) .pull-right.light - if merge_request.merged? %span diff --git a/spec/helpers/labels_helper_spec.rb b/spec/helpers/labels_helper_spec.rb index 0b7e3b1d11f..0c8d06b7059 100644 --- a/spec/helpers/labels_helper_spec.rb +++ b/spec/helpers/labels_helper_spec.rb @@ -1,6 +1,70 @@ require 'spec_helper' describe LabelsHelper do - it { expect(text_color_for_bg('#EEEEEE')).to eq('#333333') } - it { expect(text_color_for_bg('#222E2E')).to eq('#FFFFFF') } + describe 'link_to_label' do + let(:project) { create(:empty_project) } + let(:label) { create(:label, project: project) } + + context 'with @project set' do + before do + @project = project + end + + it 'uses the instance variable' do + expect(label).not_to receive(:project) + link_to_label(label) + end + end + + context 'without @project set' do + it "uses the label's project" do + expect(label).to receive(:project).and_return(project) + link_to_label(label) + end + end + + context 'with a named project argument' do + it 'uses the provided project' do + arg = double('project') + expect(arg).to receive(:namespace).and_return('foo') + expect(arg).to receive(:to_param).and_return('foo') + + link_to_label(label, project: arg) + end + + it 'takes precedence over other types' do + @project = project + expect(@project).not_to receive(:namespace) + expect(label).not_to receive(:project) + + arg = double('project', namespace: 'foo', to_param: 'foo') + link_to_label(label, project: arg) + end + end + + context 'with block' do + it 'passes the block to link_to' do + link = link_to_label(label) { 'Foo' } + expect(link).to match('Foo') + end + end + + context 'without block' do + it 'uses render_colored_label as the link content' do + expect(self).to receive(:render_colored_label). + with(label).and_return('Foo') + expect(link_to_label(label)).to match('Foo') + end + end + end + + describe 'text_color_for_bg' do + it 'uses light text on dark backgrounds' do + expect(text_color_for_bg('#222E2E')).to eq('#FFFFFF') + end + + it 'uses dark text on light backgrounds' do + expect(text_color_for_bg('#EEEEEE')).to eq('#333333') + end + end end