mirror of
https://github.com/meineerde/redmine.git
synced 2026-02-03 23:53:23 +00:00
Adds a single controller for users and groups memberships and support for adding multiple projects at once (#11702).
git-svn-id: http://svn.redmine.org/redmine/trunk@13498 e93f8b46-1217-0410-a6f0-8f06a7374b81
This commit is contained in:
parent
ca5946d82e
commit
c2e73160da
@ -23,6 +23,7 @@ class GroupsController < ApplicationController
|
||||
accept_api_auth :index, :show, :create, :update, :destroy, :add_users, :remove_user
|
||||
|
||||
helper :custom_fields
|
||||
helper :principal_memberships
|
||||
|
||||
def index
|
||||
respond_to do |format|
|
||||
@ -119,23 +120,6 @@ class GroupsController < ApplicationController
|
||||
end
|
||||
end
|
||||
|
||||
def edit_membership
|
||||
@membership = Member.edit_membership(params[:membership_id], params[:membership], @group)
|
||||
@membership.save if request.post?
|
||||
respond_to do |format|
|
||||
format.html { redirect_to edit_group_path(@group, :tab => 'memberships') }
|
||||
format.js
|
||||
end
|
||||
end
|
||||
|
||||
def destroy_membership
|
||||
Member.find(params[:membership_id]).destroy if request.post?
|
||||
respond_to do |format|
|
||||
format.html { redirect_to edit_group_path(@group, :tab => 'memberships') }
|
||||
format.js
|
||||
end
|
||||
end
|
||||
|
||||
private
|
||||
|
||||
def find_group
|
||||
|
||||
80
app/controllers/principal_memberships_controller.rb
Normal file
80
app/controllers/principal_memberships_controller.rb
Normal file
@ -0,0 +1,80 @@
|
||||
# Redmine - project management software
|
||||
# Copyright (C) 2006-2014 Jean-Philippe Lang
|
||||
#
|
||||
# This program is free software; you can redistribute it and/or
|
||||
# modify it under the terms of the GNU General Public License
|
||||
# as published by the Free Software Foundation; either version 2
|
||||
# of the License, or (at your option) any later version.
|
||||
#
|
||||
# This program is distributed in the hope that it will be useful,
|
||||
# but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
# GNU General Public License for more details.
|
||||
#
|
||||
# You should have received a copy of the GNU General Public License
|
||||
# along with this program; if not, write to the Free Software
|
||||
# Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
|
||||
|
||||
class PrincipalMembershipsController < ApplicationController
|
||||
layout 'admin'
|
||||
|
||||
before_filter :require_admin
|
||||
before_filter :find_principal, :only => [:new, :create]
|
||||
before_filter :find_membership, :only => [:update, :destroy]
|
||||
|
||||
def new
|
||||
@projects = Project.active.all
|
||||
@roles = Role.find_all_givable
|
||||
respond_to do |format|
|
||||
format.html
|
||||
format.js
|
||||
end
|
||||
end
|
||||
|
||||
def create
|
||||
@members = Member.create_principal_memberships(@principal, params[:membership])
|
||||
respond_to do |format|
|
||||
format.html { redirect_to_principal @principal }
|
||||
format.js
|
||||
end
|
||||
end
|
||||
|
||||
def update
|
||||
@membership.attributes = params[:membership]
|
||||
@membership.save
|
||||
respond_to do |format|
|
||||
format.html { redirect_to_principal @principal }
|
||||
format.js
|
||||
end
|
||||
end
|
||||
|
||||
def destroy
|
||||
if @membership.deletable?
|
||||
@membership.destroy
|
||||
end
|
||||
respond_to do |format|
|
||||
format.html { redirect_to_principal @principal }
|
||||
format.js
|
||||
end
|
||||
end
|
||||
|
||||
private
|
||||
|
||||
def find_principal
|
||||
principal_id = params[:user_id] || params[:group_id]
|
||||
@principal = Principal.find(principal_id)
|
||||
rescue ActiveRecord::RecordNotFound
|
||||
render_404
|
||||
end
|
||||
|
||||
def find_membership
|
||||
@membership = Member.find(params[:id])
|
||||
@principal = @membership.principal
|
||||
rescue ActiveRecord::RecordNotFound
|
||||
render_404
|
||||
end
|
||||
|
||||
def redirect_to_principal(principal)
|
||||
redirect_to edit_polymorphic_path(principal, :tab => 'memberships')
|
||||
end
|
||||
end
|
||||
@ -19,13 +19,14 @@ class UsersController < ApplicationController
|
||||
layout 'admin'
|
||||
|
||||
before_filter :require_admin, :except => :show
|
||||
before_filter :find_user, :only => [:show, :edit, :update, :destroy, :edit_membership, :destroy_membership]
|
||||
before_filter :find_user, :only => [:show, :edit, :update, :destroy]
|
||||
accept_api_auth :index, :show, :create, :update, :destroy
|
||||
|
||||
helper :sort
|
||||
include SortHelper
|
||||
helper :custom_fields
|
||||
include CustomFieldsHelper
|
||||
helper :principal_memberships
|
||||
|
||||
def index
|
||||
sort_init 'login', 'asc'
|
||||
@ -173,26 +174,6 @@ class UsersController < ApplicationController
|
||||
end
|
||||
end
|
||||
|
||||
def edit_membership
|
||||
@membership = Member.edit_membership(params[:membership_id], params[:membership], @user)
|
||||
@membership.save
|
||||
respond_to do |format|
|
||||
format.html { redirect_to edit_user_path(@user, :tab => 'memberships') }
|
||||
format.js
|
||||
end
|
||||
end
|
||||
|
||||
def destroy_membership
|
||||
@membership = Member.find(params[:membership_id])
|
||||
if @membership.deletable?
|
||||
@membership.destroy
|
||||
end
|
||||
respond_to do |format|
|
||||
format.html { redirect_to edit_user_path(@user, :tab => 'memberships') }
|
||||
format.js
|
||||
end
|
||||
end
|
||||
|
||||
private
|
||||
|
||||
def find_user
|
||||
|
||||
@ -252,7 +252,7 @@ module ApplicationHelper
|
||||
# Renders a tree of projects as a nested set of unordered lists
|
||||
# The given collection may be a subset of the whole project tree
|
||||
# (eg. some intermediate nodes are private and can not be seen)
|
||||
def render_project_nested_lists(projects)
|
||||
def render_project_nested_lists(projects, &block)
|
||||
s = ''
|
||||
if projects.any?
|
||||
ancestors = []
|
||||
@ -272,7 +272,7 @@ module ApplicationHelper
|
||||
end
|
||||
classes = (ancestors.empty? ? 'root' : 'child')
|
||||
s << "<li class='#{classes}'><div class='#{classes}'>"
|
||||
s << h(block_given? ? yield(project) : project.name)
|
||||
s << h(block_given? ? capture(project, &block) : project.name)
|
||||
s << "</div>\n"
|
||||
ancestors << project
|
||||
end
|
||||
|
||||
56
app/helpers/principal_memberships_helper.rb
Normal file
56
app/helpers/principal_memberships_helper.rb
Normal file
@ -0,0 +1,56 @@
|
||||
# encoding: utf-8
|
||||
#
|
||||
# Redmine - project management software
|
||||
# Copyright (C) 2006-2014 Jean-Philippe Lang
|
||||
#
|
||||
# This program is free software; you can redistribute it and/or
|
||||
# modify it under the terms of the GNU General Public License
|
||||
# as published by the Free Software Foundation; either version 2
|
||||
# of the License, or (at your option) any later version.
|
||||
#
|
||||
# This program is distributed in the hope that it will be useful,
|
||||
# but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
# GNU General Public License for more details.
|
||||
#
|
||||
# You should have received a copy of the GNU General Public License
|
||||
# along with this program; if not, write to the Free Software
|
||||
# Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
|
||||
|
||||
module PrincipalMembershipsHelper
|
||||
def render_principal_memberships(principal)
|
||||
render :partial => 'principal_memberships/index', :locals => {:principal => principal}
|
||||
end
|
||||
|
||||
def call_table_header_hook(principal)
|
||||
if principal.is_a?(Group)
|
||||
call_hook :view_groups_memberships_table_header, :group => principal
|
||||
else
|
||||
call_hook :view_users_memberships_table_header, :user => principal
|
||||
end
|
||||
end
|
||||
|
||||
def call_table_row_hook(principal, membership)
|
||||
if principal.is_a?(Group)
|
||||
call_hook :view_groups_memberships_table_row, :group => principal, :membership => membership
|
||||
else
|
||||
call_hook :view_users_memberships_table_row, :user => principal, :membership => membership
|
||||
end
|
||||
end
|
||||
|
||||
def new_principal_membership_path(principal, *args)
|
||||
if principal.is_a?(Group)
|
||||
new_group_membership_path(principal, *args)
|
||||
else
|
||||
new_user_membership_path(principal, *args)
|
||||
end
|
||||
end
|
||||
|
||||
def principal_membership_path(principal, membership, *args)
|
||||
if principal.is_a?(Group)
|
||||
group_membership_path(principal, membership, *args)
|
||||
else
|
||||
user_membership_path(principal, membership, *args)
|
||||
end
|
||||
end
|
||||
end
|
||||
@ -47,7 +47,7 @@ class Member < ActiveRecord::Base
|
||||
|
||||
new_role_ids = ids - role_ids
|
||||
# Add new roles
|
||||
new_role_ids.each {|id| member_roles << MemberRole.new(:role_id => id) }
|
||||
new_role_ids.each {|id| member_roles << MemberRole.new(:role_id => id, :member => self) }
|
||||
# Remove roles (Rails' #role_ids= will not trigger MemberRole#on_destroy)
|
||||
member_roles_to_destroy = member_roles.select {|mr| !ids.include?(mr.role_id)}
|
||||
if member_roles_to_destroy.any?
|
||||
@ -102,11 +102,23 @@ class Member < ActiveRecord::Base
|
||||
end
|
||||
end
|
||||
|
||||
# Find or initialize a Member with an id, attributes, and for a Principal
|
||||
def self.edit_membership(id, new_attributes, principal=nil)
|
||||
@membership = id.present? ? Member.find(id) : Member.new(:principal => principal)
|
||||
@membership.attributes = new_attributes
|
||||
@membership
|
||||
# Creates memberships for principal with the attributes
|
||||
# * project_ids : one or more project ids
|
||||
# * role_ids : ids of the roles to give to each membership
|
||||
#
|
||||
# Example:
|
||||
# Member.create_principal_memberships(user, :project_ids => [2, 5], :role_ids => [1, 3]
|
||||
def self.create_principal_memberships(principal, attributes)
|
||||
members = []
|
||||
if attributes
|
||||
project_ids = Array.wrap(attributes[:project_ids] || attributes[:project_id])
|
||||
role_ids = attributes[:role_ids]
|
||||
project_ids.each do |project_id|
|
||||
members << Member.new(:principal => principal, :role_ids => role_ids, :project_id => project_id)
|
||||
end
|
||||
principal.members << members
|
||||
end
|
||||
members
|
||||
end
|
||||
|
||||
# Finds or initilizes a Member for the given project and principal
|
||||
|
||||
@ -84,6 +84,11 @@ class Principal < ActiveRecord::Base
|
||||
to_s
|
||||
end
|
||||
|
||||
# Return true if the principal is a member of project
|
||||
def member_of?(project)
|
||||
projects.to_a.include?(project)
|
||||
end
|
||||
|
||||
def <=>(principal)
|
||||
if principal.nil?
|
||||
-1
|
||||
|
||||
@ -498,11 +498,6 @@ class User < Principal
|
||||
end
|
||||
end
|
||||
|
||||
# Return true if the user is a member of project
|
||||
def member_of?(project)
|
||||
projects.to_a.include?(project)
|
||||
end
|
||||
|
||||
# Returns a hash of user's projects grouped by roles
|
||||
def projects_by_role
|
||||
return @projects_by_role if @projects_by_role
|
||||
|
||||
@ -1,65 +1 @@
|
||||
<% roles = Role.find_all_givable %>
|
||||
<% projects = Project.active.to_a %>
|
||||
|
||||
<div class="splitcontentleft">
|
||||
<% if @group.memberships.any? %>
|
||||
<table class="list memberships">
|
||||
<thead><tr>
|
||||
<th><%= l(:label_project) %></th>
|
||||
<th><%= l(:label_role_plural) %></th>
|
||||
<th style="width:15%"></th>
|
||||
</tr></thead>
|
||||
<tbody>
|
||||
<% @group.memberships.each do |membership| %>
|
||||
<% next if membership.new_record? %>
|
||||
<tr id="member-<%= membership.id %>" class="<%= cycle 'odd', 'even' %> class">
|
||||
<td class="project"><%= link_to_project membership.project %></td>
|
||||
<td class="roles">
|
||||
<span id="member-<%= membership.id %>-roles"><%=h membership.roles.sort.collect(&:to_s).join(', ') %></span>
|
||||
<%= form_for(:membership, :remote => true,
|
||||
:url => { :action => 'edit_membership', :id => @group, :membership_id => membership },
|
||||
:html => { :id => "member-#{membership.id}-roles-form", :style => 'display:none;'}) do %>
|
||||
<p><% roles.each do |role| %>
|
||||
<label><%= check_box_tag 'membership[role_ids][]', role.id, membership.roles.include?(role), :id => nil %> <%=h role %></label><br />
|
||||
<% end %></p>
|
||||
<p><%= submit_tag l(:button_change) %>
|
||||
<%= link_to_function(
|
||||
l(:button_cancel),
|
||||
"$('#member-#{membership.id}-roles').show(); $('#member-#{membership.id}-roles-form').hide(); return false;"
|
||||
) %></p>
|
||||
<% end %>
|
||||
</td>
|
||||
<td class="buttons">
|
||||
<%= link_to_function(
|
||||
l(:button_edit),
|
||||
"$('#member-#{membership.id}-roles').hide(); $('#member-#{membership.id}-roles-form').show(); return false;",
|
||||
:class => 'icon icon-edit'
|
||||
) %>
|
||||
<%= delete_link({:controller => 'groups', :action => 'destroy_membership', :id => @group, :membership_id => membership},
|
||||
:remote => true,
|
||||
:method => :post) %>
|
||||
</td>
|
||||
</tr>
|
||||
<% end; reset_cycle %>
|
||||
</tbody>
|
||||
</table>
|
||||
<% else %>
|
||||
<p class="nodata"><%= l(:label_no_data) %></p>
|
||||
<% end %>
|
||||
</div>
|
||||
|
||||
<div class="splitcontentright">
|
||||
<% if projects.any? %>
|
||||
<fieldset><legend><%=l(:label_project_new)%></legend>
|
||||
<%= form_for(:membership, :remote => true, :url => { :action => 'edit_membership', :id => @group }) do %>
|
||||
<%= label_tag "membership_project_id", l(:description_choose_project), :class => "hidden-for-sighted" %>
|
||||
<%= select_tag 'membership[project_id]', options_for_membership_project_select(@group, projects) %>
|
||||
<p><%= l(:label_role_plural) %>:
|
||||
<% roles.each do |role| %>
|
||||
<label><%= check_box_tag 'membership[role_ids][]', role.id, false, :id => nil %> <%=h role %></label>
|
||||
<% end %></p>
|
||||
<p><%= submit_tag l(:button_add) %></p>
|
||||
<% end %>
|
||||
</fieldset>
|
||||
<% end %>
|
||||
</div>
|
||||
<%= render_principal_memberships @group %>
|
||||
|
||||
52
app/views/principal_memberships/_index.html.erb
Normal file
52
app/views/principal_memberships/_index.html.erb
Normal file
@ -0,0 +1,52 @@
|
||||
<% roles = Role.find_all_givable %>
|
||||
|
||||
<p><%= link_to l(:label_add_projects), new_principal_membership_path(principal), :remote => true, :class => "icon icon-add" %></p>
|
||||
|
||||
<% if principal.memberships.any? %>
|
||||
<table class="list memberships">
|
||||
<thead><tr>
|
||||
<th><%= l(:label_project) %></th>
|
||||
<th><%= l(:label_role_plural) %></th>
|
||||
<th style="width:15%"></th>
|
||||
<%= call_table_header_hook principal %>
|
||||
</tr></thead>
|
||||
<tbody>
|
||||
<% principal.memberships.preload(:member_roles => :role).each do |membership| %>
|
||||
<% next if membership.new_record? %>
|
||||
<tr id="member-<%= membership.id %>" class="<%= cycle 'odd', 'even' %> class">
|
||||
<td class="project name">
|
||||
<%= link_to_project membership.project %>
|
||||
</td>
|
||||
<td class="roles">
|
||||
<span id="member-<%= membership.id %>-roles"><%=h membership.roles.sort.collect(&:to_s).join(', ') %></span>
|
||||
<%= form_for(:membership, :remote => true,
|
||||
:url => principal_membership_path(principal, membership), :method => :put,
|
||||
:html => {:id => "member-#{membership.id}-roles-form",
|
||||
:style => 'display:none;'}) do %>
|
||||
<p><% roles.each do |role| %>
|
||||
<label><%= check_box_tag 'membership[role_ids][]', role.id, membership.roles.include?(role),
|
||||
:disabled => membership.member_roles.detect {|mr| mr.role_id == role.id && !mr.inherited_from.nil?},
|
||||
:id => nil %> <%=h role %></label><br />
|
||||
<% end %></p>
|
||||
<%= hidden_field_tag 'membership[role_ids][]', '' %>
|
||||
<p><%= submit_tag l(:button_change) %>
|
||||
<%= link_to_function l(:button_cancel),
|
||||
"$('#member-#{membership.id}-roles').show(); $('#member-#{membership.id}-roles-form').hide(); return false;"
|
||||
%></p>
|
||||
<% end %>
|
||||
</td>
|
||||
<td class="buttons">
|
||||
<%= link_to_function l(:button_edit),
|
||||
"$('#member-#{membership.id}-roles').hide(); $('#member-#{membership.id}-roles-form').show(); return false;",
|
||||
:class => 'icon icon-edit'
|
||||
%>
|
||||
<%= delete_link principal_membership_path(principal, membership), :remote => true if membership.deletable? %>
|
||||
</td>
|
||||
<%= call_table_row_hook principal, membership %>
|
||||
</tr>
|
||||
<% end; reset_cycle %>
|
||||
</tbody>
|
||||
</table>
|
||||
<% else %>
|
||||
<p class="nodata"><%= l(:label_no_data) %></p>
|
||||
<% end %>
|
||||
22
app/views/principal_memberships/_new_form.html.erb
Normal file
22
app/views/principal_memberships/_new_form.html.erb
Normal file
@ -0,0 +1,22 @@
|
||||
<fieldset class="box">
|
||||
<legend><%= l(:label_project_plural) %></legend>
|
||||
<div style="max-height:300px; overflow:auto;">
|
||||
<div class="projects-selection">
|
||||
<%= render_project_nested_lists(@projects) do |p| %>
|
||||
<label>
|
||||
<%= check_box_tag('membership[project_ids][]', p.id, false, :id => nil, :disabled => @principal.member_of?(p)) %> <%= p %>
|
||||
</label>
|
||||
<% end %>
|
||||
</div>
|
||||
</div>
|
||||
</fieldset>
|
||||
|
||||
<fieldset class="box">
|
||||
<legend><%= l(:label_role_plural) %></legend>
|
||||
<% @roles.each do |role| %>
|
||||
<label class="inline">
|
||||
<%= check_box_tag 'membership[role_ids][]', role.id, false, :id => nil %>
|
||||
<%=h role %>
|
||||
</label>
|
||||
<% end %>
|
||||
</fieldset>
|
||||
9
app/views/principal_memberships/_new_modal.html.erb
Normal file
9
app/views/principal_memberships/_new_modal.html.erb
Normal file
@ -0,0 +1,9 @@
|
||||
<h3 class="title"><%= l(:label_add_projects) %></h3>
|
||||
|
||||
<%= form_for :membership, :remote => true, :url => user_memberships_path(@principal), :method => :post do |f| %>
|
||||
<%= render :partial => 'new_form' %>
|
||||
<p class="buttons">
|
||||
<%= submit_tag l(:button_add), :name => nil %>
|
||||
<%= submit_tag l(:button_cancel), :name => nil, :onclick => "hideModal(this);", :type => 'button' %>
|
||||
</p>
|
||||
<% end %>
|
||||
12
app/views/principal_memberships/create.js.erb
Normal file
12
app/views/principal_memberships/create.js.erb
Normal file
@ -0,0 +1,12 @@
|
||||
$('#tab-content-memberships').html('<%= escape_javascript(render :partial => 'principal_memberships/index', :locals => {:principal => @principal}) %>');
|
||||
hideOnLoad();
|
||||
|
||||
<% if @members.present? && @members.all? {|m| m.persisted? } %>
|
||||
hideModal();
|
||||
<% @members.each do |member| %>
|
||||
$("#member-<%= member.id %>").effect("highlight");
|
||||
<% end %>
|
||||
<% elsif @members.present? %>
|
||||
<% errors = @members.collect {|m| m.errors.full_messages}.flatten.uniq.join(', ') %>
|
||||
alert('<%= raw(escape_javascript(l(:notice_failed_to_save_members, :errors => errors))) %>');
|
||||
<% end %>
|
||||
1
app/views/principal_memberships/destroy.js.erb
Normal file
1
app/views/principal_memberships/destroy.js.erb
Normal file
@ -0,0 +1 @@
|
||||
$('#tab-content-memberships').html('<%= escape_javascript(render :partial => 'principal_memberships/index', :locals => {:principal => @principal}) %>');
|
||||
6
app/views/principal_memberships/new.html.erb
Normal file
6
app/views/principal_memberships/new.html.erb
Normal file
@ -0,0 +1,6 @@
|
||||
<h2><%= l(:label_add_projects) %></h2>
|
||||
|
||||
<%= form_for :membership, :url => user_memberships_path(@principal), :method => :post do |f| %>
|
||||
<%= render :partial => 'new_form' %>
|
||||
<p><%= submit_tag l(:button_add), :name => nil %></p>
|
||||
<% end %>
|
||||
13
app/views/principal_memberships/new.js.erb
Normal file
13
app/views/principal_memberships/new.js.erb
Normal file
@ -0,0 +1,13 @@
|
||||
$('#ajax-modal').html('<%= escape_javascript(render :partial => 'principal_memberships/new_modal') %>');
|
||||
showModal('ajax-modal', '700px');
|
||||
|
||||
$('.projects-selection').on('click', 'input[type=checkbox]', function(e){
|
||||
if (!$(this).is(':checked')) {
|
||||
if ($(this).closest('li').find('ul input[type=checkbox]:not(:checked)').length > 0) {
|
||||
$(this).closest('li').find('ul input[type=checkbox]:not(:checked)').attr('checked', 'checked');
|
||||
e.preventDefault();
|
||||
} else {
|
||||
$(this).closest('li').find('ul input[type=checkbox]:checked').removeAttr('checked');
|
||||
}
|
||||
}
|
||||
});
|
||||
6
app/views/principal_memberships/update.js.erb
Normal file
6
app/views/principal_memberships/update.js.erb
Normal file
@ -0,0 +1,6 @@
|
||||
<% if @membership.valid? %>
|
||||
$('#tab-content-memberships').html('<%= escape_javascript(render :partial => 'principal_memberships/index', :locals => {:principal => @principal}) %>');
|
||||
$("#member-<%= @membership.id %>").effect("highlight");
|
||||
<% else %>
|
||||
alert('<%= raw(escape_javascript(l(:notice_failed_to_save_members, :errors => @membership.errors.full_messages.join(', ')))) %>');
|
||||
<% end %>
|
||||
@ -1,68 +1 @@
|
||||
<% roles = Role.find_all_givable %>
|
||||
<% projects = Project.active.to_a %>
|
||||
|
||||
<div class="splitcontentleft">
|
||||
<% if @user.memberships.any? %>
|
||||
<table class="list memberships">
|
||||
<thead><tr>
|
||||
<th><%= l(:label_project) %></th>
|
||||
<th><%= l(:label_role_plural) %></th>
|
||||
<th style="width:15%"></th>
|
||||
<%= call_hook(:view_users_memberships_table_header, :user => @user )%>
|
||||
</tr></thead>
|
||||
<tbody>
|
||||
<% @user.memberships.each do |membership| %>
|
||||
<% next if membership.new_record? %>
|
||||
<tr id="member-<%= membership.id %>" class="<%= cycle 'odd', 'even' %> class">
|
||||
<td class="project">
|
||||
<%= link_to_project membership.project %>
|
||||
</td>
|
||||
<td class="roles">
|
||||
<span id="member-<%= membership.id %>-roles"><%=h membership.roles.sort.collect(&:to_s).join(', ') %></span>
|
||||
<%= form_for(:membership, :remote => true,
|
||||
:url => user_membership_path(@user, membership), :method => :put,
|
||||
:html => {:id => "member-#{membership.id}-roles-form",
|
||||
:style => 'display:none;'}) do %>
|
||||
<p><% roles.each do |role| %>
|
||||
<label><%= check_box_tag 'membership[role_ids][]', role.id, membership.roles.include?(role),
|
||||
:disabled => membership.member_roles.detect {|mr| mr.role_id == role.id && !mr.inherited_from.nil?},
|
||||
:id => nil %> <%=h role %></label><br />
|
||||
<% end %></p>
|
||||
<%= hidden_field_tag 'membership[role_ids][]', '' %>
|
||||
<p><%= submit_tag l(:button_change) %>
|
||||
<%= link_to_function l(:button_cancel),
|
||||
"$('#member-#{membership.id}-roles').show(); $('#member-#{membership.id}-roles-form').hide(); return false;"
|
||||
%></p>
|
||||
<% end %>
|
||||
</td>
|
||||
<td class="buttons">
|
||||
<%= link_to_function l(:button_edit),
|
||||
"$('#member-#{membership.id}-roles').hide(); $('#member-#{membership.id}-roles-form').show(); return false;",
|
||||
:class => 'icon icon-edit'
|
||||
%>
|
||||
<%= delete_link user_membership_path(@user, membership), :remote => true if membership.deletable? %>
|
||||
</td>
|
||||
<%= call_hook(:view_users_memberships_table_row, :user => @user, :membership => membership, :roles => roles, :projects => projects )%>
|
||||
</tr>
|
||||
<% end; reset_cycle %>
|
||||
</tbody>
|
||||
</table>
|
||||
<% else %>
|
||||
<p class="nodata"><%= l(:label_no_data) %></p>
|
||||
<% end %>
|
||||
</div>
|
||||
|
||||
<div class="splitcontentright">
|
||||
<% if projects.any? %>
|
||||
<fieldset><legend><%=l(:label_project_new)%></legend>
|
||||
<%= form_for(:membership, :remote => true, :url => user_memberships_path(@user)) do %>
|
||||
<%= select_tag 'membership[project_id]', options_for_membership_project_select(@user, projects) %>
|
||||
<p><%= l(:label_role_plural) %>:
|
||||
<% roles.each do |role| %>
|
||||
<label><%= check_box_tag 'membership[role_ids][]', role.id, false, :id => nil %> <%=h role %></label>
|
||||
<% end %></p>
|
||||
<p><%= submit_tag l(:button_add) %></p>
|
||||
<% end %>
|
||||
</fieldset>
|
||||
<% end %>
|
||||
</div>
|
||||
<%= render_principal_memberships @user %>
|
||||
|
||||
@ -918,6 +918,7 @@ en:
|
||||
label_check_for_updates: Check for updates
|
||||
label_latest_compatible_version: Latest compatible version
|
||||
label_unknown_plugin: Unknown plugin
|
||||
label_add_projects: Add projects
|
||||
|
||||
button_login: Login
|
||||
button_submit: Submit
|
||||
|
||||
@ -938,6 +938,7 @@ fr:
|
||||
label_check_for_updates: Vérifier les mises à jour
|
||||
label_latest_compatible_version: Dernière version compatible
|
||||
label_unknown_plugin: Plugin inconnu
|
||||
label_add_projects: Ajouter des projets
|
||||
|
||||
button_login: Connexion
|
||||
button_submit: Soumettre
|
||||
|
||||
@ -73,10 +73,9 @@ Rails.application.routes.draw do
|
||||
match 'my/remove_block', :controller => 'my', :action => 'remove_block', :via => :post
|
||||
match 'my/order_blocks', :controller => 'my', :action => 'order_blocks', :via => :post
|
||||
|
||||
resources :users
|
||||
match 'users/:id/memberships/:membership_id', :to => 'users#edit_membership', :via => [:put, :patch], :as => 'user_membership'
|
||||
match 'users/:id/memberships/:membership_id', :to => 'users#destroy_membership', :via => :delete
|
||||
match 'users/:id/memberships', :to => 'users#edit_membership', :via => :post, :as => 'user_memberships'
|
||||
resources :users do
|
||||
resources :memberships, :controller => 'principal_memberships'
|
||||
end
|
||||
|
||||
post 'watchers/watch', :to => 'watchers#watch', :as => 'watch'
|
||||
delete 'watchers/watch', :to => 'watchers#unwatch'
|
||||
@ -270,6 +269,7 @@ Rails.application.routes.draw do
|
||||
resources :attachments, :only => [:show, :destroy]
|
||||
|
||||
resources :groups do
|
||||
resources :memberships, :controller => 'principal_memberships'
|
||||
member do
|
||||
get 'autocomplete_for_user'
|
||||
end
|
||||
@ -277,8 +277,6 @@ Rails.application.routes.draw do
|
||||
|
||||
match 'groups/:id/users', :controller => 'groups', :action => 'add_users', :id => /\d+/, :via => :post, :as => 'group_users'
|
||||
match 'groups/:id/users/:user_id', :controller => 'groups', :action => 'remove_user', :id => /\d+/, :via => :delete, :as => 'group_user'
|
||||
match 'groups/destroy_membership/:id', :controller => 'groups', :action => 'destroy_membership', :id => /\d+/, :via => :post
|
||||
match 'groups/edit_membership/:id', :controller => 'groups', :action => 'edit_membership', :id => /\d+/, :via => :post
|
||||
|
||||
resources :trackers, :except => :show do
|
||||
collection do
|
||||
|
||||
@ -626,6 +626,19 @@ input.autocomplete.ajax-loading {
|
||||
|
||||
.role-visibility {padding-left:2em;}
|
||||
|
||||
.projects-selection {
|
||||
column-count: auto;
|
||||
column-width: 200px;
|
||||
-webkit-column-count: auto;
|
||||
-webkit-column-width: 200px;
|
||||
-webkit-column-gap : 0.5rem;
|
||||
-webkit-column-rule: 1px solid #ccc;
|
||||
-moz-column-count: auto;
|
||||
-moz-column-width: 200px;
|
||||
-moz-column-gap : 0.5rem;
|
||||
-moz-column-rule: 1px solid #ccc;
|
||||
}
|
||||
|
||||
/***** Flash & error messages ****/
|
||||
#errorExplanation, div.flash, .nodata, .warning, .conflict {
|
||||
padding: 4px 4px 4px 30px;
|
||||
|
||||
@ -144,62 +144,6 @@ class GroupsControllerTest < ActionController::TestCase
|
||||
end
|
||||
end
|
||||
|
||||
def test_new_membership
|
||||
assert_difference 'Group.find(10).members.count' do
|
||||
post :edit_membership, :id => 10, :membership => { :project_id => 2, :role_ids => ['1', '2']}
|
||||
end
|
||||
end
|
||||
|
||||
def test_xhr_new_membership
|
||||
assert_difference 'Group.find(10).members.count' do
|
||||
xhr :post, :edit_membership, :id => 10, :membership => { :project_id => 2, :role_ids => ['1', '2']}
|
||||
assert_response :success
|
||||
assert_template 'edit_membership'
|
||||
assert_equal 'text/javascript', response.content_type
|
||||
end
|
||||
assert_match /OnlineStore/, response.body
|
||||
end
|
||||
|
||||
def test_xhr_new_membership_with_failure
|
||||
assert_no_difference 'Group.find(10).members.count' do
|
||||
xhr :post, :edit_membership, :id => 10, :membership => { :project_id => 999, :role_ids => ['1', '2']}
|
||||
assert_response :success
|
||||
assert_template 'edit_membership'
|
||||
assert_equal 'text/javascript', response.content_type
|
||||
end
|
||||
assert_match /alert/, response.body, "Alert message not sent"
|
||||
end
|
||||
|
||||
def test_edit_membership
|
||||
assert_no_difference 'Group.find(10).members.count' do
|
||||
post :edit_membership, :id => 10, :membership_id => 6, :membership => { :role_ids => ['1', '3']}
|
||||
end
|
||||
end
|
||||
|
||||
def test_xhr_edit_membership
|
||||
assert_no_difference 'Group.find(10).members.count' do
|
||||
xhr :post, :edit_membership, :id => 10, :membership_id => 6, :membership => { :role_ids => ['1', '3']}
|
||||
assert_response :success
|
||||
assert_template 'edit_membership'
|
||||
assert_equal 'text/javascript', response.content_type
|
||||
end
|
||||
end
|
||||
|
||||
def test_destroy_membership
|
||||
assert_difference 'Group.find(10).members.count', -1 do
|
||||
post :destroy_membership, :id => 10, :membership_id => 6
|
||||
end
|
||||
end
|
||||
|
||||
def test_xhr_destroy_membership
|
||||
assert_difference 'Group.find(10).members.count', -1 do
|
||||
xhr :post, :destroy_membership, :id => 10, :membership_id => 6
|
||||
assert_response :success
|
||||
assert_template 'destroy_membership'
|
||||
assert_equal 'text/javascript', response.content_type
|
||||
end
|
||||
end
|
||||
|
||||
def test_autocomplete_for_user
|
||||
xhr :get, :autocomplete_for_user, :id => 10, :q => 'smi', :format => 'js'
|
||||
assert_response :success
|
||||
|
||||
209
test/functional/principal_memberships_controller_test.rb
Normal file
209
test/functional/principal_memberships_controller_test.rb
Normal file
@ -0,0 +1,209 @@
|
||||
# Redmine - project management software
|
||||
# Copyright (C) 2006-2014 Jean-Philippe Lang
|
||||
#
|
||||
# This program is free software; you can redistribute it and/or
|
||||
# modify it under the terms of the GNU General Public License
|
||||
# as published by the Free Software Foundation; either version 2
|
||||
# of the License, or (at your option) any later version.
|
||||
#
|
||||
# This program is distributed in the hope that it will be useful,
|
||||
# but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
# GNU General Public License for more details.
|
||||
#
|
||||
# You should have received a copy of the GNU General Public License
|
||||
# along with this program; if not, write to the Free Software
|
||||
# Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
|
||||
|
||||
require File.expand_path('../../test_helper', __FILE__)
|
||||
|
||||
class PrincipalMembershipsControllerTest < ActionController::TestCase
|
||||
fixtures :projects, :users, :members, :member_roles, :roles, :groups_users
|
||||
|
||||
def setup
|
||||
@request.session[:user_id] = 1
|
||||
end
|
||||
|
||||
def test_new_user_membership
|
||||
get :new, :user_id => 7
|
||||
assert_response :success
|
||||
assert_select 'label', :text => 'eCookbook' do
|
||||
assert_select 'input[name=?][value=1]:not([disabled])', 'membership[project_ids][]'
|
||||
end
|
||||
end
|
||||
|
||||
def test_new_user_membership_should_disable_user_projects
|
||||
Member.create!(:user_id => 7, :project_id => 1, :role_ids => [1])
|
||||
|
||||
get :new, :user_id => 7
|
||||
assert_response :success
|
||||
assert_select 'label', :text => 'eCookbook' do
|
||||
assert_select 'input[name=?][value=1][disabled=disabled]', 'membership[project_ids][]'
|
||||
end
|
||||
end
|
||||
|
||||
def test_xhr_new_user_membership
|
||||
xhr :get, :new, :user_id => 7
|
||||
assert_response :success
|
||||
assert_equal 'text/javascript', response.content_type
|
||||
end
|
||||
|
||||
def test_create_user_membership
|
||||
assert_difference 'Member.count' do
|
||||
post :create, :user_id => 7, :membership => {:project_ids => [3], :role_ids => [2]}
|
||||
end
|
||||
assert_redirected_to '/users/7/edit?tab=memberships'
|
||||
member = Member.order('id DESC').first
|
||||
assert_equal User.find(7), member.principal
|
||||
assert_equal [2], member.role_ids
|
||||
assert_equal 3, member.project_id
|
||||
end
|
||||
|
||||
def test_create_user_membership_with_multiple_roles
|
||||
assert_difference 'Member.count' do
|
||||
post :create, :user_id => 7, :membership => {:project_ids => [3], :role_ids => [2, 3]}
|
||||
end
|
||||
member = Member.order('id DESC').first
|
||||
assert_equal User.find(7), member.principal
|
||||
assert_equal [2, 3], member.role_ids.sort
|
||||
assert_equal 3, member.project_id
|
||||
end
|
||||
|
||||
def test_create_user_membership_with_multiple_projects_and_roles
|
||||
assert_difference 'Member.count', 2 do
|
||||
post :create, :user_id => 7, :membership => {:project_ids => [1, 3], :role_ids => [2, 3]}
|
||||
end
|
||||
members = Member.order('id DESC').limit(2).sort_by(&:project_id)
|
||||
assert_equal 1, members[0].project_id
|
||||
assert_equal 3, members[1].project_id
|
||||
members.each do |member|
|
||||
assert_equal User.find(7), member.principal
|
||||
assert_equal [2, 3], member.role_ids.sort
|
||||
end
|
||||
end
|
||||
|
||||
def test_xhr_create_user_membership
|
||||
assert_difference 'Member.count' do
|
||||
xhr :post, :create, :user_id => 7, :membership => {:project_ids => [3], :role_ids => [2]}, :format => 'js'
|
||||
assert_response :success
|
||||
assert_template 'create'
|
||||
assert_equal 'text/javascript', response.content_type
|
||||
end
|
||||
member = Member.order('id DESC').first
|
||||
assert_equal User.find(7), member.principal
|
||||
assert_equal [2], member.role_ids
|
||||
assert_equal 3, member.project_id
|
||||
assert_include 'tab-content-memberships', response.body
|
||||
end
|
||||
|
||||
def test_xhr_create_user_membership_with_failure
|
||||
assert_no_difference 'Member.count' do
|
||||
xhr :post, :create, :user_id => 7, :membership => {:project_ids => [3]}, :format => 'js'
|
||||
assert_response :success
|
||||
assert_template 'create'
|
||||
assert_equal 'text/javascript', response.content_type
|
||||
end
|
||||
assert_include 'alert', response.body, "Alert message not sent"
|
||||
assert_include 'Role can\\\'t be empty', response.body, "Error message not sent"
|
||||
end
|
||||
|
||||
def test_update_user_membership
|
||||
assert_no_difference 'Member.count' do
|
||||
put :update, :user_id => 2, :id => 1, :membership => {:role_ids => [2]}
|
||||
assert_redirected_to '/users/2/edit?tab=memberships'
|
||||
end
|
||||
assert_equal [2], Member.find(1).role_ids
|
||||
end
|
||||
|
||||
def test_xhr_update_user_membership
|
||||
assert_no_difference 'Member.count' do
|
||||
xhr :put, :update, :user_id => 2, :id => 1, :membership => {:role_ids => [2]}, :format => 'js'
|
||||
assert_response :success
|
||||
assert_template 'update'
|
||||
assert_equal 'text/javascript', response.content_type
|
||||
end
|
||||
assert_equal [2], Member.find(1).role_ids
|
||||
assert_include 'tab-content-memberships', response.body
|
||||
end
|
||||
|
||||
def test_destroy_user_membership
|
||||
assert_difference 'Member.count', -1 do
|
||||
delete :destroy, :user_id => 2, :id => 1
|
||||
end
|
||||
assert_redirected_to '/users/2/edit?tab=memberships'
|
||||
assert_nil Member.find_by_id(1)
|
||||
end
|
||||
|
||||
def test_xhr_destroy_user_membership_js_format
|
||||
assert_difference 'Member.count', -1 do
|
||||
xhr :delete, :destroy, :user_id => 2, :id => 1
|
||||
assert_response :success
|
||||
assert_template 'destroy'
|
||||
assert_equal 'text/javascript', response.content_type
|
||||
end
|
||||
assert_nil Member.find_by_id(1)
|
||||
assert_include 'tab-content-memberships', response.body
|
||||
end
|
||||
|
||||
def test_xhr_new_group_membership
|
||||
xhr :get, :new, :group_id => 10
|
||||
assert_response :success
|
||||
assert_equal 'text/javascript', response.content_type
|
||||
end
|
||||
|
||||
def test_create_group_membership
|
||||
assert_difference 'Group.find(10).members.count' do
|
||||
post :create, :group_id => 10, :membership => {:project_ids => [2], :role_ids => ['1', '2']}
|
||||
end
|
||||
end
|
||||
|
||||
def test_xhr_create_group_membership
|
||||
assert_difference 'Group.find(10).members.count' do
|
||||
xhr :post, :create, :group_id => 10, :membership => {:project_ids => [2], :role_ids => ['1', '2']}
|
||||
assert_response :success
|
||||
assert_template 'create'
|
||||
assert_equal 'text/javascript', response.content_type
|
||||
end
|
||||
assert_match /OnlineStore/, response.body
|
||||
end
|
||||
|
||||
def test_xhr_create_group_membership_with_failure
|
||||
assert_no_difference 'Group.find(10).members.count' do
|
||||
xhr :post, :create, :group_id => 10, :membership => {:project_ids => [999], :role_ids => ['1', '2']}
|
||||
assert_response :success
|
||||
assert_template 'create'
|
||||
assert_equal 'text/javascript', response.content_type
|
||||
end
|
||||
assert_match /alert/, response.body, "Alert message not sent"
|
||||
end
|
||||
|
||||
def test_update_group_membership
|
||||
assert_no_difference 'Group.find(10).members.count' do
|
||||
put :update, :group_id => 10, :id => 6, :membership => {:role_ids => ['1', '3']}
|
||||
end
|
||||
end
|
||||
|
||||
def test_xhr_update_group_membership
|
||||
assert_no_difference 'Group.find(10).members.count' do
|
||||
xhr :post, :update, :group_id => 10, :id => 6, :membership => {:role_ids => ['1', '3']}
|
||||
assert_response :success
|
||||
assert_template 'update'
|
||||
assert_equal 'text/javascript', response.content_type
|
||||
end
|
||||
end
|
||||
|
||||
def test_destroy_group_membership
|
||||
assert_difference 'Group.find(10).members.count', -1 do
|
||||
delete :destroy, :group_id => 10, :id => 6
|
||||
end
|
||||
end
|
||||
|
||||
def test_xhr_destroy_group_membership
|
||||
assert_difference 'Group.find(10).members.count', -1 do
|
||||
xhr :delete, :destroy, :group_id => 10, :id => 6
|
||||
assert_response :success
|
||||
assert_template 'destroy'
|
||||
assert_equal 'text/javascript', response.content_type
|
||||
end
|
||||
end
|
||||
end
|
||||
@ -424,78 +424,4 @@ class UsersControllerTest < ActionController::TestCase
|
||||
end
|
||||
assert_redirected_to '/users?name=foo'
|
||||
end
|
||||
|
||||
def test_create_membership
|
||||
assert_difference 'Member.count' do
|
||||
post :edit_membership, :id => 7, :membership => { :project_id => 3, :role_ids => [2]}
|
||||
end
|
||||
assert_redirected_to :action => 'edit', :id => '7', :tab => 'memberships'
|
||||
member = Member.order('id DESC').first
|
||||
assert_equal User.find(7), member.principal
|
||||
assert_equal [2], member.role_ids
|
||||
assert_equal 3, member.project_id
|
||||
end
|
||||
|
||||
def test_create_membership_js_format
|
||||
assert_difference 'Member.count' do
|
||||
post :edit_membership, :id => 7, :membership => {:project_id => 3, :role_ids => [2]}, :format => 'js'
|
||||
assert_response :success
|
||||
assert_template 'edit_membership'
|
||||
assert_equal 'text/javascript', response.content_type
|
||||
end
|
||||
member = Member.order('id DESC').first
|
||||
assert_equal User.find(7), member.principal
|
||||
assert_equal [2], member.role_ids
|
||||
assert_equal 3, member.project_id
|
||||
assert_include 'tab-content-memberships', response.body
|
||||
end
|
||||
|
||||
def test_create_membership_js_format_with_failure
|
||||
assert_no_difference 'Member.count' do
|
||||
post :edit_membership, :id => 7, :membership => {:project_id => 3}, :format => 'js'
|
||||
assert_response :success
|
||||
assert_template 'edit_membership'
|
||||
assert_equal 'text/javascript', response.content_type
|
||||
end
|
||||
assert_include 'alert', response.body, "Alert message not sent"
|
||||
assert_include 'Role can\\\'t be empty', response.body, "Error message not sent"
|
||||
end
|
||||
|
||||
def test_update_membership
|
||||
assert_no_difference 'Member.count' do
|
||||
put :edit_membership, :id => 2, :membership_id => 1, :membership => { :role_ids => [2]}
|
||||
assert_redirected_to :action => 'edit', :id => '2', :tab => 'memberships'
|
||||
end
|
||||
assert_equal [2], Member.find(1).role_ids
|
||||
end
|
||||
|
||||
def test_update_membership_js_format
|
||||
assert_no_difference 'Member.count' do
|
||||
put :edit_membership, :id => 2, :membership_id => 1, :membership => {:role_ids => [2]}, :format => 'js'
|
||||
assert_response :success
|
||||
assert_template 'edit_membership'
|
||||
assert_equal 'text/javascript', response.content_type
|
||||
end
|
||||
assert_equal [2], Member.find(1).role_ids
|
||||
assert_include 'tab-content-memberships', response.body
|
||||
end
|
||||
|
||||
def test_destroy_membership
|
||||
assert_difference 'Member.count', -1 do
|
||||
delete :destroy_membership, :id => 2, :membership_id => 1
|
||||
end
|
||||
assert_redirected_to :action => 'edit', :id => '2', :tab => 'memberships'
|
||||
assert_nil Member.find_by_id(1)
|
||||
end
|
||||
|
||||
def test_destroy_membership_js_format
|
||||
assert_difference 'Member.count', -1 do
|
||||
delete :destroy_membership, :id => 2, :membership_id => 1, :format => 'js'
|
||||
assert_response :success
|
||||
assert_template 'destroy_membership'
|
||||
assert_equal 'text/javascript', response.content_type
|
||||
end
|
||||
assert_nil Member.find_by_id(1)
|
||||
assert_include 'tab-content-memberships', response.body
|
||||
end
|
||||
end
|
||||
|
||||
@ -94,13 +94,5 @@ class RoutingGroupsTest < ActionDispatch::IntegrationTest
|
||||
{ :method => 'delete', :path => "/groups/567/users/12.xml" },
|
||||
{ :controller => 'groups', :action => 'remove_user', :id => '567', :user_id => '12', :format => 'xml' }
|
||||
)
|
||||
assert_routing(
|
||||
{ :method => 'post', :path => "/groups/destroy_membership/567" },
|
||||
{ :controller => 'groups', :action => 'destroy_membership', :id => '567' }
|
||||
)
|
||||
assert_routing(
|
||||
{ :method => 'post', :path => "/groups/edit_membership/567" },
|
||||
{ :controller => 'groups', :action => 'edit_membership', :id => '567' }
|
||||
)
|
||||
end
|
||||
end
|
||||
|
||||
56
test/integration/routing/principal_memberships_test.rb
Normal file
56
test/integration/routing/principal_memberships_test.rb
Normal file
@ -0,0 +1,56 @@
|
||||
# Redmine - project management software
|
||||
# Copyright (C) 2006-2014 Jean-Philippe Lang
|
||||
#
|
||||
# This program is free software; you can redistribute it and/or
|
||||
# modify it under the terms of the GNU General Public License
|
||||
# as published by the Free Software Foundation; either version 2
|
||||
# of the License, or (at your option) any later version.
|
||||
#
|
||||
# This program is distributed in the hope that it will be useful,
|
||||
# but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
# GNU General Public License for more details.
|
||||
#
|
||||
# You should have received a copy of the GNU General Public License
|
||||
# along with this program; if not, write to the Free Software
|
||||
# Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
|
||||
|
||||
require File.expand_path('../../../test_helper', __FILE__)
|
||||
|
||||
class RoutingPrincipalMembershipsTest < ActionDispatch::IntegrationTest
|
||||
def test_user_memberships
|
||||
assert_routing(
|
||||
{ :method => 'post', :path => "/users/123/memberships" },
|
||||
{ :controller => 'principal_memberships', :action => 'create',
|
||||
:user_id => '123' }
|
||||
)
|
||||
assert_routing(
|
||||
{ :method => 'put', :path => "/users/123/memberships/55" },
|
||||
{ :controller => 'principal_memberships', :action => 'update',
|
||||
:user_id => '123', :id => '55' }
|
||||
)
|
||||
assert_routing(
|
||||
{ :method => 'delete', :path => "/users/123/memberships/55" },
|
||||
{ :controller => 'principal_memberships', :action => 'destroy',
|
||||
:user_id => '123', :id => '55' }
|
||||
)
|
||||
end
|
||||
|
||||
def test_group_memberships
|
||||
assert_routing(
|
||||
{ :method => 'post', :path => "/groups/123/memberships" },
|
||||
{ :controller => 'principal_memberships', :action => 'create',
|
||||
:group_id => '123' }
|
||||
)
|
||||
assert_routing(
|
||||
{ :method => 'put', :path => "/groups/123/memberships/55" },
|
||||
{ :controller => 'principal_memberships', :action => 'update',
|
||||
:group_id => '123', :id => '55' }
|
||||
)
|
||||
assert_routing(
|
||||
{ :method => 'delete', :path => "/groups/123/memberships/55" },
|
||||
{ :controller => 'principal_memberships', :action => 'destroy',
|
||||
:group_id => '123', :id => '55' }
|
||||
)
|
||||
end
|
||||
end
|
||||
@ -79,20 +79,5 @@ class RoutingUsersTest < ActionDispatch::IntegrationTest
|
||||
{ :controller => 'users', :action => 'destroy', :id => '44',
|
||||
:format => 'xml' }
|
||||
)
|
||||
assert_routing(
|
||||
{ :method => 'post', :path => "/users/123/memberships" },
|
||||
{ :controller => 'users', :action => 'edit_membership',
|
||||
:id => '123' }
|
||||
)
|
||||
assert_routing(
|
||||
{ :method => 'put', :path => "/users/123/memberships/55" },
|
||||
{ :controller => 'users', :action => 'edit_membership',
|
||||
:id => '123', :membership_id => '55' }
|
||||
)
|
||||
assert_routing(
|
||||
{ :method => 'delete', :path => "/users/123/memberships/55" },
|
||||
{ :controller => 'users', :action => 'destroy_membership',
|
||||
:id => '123', :membership_id => '55' }
|
||||
)
|
||||
end
|
||||
end
|
||||
|
||||
Loading…
x
Reference in New Issue
Block a user