Commit 1b944f750931d2865b7b24577f761f24f16fdd69

Authored by Daniela Feitosa
Committed by Antonio Terceiro
1 parent 868f9ba4

Added pagination to cms and to public view of folder

(ActionItem1689)
app/controllers/my_profile/cms_controller.rb
... ... @@ -61,17 +61,24 @@ class CmsController < MyProfileController
61 61  
62 62 def view
63 63 @article = profile.articles.find(params[:id])
64   - @subitems = @article.children.reject {|item| item.folder? }
  64 + conditions = []
65 65 if @article.blog?
66   - @subitems.reject! {|item| item.class == RssFeed }
  66 + conditions = ['type != ?', 'RssFeed']
67 67 end
68   - @folders = @article.children.select {|item| item.folder? }
  68 +
  69 + @articles = @article.children.find(
  70 + :all,
  71 + :order => "case when type = 'Folder' then 0 when type ='Blog' then 1 else 2 end, updated_at DESC",
  72 + :conditions => conditions
  73 + ).paginate(:per_page => per_page, :page => params[:npage])
69 74 end
70 75  
71 76 def index
72 77 @article = nil
73   - @subitems = profile.top_level_articles.reject {|item| item.folder? }
74   - @folders = profile.top_level_articles.select {|item| item.folder?}
  78 + @articles = profile.top_level_articles.find(
  79 + :all,
  80 + :order => "case when type = 'Folder' then 0 when type ='Blog' then 1 else 2 end, updated_at DESC"
  81 + ).paginate(:per_page => per_page, :page => params[:npage])
75 82 render :action => 'view'
76 83 end
77 84  
... ...
app/helpers/cms_helper.rb
... ... @@ -27,4 +27,30 @@ module CmsHelper
27 27 article_helper.custom_options_for_article(article)
28 28 end
29 29  
  30 + def link_to_article(article)
  31 + article_name = short_filename(article.name, 30)
  32 + if article.folder?
  33 + link_to article_name, :action => 'view', :id => article.id
  34 + else
  35 + link_to article_name, article.url
  36 + end
  37 + end
  38 +
  39 + def display_spread_button(profile, article)
  40 + if profile.person?
  41 + button_without_text :spread, _('Spread this'), :action => 'publish', :id => article.id
  42 + elsif profile.community? && environment.portal_community
  43 + button_without_text :spread, _('Spread this'), :action => 'publish_on_portal_community', :id => article.id
  44 + end
  45 + end
  46 +
  47 + def display_delete_button(article)
  48 + confirm_message = if article.folder?
  49 + _('Are you sure that you want to remove this folder? Note that all the items inside it will also be removed!')
  50 + else
  51 + _('Are you sure that you want to remove this item?')
  52 + end
  53 +
  54 + button_without_text :delete, _('Delete'), { :action => 'destroy', :id => article.id }, :method => :post, :confirm => confirm_message
  55 + end
30 56 end
... ...
app/helpers/folder_helper.rb
... ... @@ -4,11 +4,12 @@ module FolderHelper
4 4  
5 5 def list_articles(articles, recursive = false)
6 6 if !articles.blank?
7   - content_tag(
8   - 'table',
9   - content_tag('tr', content_tag('th', _('Title')) + content_tag('th', _('Last update'))) +
10   - articles.sort_by { |article| article.updated_at }.reverse.map {|item| display_article_in_listing(item, recursive, 0)}.join('')
11   - )
  7 + articles = articles.find(
  8 + :all,
  9 + :order => "updated_at DESC"
  10 + ).paginate(:per_page => 10, :page => params[:npage])
  11 +
  12 + render :file => 'shared/articles_list', :locals => {:articles => articles, :recursive => recursive}
12 13 else
13 14 content_tag('em', _('(empty folder)'))
14 15 end
... ...
app/models/article.rb
... ... @@ -110,9 +110,9 @@ class Article < ActiveRecord::Base
110 110  
111 111 # retrieves all articles belonging to the given +profile+ that are not
112 112 # sub-articles of any other article.
113   - def self.top_level_for(profile)
114   - self.find(:all, :conditions => [ 'parent_id is null and profile_id = ?', profile.id ])
115   - end
  113 + named_scope :top_level_for, lambda { |profile|
  114 + {:conditions => [ 'parent_id is null and profile_id = ?', profile.id ]}
  115 + }
