Commit c124eb8e7709f777e7f6e48cba3f74c8e9fdb055
1 parent
82dae706
Exists in
master
and in
29 other branches
organization: register and use members_count to fetch most_popular organizations
(ActionItem3039)
Showing
7 changed files
with
95 additions
and
12 deletions
Show diff stats
app/models/organization.rb
... | ... | @@ -26,11 +26,7 @@ class Organization < Profile |
26 | 26 | |
27 | 27 | has_many :mailings, :class_name => 'OrganizationMailing', :foreign_key => :source_id, :as => 'source' |
28 | 28 | |
29 | - named_scope :more_popular, | |
30 | - :select => "#{Profile.qualified_column_names}, count(resource_id) as total", | |
31 | - :group => Profile.qualified_column_names, | |
32 | - :joins => "LEFT OUTER JOIN role_assignments ON profiles.id = role_assignments.resource_id", | |
33 | - :order => "total DESC" | |
29 | + named_scope :more_popular, :order => 'members_count DESC' | |
34 | 30 | |
35 | 31 | def validation_methodology |
36 | 32 | self.validation_info ? self.validation_info.validation_methodology : nil | ... | ... |
app/models/profile.rb
... | ... | @@ -0,0 +1 @@ |
1 | +require 'noosfero/role_assignment_ext' | ... | ... |
db/migrate/20140313213142_define_initial_value_for_profiles_members_count.rb
0 → 100644
... | ... | @@ -0,0 +1,12 @@ |
1 | +class DefineInitialValueForProfilesMembersCount < ActiveRecord::Migration | |
2 | + def self.up | |
3 | + members_counts = execute("SELECT profiles.id, count(profiles.id) FROM profiles LEFT OUTER JOIN role_assignments ON profiles.id = role_assignments.resource_id WHERE (profiles.type = 'Organization' OR profiles.type = 'Community' OR profiles.type = 'Enterprise') GROUP BY profiles.id;") | |
4 | + members_counts.each do |count| | |
5 | + execute("UPDATE profiles SET members_count=#{count['count'].to_i} WHERE profiles.id=#{count['id']};") | |
6 | + end | |
7 | + end | |
8 | + | |
9 | + def self.down | |
10 | + execute("UPDATE profiles SET members_count=0;") | |
11 | + end | |
12 | +end | ... | ... |
... | ... | @@ -0,0 +1,29 @@ |
1 | +Rails.configuration.to_prepare do | |
2 | + RoleAssignment.module_eval do | |
3 | + extend CacheCounterHelper | |
4 | + | |
5 | + after_create do |role_assignment| | |
6 | + accessor = role_assignment.accessor | |
7 | + resource = role_assignment.resource | |
8 | + if resource.kind_of?(Organization) | |
9 | + #FIXME This will only work as long as the role_assignment associations | |
10 | + #happen only between profiles, due to the polymorphic column type. | |
11 | + if resource.role_assignments.where(:accessor_id => accessor.id).count == 1 | |
12 | + update_cache_counter(:members_count, resource, 1) | |
13 | + end | |
14 | + end | |
15 | + end | |
16 | + | |
17 | + after_destroy do |role_assignment| | |
18 | + accessor = role_assignment.accessor | |
19 | + resource = role_assignment.resource | |
20 | + if resource.kind_of?(Organization) | |
21 | + #FIXME This will only work as long as the role_assignment associations | |
22 | + #happen only between profiles, due to the polymorphic column type. | |
23 | + if resource.role_assignments.where(:accessor_id => accessor.id).count == 0 | |
24 | + update_cache_counter(:members_count, resource, -1) | |
25 | + end | |
26 | + end | |
27 | + end | |
28 | + end | |
29 | +end | ... | ... |
test/unit/organization_test.rb
... | ... | @@ -302,18 +302,17 @@ class OrganizationTest < ActiveSupport::TestCase |
302 | 302 | end |
303 | 303 | |
304 | 304 | should 'find more popular organizations' do |
305 | - Organization.delete_all | |
306 | 305 | o1 = fast_create(Organization) |
307 | 306 | o2 = fast_create(Organization) |
308 | 307 | |
309 | 308 | p1 = fast_create(Person) |
310 | 309 | p2 = fast_create(Person) |
311 | 310 | o1.add_member(p1) |
312 | - assert_equal [o1,o2] , Organization.more_popular | |
311 | + assert_order [o1,o2] , Organization.more_popular | |
313 | 312 | |
314 | 313 | o2.add_member(p1) |
315 | 314 | o2.add_member(p2) |
316 | - assert_equal [o2,o1] , Organization.more_popular | |
315 | + assert_order [o2,o1] , Organization.more_popular | |
317 | 316 | end |
318 | 317 | |
319 | 318 | should 'list organizations that have no members in more popular list' do |
... | ... | @@ -331,6 +330,7 @@ class OrganizationTest < ActiveSupport::TestCase |
331 | 330 | person = fast_create(Person) |
332 | 331 | organization = fast_create(Organization) |
333 | 332 | organization.add_member(person) |
333 | + organization.reload | |
334 | 334 | |
335 | 335 | assert_equal "one member", organization.more_popular_label |
336 | 336 | end |
... | ... | @@ -342,10 +342,12 @@ class OrganizationTest < ActiveSupport::TestCase |
342 | 342 | |
343 | 343 | organization.add_member(person1) |
344 | 344 | organization.add_member(person2) |
345 | + organization.reload | |
345 | 346 | assert_equal "2 members", organization.more_popular_label |
346 | 347 | |
347 | 348 | person3 = fast_create(Person) |
348 | 349 | organization.add_member(person3) |
350 | + organization.reload | |
349 | 351 | assert_equal "3 members", organization.more_popular_label |
350 | 352 | end |
351 | 353 | |
... | ... | @@ -433,5 +435,24 @@ class OrganizationTest < ActiveSupport::TestCase |
433 | 435 | end |
434 | 436 | end |
435 | 437 | |
438 | + should 'increase members_count on new membership' do | |
439 | + member = fast_create(Person) | |
440 | + organization = fast_create(Organization) | |
441 | + assert_difference organization, :members_count, 1 do | |
442 | + organization.add_member(member) | |
443 | + organization.reload | |
444 | + end | |
445 | + end | |
446 | + | |
447 | + should 'decrease members_count on membership removal' do | |
448 | + member = fast_create(Person) | |
449 | + organization = fast_create(Organization) | |
450 | + organization.add_member(member) | |
451 | + organization.reload | |
452 | + assert_difference organization, :members_count, -1 do | |
453 | + organization.remove_member(member) | |
454 | + organization.reload | |
455 | + end | |
456 | + end | |
436 | 457 | |
437 | 458 | end | ... | ... |
... | ... | @@ -0,0 +1,28 @@ |
1 | +require File.dirname(__FILE__) + '/../test_helper' | |
2 | + | |
3 | +class RoleAssignmentExtTest < ActiveSupport::TestCase | |
4 | + should 'increase organization members_count only on the first role_assignment' do | |
5 | + role1 = Role.create!(:name => 'role1') | |
6 | + role2 = Role.create!(:name => 'role2') | |
7 | + member = create_user('person').person | |
8 | + organization = Organization.create!(:name => 'Organization', :identifier => 'organization') | |
9 | + assert_difference organization, :members_count, 1 do | |
10 | + RoleAssignment.create!(:accessor => member, :resource => organization, :role => role1) | |
11 | + RoleAssignment.create!(:accessor => member, :resource => organization, :role => role2) | |
12 | + organization.reload | |
13 | + end | |
14 | + end | |
15 | + | |
16 | + should 'decrease organization members_count only on the last role_assignment' do | |
17 | + role1 = Role.create!(:name => 'role1') | |
18 | + role2 = Role.create!(:name => 'role2') | |
19 | + member = create_user('person').person | |
20 | + organization = Organization.create!(:name => 'Organization', :identifier => 'organization') | |
21 | + RoleAssignment.create!(:accessor => member, :resource => organization, :role => role1) | |
22 | + RoleAssignment.create!(:accessor => member, :resource => organization, :role => role2) | |
23 | + assert_difference organization, :members_count, -1 do | |
24 | + organization.role_assignments.destroy_all | |
25 | + organization.reload | |
26 | + end | |
27 | + end | |
28 | +end | ... | ... |