Commit c1ac4ddd6f278ed6a281cfb70e460b1dd77f07ef
1 parent
710e0abb
Exists in
master
and in
28 other branches
ActionItem253: remaking the search controller half-made
git-svn-id: https://svn.colivre.coop.br/svn/noosfero/trunk@1701 3f533792-8f58-4932-b0fe-aaf55b0a4547
Showing
10 changed files
with
326 additions
and
17 deletions
Show diff stats
app/controllers/public/account_controller.rb
... | ... | @@ -122,7 +122,7 @@ class AccountController < PublicController |
122 | 122 | protected |
123 | 123 | |
124 | 124 | def go_to_user_initial_page |
125 | - redirect_back_or_default(:controller => "content_viewer", :profile => current_user.login, :action => 'view_page', :page => []) | |
125 | + redirect_back_or_default(:controller => "profile_editor", :profile => current_user.login, :action => 'index') | |
126 | 126 | end |
127 | 127 | |
128 | 128 | end | ... | ... |
app/controllers/public/search_controller.rb
... | ... | @@ -15,14 +15,12 @@ class SearchController < ApplicationController |
15 | 15 | @search_in = SEARCH_IN |
16 | 16 | end |
17 | 17 | |
18 | - def search(finder, query) | |
19 | - finder.find_by_contents(query).sort_by do |hit| | |
20 | - -(relevance_for(hit)) | |
21 | - end | |
22 | - end | |
23 | - | |
24 | 18 | def prepare_filter |
25 | - @finder = @category || @environment | |
19 | + if @category | |
20 | + @finder = CategoryFinder.new(@category) | |
21 | + else | |
22 | + @finder = EnvironmentFinder.new(@environment) | |
23 | + end | |
26 | 24 | end |
27 | 25 | |
28 | 26 | def check_search_whole_site |
... | ... | @@ -38,8 +36,8 @@ class SearchController < ApplicationController |
38 | 36 | end |
39 | 37 | |
40 | 38 | def action_category |
41 | - @recent_articles = category.recent_articles | |
42 | - @recent_comments = category.recent_comments | |
39 | + @recent_articles = @finder.recent('articles') | |
40 | + @recent_comments = @finder.recent('comments') | |
43 | 41 | @most_commented_articles = category.most_commented_articles |
44 | 42 | end |
45 | 43 | alias :action_region :action_category |
... | ... | @@ -69,7 +67,7 @@ class SearchController < ApplicationController |
69 | 67 | @results = {} |
70 | 68 | @names = {} |
71 | 69 | SEARCH_IN.each do |key, description| |
72 | - @results[key] = search(@finder.send(key), @filtered_query) if params[:find_in].nil? || params[:find_in].empty? || params[:find_in].include?(key.to_s) | |
70 | + @results[key] = @finder.send(key, @filtered_query) if params[:find_in].nil? || params[:find_in].empty? || params[:find_in].include?(key.to_s) | |
73 | 71 | @names[key] = gettext(description) |
74 | 72 | end |
75 | 73 | end |
... | ... | @@ -90,7 +88,7 @@ class SearchController < ApplicationController |
90 | 88 | end |
91 | 89 | |
92 | 90 | |
93 | - @results = { asset => @finder.send(asset).recent(LIST_LIMIT) } | |
91 | + @results = { asset => @finder.recent(asset, LIST_LIMIT) } | |
94 | 92 | |
95 | 93 | @asset_name = gettext(SEARCH_IN.find { |entry| entry.first == asset }[1]) |
96 | 94 | @names = { asset => @asset_name } | ... | ... |
... | ... | @@ -0,0 +1,56 @@ |
1 | +class CategoryFinder | |
2 | + | |
3 | + def initialize(cat) | |
4 | + @category = cat | |
5 | + @category_ids = @category.map_traversal(&:id) | |
6 | + end | |
7 | + | |
8 | + attr_reader :category_ids | |
9 | + | |
10 | + def articles(query='*', options={}) | |
11 | + find_in_categorized(Article, query, options) | |
12 | + end | |
13 | + | |
14 | + def people(query='*', options={}) | |
15 | + find_in_categorized(Person, query, options) | |
16 | + end | |
17 | + | |
18 | + def communities(query='*', options={}) | |
19 | + find_in_categorized(Community, query, options) | |
20 | + end | |
21 | + | |
22 | + def enterprises(query='*', options={}) | |
23 | + find_in_categorized(Enterprise, query, options) | |
24 | + end | |
25 | + | |
26 | + def products(query='*', options={}) | |
27 | + Product.find_by_contents(query, {}, {:select => 'products.*', :joins => 'inner join categories_profiles on products.enterprise_id = categories_profiles.profile_id', :conditions => ['categories_profiles.category_id in (?)', category_ids]}.merge!(options)) | |
28 | + end | |
29 | + | |
30 | + def comments(query='*', options={}) | |
31 | + Comment.find_by_contents(query, {}, {:select => 'comments.*', :joins => 'inner join articles_categories on articles_categories.article_id = comments.article_id', :conditions => ['articles_categories.category_id in (?)', category_ids]}.merge!(options)) | |
32 | + end | |
33 | + | |
34 | + def recent(asset, limit = 10) | |
35 | + table = case asset | |
36 | + when 'people', 'communities', 'enterprises' | |
37 | + 'profiles' | |
38 | + else | |
39 | + asset | |
40 | + end | |
41 | + | |
42 | + with_options :limit => limit, :order => "created_at desc, #{table}.id desc" do |finder| | |
43 | + finder.send(asset, '*', {}) | |
44 | + end | |
45 | + end | |
46 | + | |
47 | + def count(asset) | |
48 | + send(asset).size | |
49 | + end | |
50 | + | |
51 | + protected | |
52 | + | |
53 | + def find_in_categorized(klass, query, options={}) | |
54 | + klass.find_by_contents(query, {}, {:include => 'categories', :conditions => ['categories.id IN (?)', category_ids]}.merge!(options)) | |
55 | + end | |
56 | +end | ... | ... |
app/models/environment.rb
... | ... | @@ -76,6 +76,10 @@ class Environment < ActiveRecord::Base |
76 | 76 | # store the Environment settings as YAML-serialized Hash. |
77 | 77 | serialize :settings |
78 | 78 | |
79 | + def homepage | |
80 | + settings[:homepage] | |
81 | + end | |
82 | + | |
79 | 83 | # returns a Hash containing the Environment configuration |
80 | 84 | def settings |
81 | 85 | self[:settings] ||= {} | ... | ... |
... | ... | @@ -0,0 +1,41 @@ |
1 | +class EnvironmentFinder | |
2 | + | |
3 | + def initialize env | |
4 | + @environment = env | |
5 | + end | |
6 | + | |
7 | + def articles(query='*', options = {}) | |
8 | + @environment.articles.find_by_contents(query, {}, options) | |
9 | + end | |
10 | + | |
11 | + def people(query='*', options = {}) | |
12 | + @environment.people.find_by_contents(query, {}, options) | |
13 | + end | |
14 | + | |
15 | + def communities(query='*', options = {}) | |
16 | + @environment.communities.find_by_contents(query, {}, options) | |
17 | + end | |
18 | + | |
19 | + def products(query='*', options = {}) | |
20 | + @environment.products.find_by_contents(query, {}, options) | |
21 | + end | |
22 | + | |
23 | + def enterprises(query='*', options = {}) | |
24 | + @environment.enterprises.find_by_contents(query, {}, options) | |
25 | + end | |
26 | + | |
27 | + def comments(query='*', options = {}) | |
28 | + @environment.comments.find_by_contents(query, {}, options) | |
29 | + end | |
30 | + | |
31 | + def recent(asset, limit = 10) | |
32 | + with_options :limit => limit, :order => 'created_at desc, id desc' do |finder| | |
33 | + finder.send(asset, '*', {}) | |
34 | + end | |
35 | + end | |
36 | + | |
37 | + def count(asset) | |
38 | + @environment.send(asset).count | |
39 | + end | |
40 | + | |
41 | +end | ... | ... |
test/functional/account_controller_test.rb
... | ... | @@ -31,6 +31,13 @@ class AccountControllerTest < Test::Unit::TestCase |
31 | 31 | assert_response :redirect |
32 | 32 | end |
33 | 33 | |
34 | + should 'redirect to user control panel on login' do | |
35 | + u = create_user | |
36 | + post :login, :user => {:login => 'quire', :password => 'quire'} | |
37 | + | |
38 | + assert_redirected_to :controller => 'profile_editor', :action => 'index', :profile => 'quire' | |
39 | + end | |
40 | + | |
34 | 41 | def test_should_fail_login_and_not_redirect |
35 | 42 | post :login, :user => {:login => 'johndoe', :password => 'bad password'} |
36 | 43 | assert_nil session[:user] |
... | ... | @@ -264,6 +271,7 @@ class AccountControllerTest < Test::Unit::TestCase |
264 | 271 | end |
265 | 272 | |
266 | 273 | |
274 | + | |
267 | 275 | protected |
268 | 276 | def create_user(options = {}) |
269 | 277 | post :signup, :user => { :login => 'quire', :email => 'quire@example.com', | ... | ... |
test/functional/search_controller_test.rb
... | ... | @@ -235,7 +235,8 @@ class SearchControllerTest < Test::Unit::TestCase |
235 | 235 | p2 = create_user('test2').person |
236 | 236 | |
237 | 237 | get :assets, :asset => 'people' |
238 | - assert_equal [p2,p1], assigns(:results)[:people] | |
238 | + | |
239 | + assert_equal [p2,p1], assigns(:results)[:people].instance_variable_get('@results') | |
239 | 240 | end |
240 | 241 | |
241 | 242 | # 'assets' menu inside a category |
... | ... | @@ -249,7 +250,7 @@ class SearchControllerTest < Test::Unit::TestCase |
249 | 250 | p2 = create_user('test2').person |
250 | 251 | |
251 | 252 | get :assets, :asset => 'people', :category_path => [ 'my-category' ] |
252 | - assert_equal [p1], assigns(:results)[:people] | |
253 | + assert_equal [p1], assigns(:results)[:people].instance_variable_get('@results') | |
253 | 254 | end |
254 | 255 | |
255 | 256 | should 'find communities' do |
... | ... | @@ -273,7 +274,7 @@ class SearchControllerTest < Test::Unit::TestCase |
273 | 274 | c2 = Community.create!(:name => 'another beautiful community', :identifier => 'an_bea_comm', :environment => Environment.default) |
274 | 275 | |
275 | 276 | get :assets, :asset => 'communities' |
276 | - assert_equal [c2, c1], assigns(:results)[:communities] | |
277 | + assert_equal [c2, c1], assigns(:results)[:communities].instance_variable_get('@results') | |
277 | 278 | end |
278 | 279 | |
279 | 280 | # 'assets' menu |
... | ... | @@ -291,7 +292,8 @@ class SearchControllerTest < Test::Unit::TestCase |
291 | 292 | c3.categories << @category |
292 | 293 | |
293 | 294 | get :assets, :asset => 'communities', :category_path => [ 'my-category' ] |
294 | - assert_equal [c3, c1], assigns(:results)[:communities] | |
295 | + | |
296 | + assert_equal [c3, c1], assigns(:results)[:communities].instance_variable_get('@results') | |
295 | 297 | end |
296 | 298 | |
297 | 299 | should 'find products' do |
... | ... | @@ -321,7 +323,7 @@ class SearchControllerTest < Test::Unit::TestCase |
321 | 323 | prod2 = ent2.products.create!(:name => 'another beautiful product') |
322 | 324 | |
323 | 325 | get :assets, :asset => 'products' |
324 | - assert_equal [prod2, prod1], assigns(:results)[:products] | |
326 | + assert_equivalent [prod2, prod1], assigns(:results)[:products] | |
325 | 327 | end |
326 | 328 | |
327 | 329 | # 'assets' menu inside a category |
... | ... | @@ -509,5 +511,20 @@ class SearchControllerTest < Test::Unit::TestCase |
509 | 511 | get :index, :category_path => [ 'parent-category', 'child-category' ], :query => 'a sample search' |
510 | 512 | assert_tag :tag => 'h2', :content => /Search results for "a sample search" in "Child Category"/ |
511 | 513 | end |
514 | + | |
515 | + should 'search in categoty hierachy' do | |
516 | + parent = Category.create!(:name => 'Parent Category', :environment => Environment.default) | |
517 | + child = Category.create!(:name => 'Child Category', :environment => Environment.default, :parent => parent) | |
518 | + | |
519 | + p = create_user('test_profile').person | |
520 | + p.categories << child | |
521 | + p.save! | |
522 | + | |
523 | + Profile.rebuild_index | |
524 | + | |
525 | + get :index, :category_path => ['parent-category'], :query => 'test_profile', :find_in => ['people'] | |
526 | + | |
527 | + assert_includes assigns(:results)[:people], p | |
528 | + end | |
512 | 529 | |
513 | 530 | end | ... | ... |
test/test_helper.rb
... | ... | @@ -0,0 +1,117 @@ |
1 | +require File.dirname(__FILE__) + '/../test_helper' | |
2 | + | |
3 | +class CategoryFinderTest < ActiveSupport::TestCase | |
4 | + | |
5 | + def setup | |
6 | + @category = Category.create!(:name => 'my category', :environment => Environment.default) | |
7 | + @finder = CategoryFinder.new(@category) | |
8 | + end | |
9 | + | |
10 | + should 'search for articles in a specific category' do | |
11 | + person = create_user('teste').person | |
12 | + | |
13 | + # in category | |
14 | + art1 = person.articles.build(:name => 'an article to be found') | |
15 | + art1.categories << @category | |
16 | + art1.save! | |
17 | + | |
18 | + # not in category | |
19 | + art2 = person.articles.build(:name => 'another article to be found') | |
20 | + art2.save! | |
21 | + | |
22 | + assert_includes @finder.articles, art1 | |
23 | + assert_not_includes @finder.articles, art2 | |
24 | + end | |
25 | + | |
26 | + should 'search for comments in a specific category' do | |
27 | + person = create_user('teste').person | |
28 | + | |
29 | + # in category | |
30 | + art1 = person.articles.build(:name => 'an article to be found') | |
31 | + art1.categories << @category | |
32 | + art1.save! | |
33 | + comment1 = art1.comments.build(:title => 'comment to be found', :body => 'hfyfyh', :author => person); comment1.save! | |
34 | + | |
35 | + # not in category | |
36 | + art2 = person.articles.build(:name => 'another article to be found') | |
37 | + art2.save! | |
38 | + comment2 = art2.comments.build(:title => 'comment to be found', :body => 'hfyfyh', :author => person); comment2.save! | |
39 | + | |
40 | + assert_includes @finder.comments, comment1 | |
41 | + assert_not_includes @finder.comments, comment2 | |
42 | + end | |
43 | + | |
44 | + should 'search for enterprises in a specific category' do | |
45 | + | |
46 | + # in category | |
47 | + ent1 = Enterprise.create!(:name => 'testing enterprise 1', :identifier => 'test1', :categories => [@category]) | |
48 | + | |
49 | + # not in category | |
50 | + ent2 = Enterprise.create!(:name => 'testing enterprise 2', :identifier => 'test2') | |
51 | + | |
52 | + assert_includes @finder.enterprises, ent1 | |
53 | + assert_not_includes @finder.enterprises, ent2 | |
54 | + end | |
55 | + | |
56 | + should 'search for people in a specific category' do | |
57 | + p1 = create_user('people_1').person; p1.name = 'a beautiful person'; p1.categories << @category; p1.save! | |
58 | + p2 = create_user('people_2').person; p2.name = 'another beautiful person'; p2.save! | |
59 | + assert_includes @finder.people, p1 | |
60 | + assert_not_includes @finder.people, p2 | |
61 | + end | |
62 | + | |
63 | + should 'search for communities in a specific category' do | |
64 | + c1 = Community.create!(:name => 'a beautiful community', :identifier => 'bea_comm', :environment => Environment.default) | |
65 | + c2 = Community.create!(:name => 'another beautiful community', :identifier => 'an_bea_comm', :environment => Environment.default) | |
66 | + c1.categories << @category; c1.save! | |
67 | + assert_includes @finder.communities, c1 | |
68 | + assert_not_includes @finder.communities, c2 | |
69 | + end | |
70 | + | |
71 | + should 'search for products in a specific category' do | |
72 | + ent1 = Enterprise.create!(:name => 'teste1', :identifier => 'teste1'); ent1.categories << @category | |
73 | + ent2 = Enterprise.create!(:name => 'teste2', :identifier => 'teste2') | |
74 | + prod1 = ent1.products.create!(:name => 'a beautiful product') | |
75 | + prod2 = ent2.products.create!(:name => 'another beautiful product') | |
76 | + assert_includes @finder.products, prod1 | |
77 | + assert_not_includes @finder.products, prod2 | |
78 | + end | |
79 | + | |
80 | + should 'load ids for category full hierarchy' do | |
81 | + c1 = Category.create!(:name => 'parent', :environment => Environment.default) | |
82 | + c2 = Category.create!(:name => 'child 1', :environment => Environment.default, :parent => c1) | |
83 | + c3 = Category.create!(:name => 'grandchild', :environment => Environment.default, :parent => c2) | |
84 | + c4 = Category.create!(:name => 'child 2', :environment => Environment.default, :parent => c1) | |
85 | + c5 = Category.create!(:name => 'grandchild 2', :environment => Environment.default, :parent => c4) | |
86 | + | |
87 | + assert_equivalent [c1,c2,c3,c4,c5].map(&:id), CategoryFinder.new(c1).category_ids | |
88 | + end | |
89 | + | |
90 | + should 'search in category hierarchy' do | |
91 | + parent = Category.create!(:name => 'child category', :environment => Environment.default) | |
92 | + child = Category.create!(:name => 'child category', :environment => Environment.default, :parent => parent) | |
93 | + p1 = create_user('people_1').person; p1.name = 'a beautiful person'; p1.categories << parent; p1.save! | |
94 | + | |
95 | + f = CategoryFinder.new(parent) | |
96 | + assert_includes f.people, p1 | |
97 | + end | |
98 | + | |
99 | + should 'list recent enterprises' do | |
100 | + ent = Enterprise.create!(:name => 'teste', :identifier => 'teste', :categories => [@category]) | |
101 | + assert_includes @finder.recent('enterprises'), ent | |
102 | + end | |
103 | + | |
104 | + should 'not list more enterprises than limit' do | |
105 | + ent1 = Enterprise.create!(:name => 'teste1', :identifier => 'teste1', :categories => [@category]) | |
106 | + ent2 = Enterprise.create!(:name => 'teste2', :identifier => 'teste2', :categories => [@category]) | |
107 | + recent = @finder.recent('enterprises', 1) | |
108 | + assert_includes recent, ent1 | |
109 | + assert_not_includes recent, ent2 | |
110 | + end | |
111 | + | |
112 | + should 'count entrprises' do | |
113 | + count = @finder.count('enterprises') | |
114 | + ent1 = Enterprise.create!(:name => 'teste1', :identifier => 'teste1', :categories => [@category]) | |
115 | + assert_equal count+1, @finder.count('enterprises') | |
116 | + end | |
117 | +end | ... | ... |
... | ... | @@ -0,0 +1,67 @@ |
1 | +require File.dirname(__FILE__) + '/../test_helper' | |
2 | + | |
3 | +class EnvironmentFinderTest < ActiveSupport::TestCase | |
4 | + | |
5 | + should 'find articles' do | |
6 | + person = create_user('teste').person | |
7 | + art = person.articles.build(:name => 'an article to be found'); art.save! | |
8 | + finder = EnvironmentFinder.new(Environment.default) | |
9 | + assert_includes finder.articles, art | |
10 | + end | |
11 | + | |
12 | + should 'find people' do | |
13 | + p1 = create_user('people_1').person; p1.name = 'a beautiful person'; p1.save! | |
14 | + finder = EnvironmentFinder.new(Environment.default) | |
15 | + assert_includes finder.people, p1 | |
16 | + end | |
17 | + | |
18 | + should 'find communities' do | |
19 | + c1 = Community.create!(:name => 'a beautiful community', :identifier => 'bea_comm', :environment => Environment.default) | |
20 | + finder = EnvironmentFinder.new(Environment.default) | |
21 | + assert_includes finder.communities, c1 | |
22 | + end | |
23 | + | |
24 | + should 'find comments' do | |
25 | + finder = EnvironmentFinder.new(Environment.default) | |
26 | + person = create_user('teste').person | |
27 | + art = person.articles.build(:name => 'an article to be found'); art.save! | |
28 | + comment = art.comments.build(:title => 'comment to be found', :body => 'hfyfyh', :author => person); comment.save! | |
29 | + assert_includes finder.comments, comment | |
30 | + end | |
31 | + | |
32 | + should 'find products' do | |
33 | + finder = EnvironmentFinder.new(Environment.default) | |
34 | + ent = Enterprise.create!(:name => 'teste', :identifier => 'teste') | |
35 | + prod = ent.products.create!(:name => 'a beautiful product') | |
36 | + assert_includes finder.products, prod | |
37 | + end | |
38 | + | |
39 | + should 'find enterprises' do | |
40 | + finder = EnvironmentFinder.new(Environment.default) | |
41 | + ent = Enterprise.create!(:name => 'teste', :identifier => 'teste') | |
42 | + assert_includes finder.enterprises, ent | |
43 | + end | |
44 | + | |
45 | + should 'list recent enterprises' do | |
46 | + finder = EnvironmentFinder.new(Environment.default) | |
47 | + ent = Enterprise.create!(:name => 'teste', :identifier => 'teste') | |
48 | + assert_includes finder.recent('enterprises'), ent | |
49 | + end | |
50 | + | |
51 | + should 'not list more enterprises than limit' do | |
52 | + finder = EnvironmentFinder.new(Environment.default) | |
53 | + ent1 = Enterprise.create!(:name => 'teste1', :identifier => 'teste1') | |
54 | + ent2 = Enterprise.create!(:name => 'teste2', :identifier => 'teste2') | |
55 | + recent = finder.recent('enterprises', 1) | |
56 | + assert_includes recent, ent1 | |
57 | + assert_not_includes recent, ent2 | |
58 | + end | |
59 | + | |
60 | + should 'count entrprises' do | |
61 | + finder = EnvironmentFinder.new(Environment.default) | |
62 | + count = finder.count('enterprises') | |
63 | + ent1 = Enterprise.create!(:name => 'teste1', :identifier => 'teste1') | |
64 | + assert_equal count+1, finder.count('enterprises') | |
65 | + end | |
66 | + | |
67 | +end | ... | ... |