116 116  
117 117 # retrieves the latest +limit+ articles, sorted from the most recent to the
118 118 # oldest.
... ...
app/views/cms/view.rhtml
... ... @@ -46,51 +46,27 @@
46 46 </tr>
47 47 <% end %>
48 48  
49   - <%# folders %>
50   - <% for folder in @folders %>
  49 + <% @articles.each do |article| %>
51 50 <tr>
52 51 <td>
53   - <%= image_tag(icon_for_article(folder)) %>
54   - <%= link_to folder.name, :action => 'view', :id => folder.id %>
  52 + <%= image_tag(icon_for_article(article)) %>
  53 + <%= link_to_article(article) %>
55 54 </td>
56 55 <td>
57   - <%= folder.class.short_description %>
  56 + <%= article.class.short_description %>
58 57 </td>
59 58 <td class="article-controls">
60   - <%= button_without_text :edit, _('Properties'), :action => 'edit', :id => folder.id %>
61   - <%= button_without_text :eyes, _('Public view'), folder.url %>
  59 + <%= button_without_text :edit, _('Edit'), :action => 'edit', :id => article.id %>
  60 + <%= button_without_text :eyes, _('Public view'), article.url %>
  61 + <%= display_spread_button(profile, article) unless article.folder? %>
62 62 <% if !environment.enabled?('cant_change_homepage') %>
63   - <%= button_without_text :home, _('Use as homepage'), { :action => 'set_home_page', :id => folder.id }, :method => :post %>
  63 + <%= button_without_text :home, _('Use as homepage'), { :action => 'set_home_page', :id => article.id }, :method => :post %>
64 64 <% end %>
65   - <%= button_without_text :delete, _('Delete'), { :action => 'destroy', :id => folder.id }, :method => :post, :confirm => _('Are you sure that you want to remove this folder? Note that all the items inside it will also be removed!') %>
66   - </td>
67   - </tr>
68   - <% end %>
69   -
70   - <%# non-folder subitems %>
71   - <% for item in @subitems %>
72   - <tr>
73   - <td>
74   - <%= image_tag(icon_for_article(item)) %>
75   - <%= link_to short_filename(item.name,30), item.url %>
76   - </td>
77   - <td>
78   - <%= item.class.short_description %>
79   - </td>
80   - <td class="article-controls">
81   - <%= button_without_text :edit, _('Edit'), :action => 'edit', :id => item.id %>
82   - <%= button_without_text :eyes, _('Public view'), item.url %>
83   - <% if profile.person? %>
84   - <%= button_without_text :spread, _('Spread this'), :action => 'publish', :id => item.id %>
85   - <% elsif profile.community? && environment.portal_community %>
86   - <%= button_without_text :spread, _('Spread this'), :action => 'publish_on_portal_community', :id => item.id %>
87   - <% end %>
88   - <% if !environment.enabled?('cant_change_homepage') %>
89   - <%= button_without_text :home, _('Use as homepage'), { :action => 'set_home_page', :id => item.id }, :method => :post %>
90   - <% end %>
91   - <%= button_without_text :delete, _('Delete'), { :action => 'destroy', :id => item.id }, :method => :post, :confirm => _('Are you sure that you want to remove this item?') %>
  65 + <%= display_delete_button(article) %>
92 66 </td>
93 67 </tr>
94 68 <% end %>
95 69  
96 70 </table>
  71 +
  72 +<%= pagination_links @articles, {:param_name => 'npage', :prev_label => '&laquo; ' + _('Previous'), :next_label => _('Next') + ' &raquo;', :page_links => true} %>
... ...
app/views/content_viewer/folder.rhtml
... ... @@ -8,5 +8,5 @@
8 8 <% if folder.children.empty? %>
9 9 <em><%= _('(empty folder)') %></em>
10 10 <% else %>
11   - <%= list_articles(available_articles(folder.children, user)) %>
  11 + <%= list_articles(folder.children) %>
