summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorDouglas Barbosa Alexandre <dbalexandre@gmail.com>2016-09-19 16:49:08 -0300
committerDouglas Barbosa Alexandre <dbalexandre@gmail.com>2016-10-19 14:57:15 -0200
commit52e0c3b565b7b177abbf8ea3bc573651060179a2 (patch)
tree1cd659377de0a28c7dc5afee456a1b9bb9849d7b
parentd820c090ec85f8118e4cea75bd63d800e812ea25 (diff)
downloadgitlab-ce-52e0c3b565b7b177abbf8ea3bc573651060179a2.tar.gz
Add CRUD for Group Labels
-rw-r--r--app/assets/javascripts/dispatcher.js.es62
-rw-r--r--app/controllers/groups/labels_controller.rb67
-rw-r--r--app/helpers/labels_helper.rb28
-rw-r--r--app/policies/group_policy.rb1
-rw-r--r--app/views/groups/labels/_form.html.haml33
-rw-r--r--app/views/groups/labels/_label.html.haml53
-rw-r--r--app/views/groups/labels/_label_row.html.haml6
-rw-r--r--app/views/groups/labels/destroy.js.haml2
-rw-r--r--app/views/groups/labels/edit.html.haml8
-rw-r--r--app/views/groups/labels/index.html.haml24
-rw-r--r--app/views/groups/labels/new.html.haml9
-rw-r--r--app/views/layouts/nav/_group.html.haml4
-rw-r--r--config/routes/group.rb6
13 files changed, 238 insertions, 5 deletions
diff --git a/app/assets/javascripts/dispatcher.js.es6 b/app/assets/javascripts/dispatcher.js.es6
index 73691f40c74..afc0d6f8c62 100644
--- a/app/assets/javascripts/dispatcher.js.es6
+++ b/app/assets/javascripts/dispatcher.js.es6
@@ -168,6 +168,8 @@
shortcut_handler = new ShortcutsNavigation();
new ShortcutsBlob(true);
break;
+ case 'groups:labels:new':
+ case 'groups:labels:edit':
case 'projects:labels:new':
case 'projects:labels:edit':
new Labels();
diff --git a/app/controllers/groups/labels_controller.rb b/app/controllers/groups/labels_controller.rb
new file mode 100644
index 00000000000..449298f51a8
--- /dev/null
+++ b/app/controllers/groups/labels_controller.rb
@@ -0,0 +1,67 @@
+class Groups::LabelsController < Groups::ApplicationController
+ include ToggleSubscriptionAction
+
+ before_action :label, only: [:edit, :update, :destroy, :toggle_subscription]
+ before_action :authorize_admin_labels!, only: [:new, :create, :edit, :update, :destroy]
+
+ respond_to :html
+
+ def index
+ @labels = @group.labels.page(params[:page])
+ end
+
+ def new
+ @label = @group.labels.new
+ end
+
+ def create
+ @label = @group.labels.create(label_params)
+
+ if @label.valid?
+ redirect_to group_labels_path(@group)
+ else
+ render :new
+ end
+ end
+
+ def edit
+ end
+
+ def update
+ if @label.update_attributes(label_params)
+ redirect_to group_labels_path(@group)
+ else
+ render :edit
+ end
+ end
+
+ def destroy
+ @label.destroy
+
+ respond_to do |format|
+ format.html do
+ redirect_to group_labels_path(@group), notice: 'Label was removed'
+ end
+ format.js
+ end
+ end
+
+ protected
+
+ def authorize_admin_labels!
+ return render_404 unless can?(current_user, :admin_label, @group)
+ end
+
+ def authorize_read_labels!
+ return render_404 unless can?(current_user, :read_label, @group)
+ end
+
+ def label
+ @label ||= @group.labels.find(params[:id])
+ end
+ alias_method :subscribable_resource, :label
+
+ def label_params
+ params.require(:label).permit(:title, :description, :color)
+ end
+end
diff --git a/app/helpers/labels_helper.rb b/app/helpers/labels_helper.rb
index b9f3d6c75c2..540eb6dd493 100644
--- a/app/helpers/labels_helper.rb
+++ b/app/helpers/labels_helper.rb
@@ -43,11 +43,29 @@ module LabelsHelper
end
end
- def label_filter_path(project, label, type: issue)
- send("namespace_project_#{type.to_s.pluralize}_path",
- project.namespace,
- project,
- label_name: [label.name])
+ def link_to_group_label(label, group: nil, type: :issue, tooltip: true, css_class: nil, &block)
+ group ||= @group || label.group
+ link = label_filter_path(group, label, type: type)
+
+ if block_given?
+ link_to link, class: css_class, &block
+ else
+ link_to render_colored_label(label, tooltip: tooltip), link, class: css_class
+ end
+ end
+
+ def label_filter_path(subject, label, type: issue)
+ case subject
+ when Project
+ send("namespace_project_#{type.to_s.pluralize}_path",
+ subject.namespace,
+ subject,
+ label_name: [label.name])
+ when Group
+ send("#{type.to_s.pluralize}_group_path",
+ subject,
+ label_name: [label.name])
+ end
end
def project_label_names
diff --git a/app/policies/group_policy.rb b/app/policies/group_policy.rb
index 97ff6233968..b65fb68cd88 100644
--- a/app/policies/group_policy.rb
+++ b/app/policies/group_policy.rb
@@ -19,6 +19,7 @@ class GroupPolicy < BasePolicy
if master
can! :create_projects
can! :admin_milestones
+ can! :admin_label
end
# Only group owner and administrators can admin group
diff --git a/app/views/groups/labels/_form.html.haml b/app/views/groups/labels/_form.html.haml
new file mode 100644
index 00000000000..008b5fb9ba1
--- /dev/null
+++ b/app/views/groups/labels/_form.html.haml
@@ -0,0 +1,33 @@
+= form_for @label, as: :label, url: url, html: { class: 'form-horizontal label-form js-quick-submit js-requires-input' } do |f|
+ = form_errors(@label)
+
+ .form-group
+ = f.label :title, class: 'control-label'
+ .col-sm-10
+ = f.text_field :title, class: "form-control", required: true, autofocus: true
+ .form-group
+ = f.label :description, class: 'control-label'
+ .col-sm-10
+ = f.text_field :description, class: "form-control js-quick-submit"
+ .form-group
+ = f.label :color, "Background color", class: 'control-label'
+ .col-sm-10
+ .input-group
+ .input-group-addon.label-color-preview &nbsp;
+ = f.color_field :color, class: "form-control"
+ .help-block
+ Choose any color.
+ %br
+ Or you can choose one of suggested colors below
+
+ .suggest-colors
+ - suggested_colors.each do |color|
+ = link_to '#', style: "background-color: #{color}", data: { color: color } do
+ &nbsp;
+
+ .form-actions
+ - if @label.persisted?
+ = f.submit 'Save changes', class: 'btn btn-save js-save-button'
+ - else
+ = f.submit 'Create Label', class: 'btn btn-create js-save-button'
+ = link_to "Cancel", group_labels_path(@group), class: 'btn btn-cancel'
diff --git a/app/views/groups/labels/_label.html.haml b/app/views/groups/labels/_label.html.haml
new file mode 100644
index 00000000000..b9aab76f057
--- /dev/null
+++ b/app/views/groups/labels/_label.html.haml
@@ -0,0 +1,53 @@
+- label_css_id = dom_id(label)
+- open_issues_count = label.open_issues_count(current_user)
+- open_merge_requests_count = label.open_merge_requests_count
+
+%li{id: label_css_id, data: { id: label.id } }
+ = render 'label_row', label: label
+
+ .visible-xs.visible-sm-inline-block.visible-md-inline-block.dropdown
+ %button.btn.btn-default.label-options-toggle{ data: { toggle: 'dropdown' } }
+ Options
+ %span.caret
+ .dropdown-menu.dropdown-menu-align-right
+ %ul
+ %li
+ = link_to_group_label(label, type: :merge_request) do
+ = pluralize open_merge_requests_count, 'merge request'
+ %li
+ = link_to_group_label(label) do
+ = pluralize open_issues_count, 'open issue'
+ - if current_user
+ %li.label-subscription{ data: { url: toggle_subscription_group_label_path(@group, label) } }
+ %a.js-subscribe-button.label-subscribe-button.subscription-status{ role: "button", href: "#", data: { toggle: "tooltip", status: label_subscription_status(label) } }
+ %span= label_subscription_toggle_button_text(label)
+ - if can? current_user, :admin_label, @group
+ %li
+ = link_to 'Edit', edit_group_label_path(@group, label)
+ %li
+ = link_to 'Delete', group_label_path(@group, label), title: 'Delete', method: :delete, remote: true, data: {confirm: "Remove this label? Are you sure?"}
+
+ .pull-right.hidden-xs.hidden-sm.hidden-md
+ = link_to_group_label(label, type: :merge_request, css_class: 'btn btn-transparent btn-action') do
+ = pluralize open_merge_requests_count, 'merge request'
+ = link_to_group_label(label, css_class: 'btn btn-transparent btn-action') do
+ = pluralize open_issues_count, 'open issue'
+
+ - if current_user
+ .label-subscription.inline{ data: { url: toggle_subscription_group_label_path(@group, label) } }
+ %button.js-subscribe-button.label-subscribe-button.btn.btn-transparent.btn-action.subscription-status{ type: "button", title: label_subscription_toggle_button_text(label), data: { toggle: "tooltip", status: label_subscription_status(label) } }
+ %span.sr-only= label_subscription_toggle_button_text(label)
+ = icon('eye', class: 'label-subscribe-button-icon')
+ = icon('spinner spin', class: 'label-subscribe-button-loading')
+
+ - if can? current_user, :admin_label, @group
+ = link_to edit_group_label_path(@group, label), title: 'Edit', class: 'btn btn-transparent btn-action', data: {toggle: 'tooltip'} do
+ %span.sr-only Edit
+ = icon('pencil-square-o')
+ = link_to group_label_path(@group, label), title: 'Delete', class: 'btn btn-transparent btn-action remove-row', method: :delete, remote: true, data: {confirm: 'Remove this label? Are you sure?', toggle: 'tooltip'} do
+ %span.sr-only Delete
+ = icon('trash-o')
+
+ - if current_user
+ :javascript
+ new Subscription('##{dom_id(label)} .label-subscription');
diff --git a/app/views/groups/labels/_label_row.html.haml b/app/views/groups/labels/_label_row.html.haml
new file mode 100644
index 00000000000..e21fac25b01
--- /dev/null
+++ b/app/views/groups/labels/_label_row.html.haml
@@ -0,0 +1,6 @@
+%span.label-row
+ %span.label-name
+ = link_to_group_label(label, tooltip: false)
+ - if label.description
+ %span.label-description
+ = markdown(label.description, pipeline: :single_line)
diff --git a/app/views/groups/labels/destroy.js.haml b/app/views/groups/labels/destroy.js.haml
new file mode 100644
index 00000000000..3dfbfc77c0d
--- /dev/null
+++ b/app/views/groups/labels/destroy.js.haml
@@ -0,0 +1,2 @@
+- if @group.labels.empty?
+ $('.labels').load(document.URL + ' .nothing-here-block').hide().fadeIn(1000)
diff --git a/app/views/groups/labels/edit.html.haml b/app/views/groups/labels/edit.html.haml
new file mode 100644
index 00000000000..e247393abd5
--- /dev/null
+++ b/app/views/groups/labels/edit.html.haml
@@ -0,0 +1,8 @@
+- page_title 'Edit', @label.name, 'Labels'
+
+%h3.page-title
+ = icon('folder-open')
+ Edit Group Label
+%hr
+
+= render 'form', url: group_label_path(@group, @label)
diff --git a/app/views/groups/labels/index.html.haml b/app/views/groups/labels/index.html.haml
new file mode 100644
index 00000000000..d9f1d350cb3
--- /dev/null
+++ b/app/views/groups/labels/index.html.haml
@@ -0,0 +1,24 @@
+- page_title 'Labels'
+
+.top-area.adjust
+ .nav-text
+ Labels can be applied to issues and merge requests.
+
+ .nav-controls
+ - if can?(current_user, :admin_label, @group)
+ = link_to new_group_label_path(@group), class: "btn btn-new" do
+ New label
+
+.labels
+ - hide = @group.labels.empty? || (params[:page].present? && params[:page] != '1')
+ .group-labels
+ %h5{ class: ('hide' if hide) }
+ = icon('folder-open')
+ Group Labels
+ - if @labels.present?
+ %ul.content-list.manage-labels-list.js-group-labels
+ = render partial: 'label', collection: @labels, as: :label
+ = paginate @labels, theme: 'gitlab'
+ - else
+ .nothing-here-block
+ No labels created yet.
diff --git a/app/views/groups/labels/new.html.haml b/app/views/groups/labels/new.html.haml
new file mode 100644
index 00000000000..01a50607db4
--- /dev/null
+++ b/app/views/groups/labels/new.html.haml
@@ -0,0 +1,9 @@
+- page_title 'New Group Label'
+- header_title group_title(@group, 'Labels', group_labels_path(@group))
+
+%h3.page-title
+ = icon('folder-open')
+ New Group Label
+%hr
+
+= render 'form', url: group_labels_path
diff --git a/app/views/layouts/nav/_group.html.haml b/app/views/layouts/nav/_group.html.haml
index 27ac1760166..f7edb47b666 100644
--- a/app/views/layouts/nav/_group.html.haml
+++ b/app/views/layouts/nav/_group.html.haml
@@ -13,6 +13,10 @@
= link_to activity_group_path(@group), title: 'Activity' do
%span
Activity
+ = nav_link(controller: [:group, :labels]) do
+ = link_to group_labels_path(@group), title: 'Labels' do
+ %span
+ Labels
= nav_link(controller: [:group, :milestones]) do
= link_to group_milestones_path(@group), title: 'Milestones' do
%span
diff --git a/config/routes/group.rb b/config/routes/group.rb
index 06b464d79c8..7bb9aa50875 100644
--- a/config/routes/group.rb
+++ b/config/routes/group.rb
@@ -28,5 +28,11 @@ resources :groups, constraints: { id: /[a-zA-Z.0-9_\-]+(?<!\.atom)/ } do
resource :avatar, only: [:destroy]
resources :milestones, constraints: { id: /[^\/]+/ }, only: [:index, :show, :update, :new, :create]
+
+ resources :labels, except: [:show], constraints: { id: /\d+/ } do
+ member do
+ post :toggle_subscription
+ end
+ end
end
end