Feature #23997 » 0001-per-role-visibility-settings-for-project-and-version.patch
app/models/project.rb | ||
---|---|---|
570 | 570 |
end |
571 | 571 |
end |
572 | 572 | |
573 |
def visible_custom_field_values(user = nil) |
|
574 |
user ||= User.current |
|
575 |
custom_field_values.select do |value| |
|
576 |
value.custom_field.visible_by?(project, user) |
|
577 |
end |
|
578 |
end |
|
579 | ||
573 | 580 |
def project |
574 | 581 |
self |
575 | 582 |
end |
app/models/project_custom_field.rb | ||
---|---|---|
19 | 19 |
def type_name |
20 | 20 |
:label_project_plural |
21 | 21 |
end |
22 | ||
23 |
def visible_by?(project, user=User.current) |
|
24 |
super || (roles & user.roles_for_project(project)).present? |
|
25 |
end |
|
26 | ||
27 |
def validate_custom_field |
|
28 |
super |
|
29 |
errors.add(:base, l(:label_role_plural) + ' ' + l('activerecord.errors.messages.blank')) unless visible? || roles.present? |
|
30 |
end |
|
22 | 31 |
end |
app/models/version.rb | ||
---|---|---|
68 | 68 |
'custom_field_values', |
69 | 69 |
'custom_fields' |
70 | 70 | |
71 |
def safe_attributes=(attrs, user = User.current) |
|
72 |
return unless attrs.is_a?(Hash) |
|
73 | ||
74 |
attrs = delete_unsafe_attributes(attrs, user) |
|
75 |
return if attrs.empty? |
|
76 | ||
77 |
if attrs['custom_field_values'].present? |
|
78 |
editable_custom_field_ids = editable_custom_field_values(user).map {|v| v.custom_field_id.to_s} |
|
79 |
attrs['custom_field_values'].reject! {|k, v| !editable_custom_field_ids.include?(k.to_s)} |
|
80 |
end |
|
81 | ||
82 |
if attrs['custom_fields'].present? |
|
83 |
editable_custom_field_ids = editable_custom_field_values(user).map {|v| v.custom_field_id.to_s} |
|
84 |
attrs['custom_fields'].reject! {|c| !editable_custom_field_ids.include?(c['id'].to_s)} |
|
85 |
end |
|
86 | ||
87 |
# mass-assignment security bypass |
|
88 |
assign_attributes attrs, :without_protection => true |
|
89 |
end |
|
90 | ||
91 |
# Returns the custom_field_values that can be edited by the given user |
|
92 |
def editable_custom_field_values(user=nil) |
|
93 |
visible_custom_field_values(user) |
|
94 |
end |
|
95 | ||
71 | 96 |
# Returns true if +user+ or current user is allowed to view the version |
72 | 97 |
def visible?(user=User.current) |
73 | 98 |
user.allowed_to?(:view_issues, self.project) |
74 | 99 |
end |
75 | 100 | |
101 |
def visible_custom_field_values(user = nil) |
|
102 |
user ||= User.current |
|
103 |
custom_field_values.select do |value| |
|
104 |
value.custom_field.visible_by?(project, user) |
|
105 |
end |
|
106 |
end |
|
107 | ||
76 | 108 |
# Version files have same visibility as project files |
77 | 109 |
def attachments_visible?(*args) |
78 | 110 |
project.present? && project.attachments_visible?(*args) |
app/models/version_custom_field.rb | ||
---|---|---|
19 | 19 |
def type_name |
20 | 20 |
:label_version_plural |
21 | 21 |
end |
22 | ||
23 |
def visible_by?(project, user=User.current) |
|
24 |
super || (roles & user.roles_for_project(project)).present? |
|
25 |
end |
|
26 | ||
27 |
def validate_custom_field |
|
28 |
super |
|
29 |
errors.add(:base, l(:label_role_plural) + ' ' + l('activerecord.errors.messages.blank')) unless visible? || roles.present? |
|
30 |
end |
|
22 | 31 |
end |
app/views/custom_fields/_form.html.erb | ||
---|---|---|
32 | 32 |
<% if @custom_field.format.searchable_supported %> |
33 | 33 |
<p><%= f.check_box :searchable %></p> |
34 | 34 |
<% end %> |
35 |
<p> |
|
36 |
<label><%= l(:field_visible) %></label> |
|
37 |
<label class="block"> |
|
38 |
<%= radio_button_tag 'custom_field[visible]', 1, @custom_field.visible?, :id => 'custom_field_visible_on', |
|
39 |
:data => {:disables => '.custom_field_role input'} %> |
|
40 |
<%= l(:label_visibility_public) %> |
|
41 |
</label> |
|
42 |
<label class="block"> |
|
43 |
<%= radio_button_tag 'custom_field[visible]', 0, !@custom_field.visible?, :id => 'custom_field_visible_off', |
|
44 |
:data => {:enables => '.custom_field_role input'} %> |
|
45 |
<%= l(:label_visibility_roles) %>: |
|
46 |
</label> |
|
47 |
<% Role.givable.sorted.each do |role| %> |
|
48 |
<label class="block custom_field_role" style="padding-left:2em;"> |
|
49 |
<%= check_box_tag 'custom_field[role_ids][]', role.id, @custom_field.roles.include?(role), :id => nil %> |
|
50 |
<%= role.name %> |
|
51 |
</label> |
|
52 |
<% end %> |
|
53 |
<%= hidden_field_tag 'custom_field[role_ids][]', '' %> |
|
54 |
</p> |
|
35 |
<%= render :partial => 'visibility_by_role_selector' %> |
|
55 | 36 | |
56 | 37 |
<% when "UserCustomField" %> |
57 | 38 |
<p><%= f.check_box :is_required %></p> |
... | ... | |
61 | 42 | |
62 | 43 |
<% when "ProjectCustomField" %> |
63 | 44 |
<p><%= f.check_box :is_required %></p> |
64 |
<p><%= f.check_box :visible %></p> |
|
65 | 45 |
<% if @custom_field.format.searchable_supported %> |
66 | 46 |
<p><%= f.check_box :searchable %></p> |
67 | 47 |
<% end %> |
68 | 48 |
<p><%= f.check_box :is_filter %></p> |
49 |
<%= render :partial => 'visibility_by_role_selector' %> |
|
69 | 50 | |
70 | 51 |
<% when "VersionCustomField" %> |
71 | 52 |
<p><%= f.check_box :is_required %></p> |
72 | 53 |
<p><%= f.check_box :is_filter %></p> |
54 |
<%= render :partial => 'visibility_by_role_selector' %> |
|
73 | 55 | |
74 | 56 |
<% when "GroupCustomField" %> |
75 | 57 |
<p><%= f.check_box :is_required %></p> |
app/views/custom_fields/_visibility_by_role_selector.html.erb | ||
---|---|---|
1 |
<p> |
|
2 |
<label><%= l(:field_visible) %></label> |
|
3 |
<label class="block"> |
|
4 |
<%= radio_button_tag 'custom_field[visible]', 1, @custom_field.visible?, :id => 'custom_field_visible_on', |
|
5 |
:data => {:disables => '.custom_field_role input'} %> |
|
6 |
<%= l(:label_visibility_public) %> |
|
7 |
</label> |
|
8 |
<label class="block"> |
|
9 |
<%= radio_button_tag 'custom_field[visible]', 0, !@custom_field.visible?, :id => 'custom_field_visible_off', |
|
10 |
:data => {:enables => '.custom_field_role input'} %> |
|
11 |
<%= l(:label_visibility_roles) %>: |
|
12 |
</label> |
|
13 |
<% Role.givable.sorted.each do |role| %> |
|
14 |
<label class="block custom_field_role" style="padding-left:2em;"> |
|
15 |
<%= check_box_tag 'custom_field[role_ids][]', role.id, @custom_field.roles.include?(role), :id => nil %> |
|
16 |
<%= role.name %> |
|
17 |
</label> |
|
18 |
<% end %> |
|
19 |
<%= hidden_field_tag 'custom_field[role_ids][]', '' %> |
|
20 |
</p> |
|
21 |
app/views/projects/_form.html.erb | ||
---|---|---|
26 | 26 | |
27 | 27 |
<%= wikitoolbar_for 'project_description' %> |
28 | 28 | |
29 |
<% @project.custom_field_values.each do |value| %> |
|
29 |
<% @project.visible_custom_field_values.each do |value| %>
|
|
30 | 30 |
<p><%= custom_field_tag_with_label :project, value %></p> |
31 | 31 |
<% end %> |
32 | 32 |
<%= call_hook(:view_projects_form, :project => @project, :form => f) %> |
app/views/versions/_form.html.erb | ||
---|---|---|
11 | 11 |
<p><%= f.date_field :effective_date, :size => 10 %><%= calendar_for('version_effective_date') %></p> |
12 | 12 |
<p><%= f.select :sharing, @version.allowed_sharings.collect {|v| [format_version_sharing(v), v]} %></p> |
13 | 13 | |
14 |
<% @version.custom_field_values.each do |value| %> |
|
14 |
<% @version.visible_custom_field_values.each do |value| %>
|
|
15 | 15 |
<p><%= custom_field_tag_with_label :version, value %></p> |
16 | 16 |
<% end %> |
17 | 17 |
app/views/versions/index.api.rsb | ||
---|---|---|
10 | 10 |
api.due_date version.effective_date |
11 | 11 |
api.sharing version.sharing |
12 | 12 | |
13 |
render_api_custom_values version.custom_field_values, api |
|
13 |
render_api_custom_values version.visible_custom_field_values, api
|
|
14 | 14 | |
15 | 15 |
api.created_on version.created_on |
16 | 16 |
api.updated_on version.updated_on |
app/views/versions/show.api.rsb | ||
---|---|---|
8 | 8 |
api.due_date @version.effective_date |
9 | 9 |
api.sharing @version.sharing |
10 | 10 | |
11 |
render_api_custom_values @version.custom_field_values, api |
|
11 |
render_api_custom_values @version.visible_custom_field_values, api
|
|
12 | 12 | |
13 | 13 |
api.created_on @version.created_on |
14 | 14 |
api.updated_on @version.updated_on |