12 12 <% end %>
... ...
app/views/shared/articles_list.rhtml 0 → 100644
... ... @@ -0,0 +1,14 @@
  1 +<table>
  2 +
  3 + <tr>
  4 + <th><%= _('Title') %></th>
  5 + <th><%= _('Last update') %></th>
  6 + </tr>
  7 + <% articles.each do |article| %>
  8 + <% if article.display_to?(user) %>
  9 + <%= display_article_in_listing(article, recursive, 0) %>
  10 + <% end %>
  11 + <% end %>
  12 +</table>
  13 +
  14 +<p><%= pagination_links(articles, {:param_name => 'npage', :prev_label => '&laquo; ' + _('Previous'), :next_label => _('Next') + ' &raquo;', :page_links => true}) %></p>
... ...
test/functional/cms_controller_test.rb
... ... @@ -34,7 +34,7 @@ class CmsControllerTest &lt; Test::Unit::TestCase
34 34 assert_template 'view'
35 35 assert_equal profile, assigns(:profile)
36 36 assert_nil assigns(:article)
37   - assert_kind_of Array, assigns(:subitems)
  37 + assert_kind_of Array, assigns(:articles)
38 38 end
39 39  
40 40 should 'be able to view a particular document' do
... ... @@ -46,9 +46,9 @@ class CmsControllerTest &lt; Test::Unit::TestCase
46 46  
47 47 assert_template 'view'
48 48 assert_equal a, assigns(:article)
49   - assert_equal [], assigns(:subitems)
  49 + assert_equal [], assigns(:articles)
50 50  
51   - assert_kind_of Array, assigns(:subitems)
  51 + assert_kind_of Array, assigns(:articles)
52 52 end
53 53  
54 54 should 'be able to edit a document' do
... ... @@ -84,7 +84,7 @@ class CmsControllerTest &lt; Test::Unit::TestCase
84 84 end
85 85  
86 86 should 'display set as home page link to non folder' do
87   - a = profile.articles.create!(:name => 'my new home page')
  87 + a = fast_create(TextileArticle, :profile_id => profile.id, :updated_at => DateTime.now)
88 88 Article.stubs(:short_description).returns('bli')
89 89 get :index, :profile => profile.identifier
90 90 assert_tag :tag => 'a', :content => 'Use as homepage', :attributes => { :href => "/myprofile/#{profile.identifier}/cms/set_home_page/#{a.id}" }
... ... @@ -452,26 +452,27 @@ class CmsControllerTest &lt; Test::Unit::TestCase
452 452 assert_tag :tag => 'input', :attributes => { :name => 'parent_id', :value => profile.home_page.id }
453 453 end
454 454  
455   - should 'list folders at top level' do
456   - Folder.destroy_all
457   - f1 = Folder.new(:name => 'f1'); profile.articles << f1; f1.save!
458   - f2 = Folder.new(:name => 'f2'); profile.articles << f2; f2.save!
  455 + should 'list folders before others' do
  456 + profile.articles.destroy_all
  457 +
  458 + folder1 = fast_create(Folder, :profile_id => profile.id, :updated_at => DateTime.now - 1.hour)
  459 + article = fast_create(TextileArticle, :profile_id => profile.id, :updated_at => DateTime.now)
  460 + folder2 = fast_create(Folder, :profile_id => profile.id, :updated_at => DateTime.now + 1.hour)
459 461  
460 462 get :index, :profile => profile.identifier
461   - assert_equal [f1, f2], assigns(:folders)
462   - assert_not_includes assigns(:subitems), f1
463   - assert_not_includes assigns(:subitems), f2
  463 + assert_equal [folder2, folder1, article], assigns(:articles)
464 464 end
465 465  
466 466 should 'list folders inside another folder' do
467   - parent = Folder.new(:name => 'parent'); profile.articles << parent; parent.save!
468   - f1 = Folder.new(:name => 'f1', :parent => parent); profile.articles << f1; f1.save!
469   - f2 = Folder.new(:name => 'f2', :parent => parent); profile.articles << f2; f2.save!
  467 + profile.articles.destroy_all
  468 +
  469 + parent = fast_create(Folder, :profile_id => profile.id)
  470 + folder1 = fast_create(Folder, :parent_id => parent.id, :profile_id => profile.id, :updated_at => DateTime.now - 1.hour)
  471 + article = fast_create(TextileArticle, :parent_id => parent.id, :profile_id => profile.id, :updated_at => DateTime.now)
  472 + folder2 = fast_create(Folder, :parent_id => parent.id, :profile_id => profile.id, :updated_at => DateTime.now + 1.hour)
470 473  
471 474 get :view, :profile => profile.identifier, :id => parent.id
472   - assert_equal [f1, f2], assigns(:folders)
473   - assert_not_includes assigns(:subitems), f1
474   - assert_not_includes assigns(:subitems), f2
  475 + assert_equal [folder2, folder1, article], assigns(:articles)
475 476 end
476 477  
477 478 should 'offer to create new top-level folder' do
... ... @@ -1190,7 +1191,7 @@ class CmsControllerTest &lt; Test::Unit::TestCase
1190 1191 end
1191 1192  
1192 1193 should "display 'Publish' when profile is a person" do
1193   - a = profile.articles.create!(:name => 'my new home page')
  1194 + a = fast_create(TextileArticle, :profile_id => profile.id, :updated_at => DateTime.now)
1194 1195 Article.stubs(:short_description).returns('bli')
1195 1196 get :index, :profile => profile.identifier
1196 1197 assert_tag :tag => 'a', :attributes => {:href => "/myprofile/#{profile.identifier}/cms/publish/#{a.id}"}
... ... @@ -1200,7 +1201,7 @@ class CmsControllerTest &lt; Test::Unit::TestCase
1200 1201 community = fast_create(Community)
1201 1202 community.add_member(profile)
1202 1203 Environment.any_instance.stubs(:portal_community).returns(community)
1203   - a = community.articles.create!(:name => 'my new home page')
  1204 + a = fast_create(TextileArticle, :profile_id => community.id, :updated_at => DateTime.now)
1204 1205 Article.stubs(:short_description).returns('bli')
1205 1206 get :index, :profile => community.identifier
1206 1207 assert_tag :tag => 'a', :attributes => {:href => "/myprofile/#{community.identifier}/cms/publish_on_portal_community/#{a.id}"}
... ...
test/unit/cms_helper_test.rb
... ... @@ -18,6 +18,74 @@ class CmsHelperTest &lt; Test::Unit::TestCase
18 18 assert_match /id="article\[accept_comments\]" name="article\[accept_comments\]" type="hidden" value="0"/, result
19 19 end
20 20  
  21 + should 'display link to folder content if article is folder' do
  22 + profile = fast_create(Profile)
  23 + folder = fast_create(Folder, :name => 'My folder', :profile_id => profile.id)
  24 + expects(:link_to).with('My folder', :action => 'view', :id => folder.id)
  25 +
  26 + result = link_to_article(folder)
  27 + end
  28 +
  29 + should 'display link to article if article is not folder' do
  30 + profile = fast_create(Profile)
  31 + article = fast_create(TinyMceArticle, :name => 'My article', :profile_id => profile.id)
  32 + expects(:link_to).with('My article', article.url)
  33 +
  34 + result = link_to_article(article)
  35 + end
  36 +
  37 + should 'display spread button when profile is a person' do
  38 + profile = fast_create(Person)
  39 + article = fast_create(TinyMceArticle, :name => 'My article', :profile_id => profile.id)
  40 + expects(:button_without_text).with(:spread, 'Spread this', :action => 'publish', :id => article.id)
  41 +
  42 + result = display_spread_button(profile, article)
  43 + end
  44 +
  45 + should 'display spread button when profile is a community and env has portal_community' do
  46 + env = fast_create(Environment)
  47 + env.expects(:portal_community).returns(true)
  48 + profile = fast_create(Community, :environment_id => env.id)
  49 + expects(:environment).returns(env)
  50 +
  51 + article = fast_create(TinyMceArticle, :name => 'My article', :profile_id => profile.id)
  52 +
  53 + expects(:button_without_text).with(:spread, 'Spread this', :action => 'publish_on_portal_community', :id => article.id)
  54 +
  55 + result = display_spread_button(profile, article)
  56 + end
  57 +
  58 + should 'not display spread button when profile is a community and env has not portal_community' do
  59 + env = fast_create(Environment)
  60 + env.expects(:portal_community).returns(nil)
  61 + profile = fast_create(Community, :environment_id => env.id)
  62 + expects(:environment).returns(env)
  63 +
  64 + article = fast_create(TinyMceArticle, :name => 'My article', :profile_id => profile.id)
  65 +
  66 + expects(:button_without_text).with(:spread, 'Spread this', :action => 'publish_on_portal_community', :id => article.id).never
  67 +
  68 + result = display_spread_button(profile, article)
  69 + end
  70 +
  71 + should 'display delete_button to folder' do
  72 + profile = fast_create(Profile)
  73 + folder = fast_create(Folder, :name => 'My folder', :profile_id => profile.id)
  74 + confirm_message = 'Are you sure that you want to remove this folder? Note that all the items inside it will also be removed!'
  75 + expects(:button_without_text).with(:delete, 'Delete', {:action => 'destroy', :id => folder.id}, :method => :post, :confirm => confirm_message)
  76 +
  77 + result = display_delete_button(folder)
  78 + end
  79 +
  80 + should 'display delete_button to article' do
  81 + profile = fast_create(Profile)
  82 + article = fast_create(TinyMceArticle, :name => 'My article', :profile_id => profile.id)
  83 + confirm_message = 'Are you sure that you want to remove this item?'
  84 + expects(:button_without_text).with(:delete, 'Delete', {:action => 'destroy', :id => article.id}, :method => :post, :confirm => confirm_message)
  85 +
  86 + result = display_delete_button(article)
  87 + end
  88 +
21 89 end
22 90  
23 91 module RssFeedHelper
... ...
test/unit/folder_helper_test.rb
... ... @@ -77,8 +77,16 @@ class FolderHelperTest &lt; Test::Unit::TestCase
77 77 should 'list subitems as HTML content' do
78 78 profile = create_user('folder-owner').person
79 79 folder = fast_create(Folder, {:name => 'Parent Folder', :profile_id => profile.id})
80   - article = fast_create(Article, {:name => 'Article1', :parent_id => folder.id, :profile_id => profile.id})
81   - article = fast_create(Article, {:name => 'Article2', :parent_id => folder.id, :profile_id => profile.id})
  80 + article1 = fast_create(Article, {:name => 'Article1', :parent_id => folder.id, :profile_id => profile.id, :updated_at => DateTime.now })
  81 + article2 = fast_create(Article, {:name => 'Article2', :parent_id => folder.id, :profile_id => profile.id, :updated_at => DateTime.now })
  82 + self.stubs(:params).returns({:npage => nil})
  83 +
  84 + articles = folder.children.find(:all, :order => 'updated_at DESC').paginate(:per_page => 10, :page => params[:npage])
  85 + expects(:user).returns(profile).at_least_once
  86 + expects(:recursive).returns(false).at_least_once
  87 + expects(:pagination_links).with(anything, anything).returns('')
  88 + list = render 'shared/articles_list', binding
  89 + expects(:render).with(:file => 'shared/articles_list', :locals => { :articles => articles, :recursive => false}).returns(list)
82 90  
83 91 result = list_articles(folder.children)
84 92  
... ...
test/unit/profile_test.rb
... ... @@ -193,10 +193,10 @@ class ProfileTest &lt; Test::Unit::TestCase
193 193  
194 194 list = profile.top_level_articles
195 195 same_list = profile.top_level_articles
196   - assert_same list, same_list
  196 + assert_equal list.object_id, same_list.object_id
197 197  
198 198 other_list = profile.top_level_articles(true)
199   - assert_not_same list, other_list
  199 + assert_not_equal list.object_id, other_list.object_id
200 200 end
201 201  
202 202 should 'be able to find profiles by their names with ferret' do
... ...