Commit 7e85741bd4aca60edc23fa80e96814e026612590

Authored by Victor Costa
2 parents 82eec1f1 e83b4b8c
Exists in production

Merge branch 'staging' into production

@@ -81,7 +81,7 @@ group :cucumber do @@ -81,7 +81,7 @@ group :cucumber do
81 gem 'cucumber' 81 gem 'cucumber'
82 gem 'cucumber-rails', '~> 1.4.2', :require => false 82 gem 'cucumber-rails', '~> 1.4.2', :require => false
83 gem 'database_cleaner', '~> 1.3' 83 gem 'database_cleaner', '~> 1.3'
84 - gem 'selenium-webdriver' 84 + gem 'selenium-webdriver', '>= 2.50'
85 end 85 end
86 86
87 # Requires custom dependencies 87 # Requires custom dependencies
app/controllers/application_controller.rb
1 require 'noosfero/multi_tenancy' 1 require 'noosfero/multi_tenancy'
2 2
3 class ApplicationController < ActionController::Base 3 class ApplicationController < ActionController::Base
4 - #protect_from_forgery 4 + protect_from_forgery
5 5
6 - before_filter :setup_multitenancy  
7 before_filter :detect_stuff_by_domain 6 before_filter :detect_stuff_by_domain
8 before_filter :init_noosfero_plugins 7 before_filter :init_noosfero_plugins
9 before_filter :allow_cross_domain_access 8 before_filter :allow_cross_domain_access
@@ -107,12 +106,7 @@ class ApplicationController &lt; ActionController::Base @@ -107,12 +106,7 @@ class ApplicationController &lt; ActionController::Base
107 protected 106 protected
108 107
109 def verified_request? 108 def verified_request?
110 - true  
111 - #super || valid_authenticity_token?(session, request.headers['X-XSRF-TOKEN'])  
112 - end  
113 -  
114 - def setup_multitenancy  
115 - Noosfero::MultiTenancy.setup!(request.host) 109 + super || form_authenticity_token == request.headers['X-XSRF-TOKEN']
116 end 110 end
117 111
118 def boxes_editor? 112 def boxes_editor?
@@ -137,12 +131,11 @@ class ApplicationController &lt; ActionController::Base @@ -137,12 +131,11 @@ class ApplicationController &lt; ActionController::Base
137 @domain = Domain.find_by_name(request.host) 131 @domain = Domain.find_by_name(request.host)
138 if @domain.nil? 132 if @domain.nil?
139 @environment = Environment.default 133 @environment = Environment.default
140 - if @environment.nil? && Rails.env.development?  
141 - # This should only happen in development ... 134 + # Avoid crashes on test and development setups
  135 + if @environment.nil? && !Rails.env.production?
142 @environment = Environment.new 136 @environment = Environment.new
143 @environment.name = "Noosfero" 137 @environment.name = "Noosfero"
144 @environment.is_default = true 138 @environment.is_default = true
145 - @environment.save!  
146 end 139 end
147 else 140 else
148 @environment = @domain.environment 141 @environment = @domain.environment
app/controllers/my_profile/memberships_controller.rb
@@ -18,12 +18,14 @@ class MembershipsController &lt; MyProfileController @@ -18,12 +18,14 @@ class MembershipsController &lt; MyProfileController
18 18
19 def new_community 19 def new_community
20 @community = Community.new(params[:community]) 20 @community = Community.new(params[:community])
  21 + custom_values = params[:profile_data][:custom_values] if (params[:profile_data] && params[:profile_data][:custom_values])
  22 + @community.custom_values = custom_values
21 @community.environment = environment 23 @community.environment = environment
22 @back_to = params[:back_to] || url_for(:action => 'index') 24 @back_to = params[:back_to] || url_for(:action => 'index')
23 if request.post? && @community.valid? 25 if request.post? && @community.valid?
24 begin 26 begin
25 # Community was created 27 # Community was created
26 - @community = Community.create_after_moderation(user, params[:community].merge({:environment => environment})) 28 + @community = Community.create_after_moderation(user, params[:community].merge({:environment => environment, :custom_values => custom_values}))
27 @community.reload 29 @community.reload
28 redirect_to :action => 'welcome', :community_id => @community.id, :back_to => @back_to 30 redirect_to :action => 'welcome', :community_id => @community.id, :back_to => @back_to
29 rescue ActiveRecord::RecordNotFound 31 rescue ActiveRecord::RecordNotFound
app/controllers/public/account_controller.rb
@@ -6,7 +6,7 @@ class AccountController &lt; ApplicationController @@ -6,7 +6,7 @@ class AccountController &lt; ApplicationController
6 before_filter :redirect_if_logged_in, :only => [:login, :signup] 6 before_filter :redirect_if_logged_in, :only => [:login, :signup]
7 before_filter :protect_from_bots, :only => :signup 7 before_filter :protect_from_bots, :only => :signup
8 8
9 - #protect_from_forgery except: [:login] 9 + protect_from_forgery except: [:login]
10 10
11 helper CustomFieldsHelper 11 helper CustomFieldsHelper
12 # say something nice, you goof! something sweet. 12 # say something nice, you goof! something sweet.
app/models/community.rb
@@ -33,7 +33,7 @@ class Community &lt; Organization @@ -33,7 +33,7 @@ class Community &lt; Organization
33 community = Community.new(attributes) 33 community = Community.new(attributes)
34 community.environment = environment 34 community.environment = environment
35 if community.environment.enabled?('admin_must_approve_new_communities') 35 if community.environment.enabled?('admin_must_approve_new_communities')
36 - CreateCommunity.create!(attributes.merge(:requestor => requestor, :environment => environment)) 36 + CreateCommunity.create!(attributes.merge(:requestor => requestor, :environment => environment).except(:custom_values))
37 else 37 else
38 community.save! 38 community.save!
39 community.add_admin(requestor) 39 community.add_admin(requestor)
app/models/session.rb
1 class Session < ActiveRecord::SessionStore::Session 1 class Session < ActiveRecord::SessionStore::Session
2 2
3 - def self.find_by_session_id(session_id)  
4 - where(session_id: session_id).first 3 + # removed and redefined on super class
  4 + def self.find_by_session_id session_id
  5 + super
5 end 6 end
6 7
7 belongs_to :user 8 belongs_to :user
app/models/suggest_article.rb
@@ -23,6 +23,10 @@ class SuggestArticle &lt; Task @@ -23,6 +23,10 @@ class SuggestArticle &lt; Task
23 requestor ? "#{requestor.name}" : "#{name} (#{email})" 23 requestor ? "#{requestor.name}" : "#{name} (#{email})"
24 end 24 end
25 25
  26 + def author_name
  27 + sender
  28 + end
  29 +
26 def article_object 30 def article_object
27 if @article_object.nil? 31 if @article_object.nil?
28 @article_object = article_type.new(article.merge(target.present? ? {:profile => target} : {}).except(:type)) 32 @article_object = article_type.new(article.merge(target.present? ? {:profile => target} : {}).except(:type))
@@ -41,7 +45,6 @@ class SuggestArticle &lt; Task @@ -41,7 +45,6 @@ class SuggestArticle &lt; Task
41 return type if type < Article 45 return type if type < Article
42 end 46 end
43 TinyMceArticle 47 TinyMceArticle
44 - (article[:type] || 'TinyMceArticle').constantize  
45 end 48 end
46 49
47 def perform 50 def perform
config/application.rb
@@ -15,6 +15,9 @@ module Noosfero @@ -15,6 +15,9 @@ module Noosfero
15 15
16 require 'noosfero/plugin' 16 require 'noosfero/plugin'
17 17
  18 + require 'noosfero/multi_tenancy'
  19 + config.middleware.use Noosfero::MultiTenancy::Middleware
  20 +
18 # Adds custom attributes to the Set of allowed html attributes for the #sanitize helper 21 # Adds custom attributes to the Set of allowed html attributes for the #sanitize helper
19 config.action_view.sanitized_allowed_attributes = 'align', 'border', 'alt', 'vspace', 'hspace', 'width', 'heigth', 'value', 'type', 'data', 'style', 'target', 'codebase', 'archive', 'classid', 'code', 'flashvars', 'scrolling', 'frameborder', 'controls', 'autoplay', 'colspan', 'rowspan', 'usemap', 'shape', 'coords' 22 config.action_view.sanitized_allowed_attributes = 'align', 'border', 'alt', 'vspace', 'hspace', 'width', 'heigth', 'value', 'type', 'data', 'style', 'target', 'codebase', 'archive', 'classid', 'code', 'flashvars', 'scrolling', 'frameborder', 'controls', 'autoplay', 'colspan', 'rowspan', 'usemap', 'shape', 'coords'
20 23
features/edit_article.feature
@@ -90,7 +90,7 @@ Feature: edit article @@ -90,7 +90,7 @@ Feature: edit article
90 And I fill in "Title" with "My Folder" 90 And I fill in "Title" with "My Folder"
91 And I choose "article_published_false" 91 And I choose "article_published_false"
92 And I uncheck "article_show_to_followers" 92 And I uncheck "article_show_to_followers"
93 - Then I should see "Fill in the search field to add the exception users to see this content" 93 + Then I should see "Allow only community members entered below to view this content"
94 94
95 @selenium 95 @selenium
96 Scenario: allowed user should see the content of a folder 96 Scenario: allowed user should see the content of a folder
features/forum.feature
@@ -79,7 +79,7 @@ Feature: forum @@ -79,7 +79,7 @@ Feature: forum
79 | joaosilva | Forum One | 79 | joaosilva | Forum One |
80 And I go to /joaosilva/forum-one 80 And I go to /joaosilva/forum-one
81 When I follow "Configure forum" 81 When I follow "Configure forum"
82 - And I fill in "Description" with "My description" 82 + And I fill in tinyMCE "article_body" with "My description"
83 And I check "Has terms of use:" 83 And I check "Has terms of use:"
84 And I press "Save" 84 And I press "Save"
85 Then I should see "Forum One" 85 Then I should see "Forum One"
@@ -95,7 +95,7 @@ Feature: forum @@ -95,7 +95,7 @@ Feature: forum
95 | mariasilva | Maria Silva | 95 | mariasilva | Maria Silva |
96 And I go to /joaosilva/forum-one 96 And I go to /joaosilva/forum-one
97 When I follow "Configure forum" 97 When I follow "Configure forum"
98 - And I fill in "Description" with "My description" 98 + And I fill in tinyMCE "article_body" with "My description"
99 And I check "Has terms of use:" 99 And I check "Has terms of use:"
100 And I press "Save" 100 And I press "Save"
101 When I follow "New discussion topic" 101 When I follow "New discussion topic"
@@ -118,7 +118,7 @@ Feature: forum @@ -118,7 +118,7 @@ Feature: forum
118 | mariasilva | Maria Silva | 118 | mariasilva | Maria Silva |
119 And I go to /joaosilva/forum-one 119 And I go to /joaosilva/forum-one
120 When I follow "Configure forum" 120 When I follow "Configure forum"
121 - And I fill in "Description" with "My description" 121 + And I fill in tinyMCE "article_body" with "My description"
122 And I check "Has terms of use:" 122 And I check "Has terms of use:"
123 And I press "Save" 123 And I press "Save"
124 When I follow "Logout" 124 When I follow "Logout"
@@ -135,7 +135,7 @@ Feature: forum @@ -135,7 +135,7 @@ Feature: forum
135 | joaosilva | Forum One | 135 | joaosilva | Forum One |
136 And I go to /joaosilva/forum-one 136 And I go to /joaosilva/forum-one
137 When I follow "Configure forum" 137 When I follow "Configure forum"
138 - And I fill in "Description" with "My description" 138 + And I fill in tinyMCE "article_body" with "My description"
139 And I check "Has terms of use:" 139 And I check "Has terms of use:"
140 And I press "Save" 140 And I press "Save"
141 When I follow "Logout" 141 When I follow "Logout"
features/media_panel_upload_files.feature
@@ -94,20 +94,17 @@ Feature: uploads items on media panel @@ -94,20 +94,17 @@ Feature: uploads items on media panel
94 94
95 @selenium 95 @selenium
96 Scenario: select type when create new folder 96 Scenario: select type when create new folder
97 - When I follow "Show/Hide"  
98 - And I follow "New folder"  
99 - And I choose "Folder" within "#new-folder-dialog"  
100 - And I fill in "Name" with "Main new folder" within "#new-folder-dialog"  
101 - And I press "Create" 97 + Given I follow "Show/Hide"
  98 + And I follow "New folder"
  99 + And I choose "Folder" within "#new-folder-dialog"
  100 + And I fill in "Name" with "Main new folder" within "#new-folder-dialog"
  101 + When I press "Create"
102 Then I should see "joaosilva/Gallery/Main new folder" within "#parent_id" 102 Then I should see "joaosilva/Gallery/Main new folder" within "#parent_id"
103 - When I follow "New folder"  
104 - And I choose "Gallery" within "#new-folder-dialog"  
105 - And I fill in "Name" with "Gallery new folder" within "#new-folder-dialog"  
106 - And I press "Create"  
107 - And I go to joaosilva's cms  
108 - And I follow "Gallery"  
109 - Then I should see "Folder" within "tr[title='Main new folder'] td.article-mime"  
110 - And I should see "Gallery" within "tr[title='Gallery new folder'] td.article-mime" 103 + Given I follow "New folder"
  104 + And I choose "Gallery" within "#new-folder-dialog"
  105 + And I fill in "Name" with "Gallery new folder" within "#new-folder-dialog"
  106 + When I press "Create"
  107 + Then I should see "joaosilva/Gallery/Gallery new folder" within "#parent_id"
111 108
112 @selenium 109 @selenium
113 Scenario: hide and show upload list 110 Scenario: hide and show upload list
features/step_definitions/web_steps.rb
@@ -39,7 +39,37 @@ end @@ -39,7 +39,37 @@ end
39 39
40 When /^(?:|I )follow "([^"]*)"(?: within "([^"]*)")?$/ do |link, selector| 40 When /^(?:|I )follow "([^"]*)"(?: within "([^"]*)")?$/ do |link, selector|
41 with_scope(selector) do 41 with_scope(selector) do
42 - click_link(link, :match => :prefer_exact) 42 + begin
  43 + click_link(link, :match => :prefer_exact)
  44 + rescue Selenium::WebDriver::Error::UnknownError => selenium_error
  45 + if selenium_error.message.start_with? 'Element is not clickable at point'
  46 + link = find_link(link)
  47 + href = link[:href]
  48 + onclick = link[:onClick]
  49 +
  50 + warn "#{selenium_error.message}\n\n"\
  51 + "Trying to overcome this by:\n"
  52 +
  53 + onclick_return = true
  54 +
  55 + unless onclick.nil?
  56 + warn "\t* Running onClick JS:\n"\
  57 + "\t\t'#{onclick}'\n"
  58 + onclick_return = page.execute_script onclick
  59 + end
  60 +
  61 + if onclick_return
  62 + warn "\t* Redirecting you to the link's href:\n"\
  63 + "\t\t'#{href}'\n"
  64 +
  65 + visit href
  66 + end
  67 +
  68 + warn "\nGood luck and be careful that this may produce hidden links to work on tests!\n"
  69 + else
  70 + raise selenium_error
  71 + end
  72 + end
43 end 73 end
44 end 74 end
45 75
@@ -107,6 +137,7 @@ When /^(?:|I )attach the file &quot;([^&quot;]*)&quot; to &quot;([^&quot;]*)&quot;(?: within &quot;([^&quot;]*)&quot;)?$/ do @@ -107,6 +137,7 @@ When /^(?:|I )attach the file &quot;([^&quot;]*)&quot; to &quot;([^&quot;]*)&quot;(?: within &quot;([^&quot;]*)&quot;)?$/ do
107 with_scope(selector) do 137 with_scope(selector) do
108 attach_file(field, path) 138 attach_file(field, path)
109 end 139 end
  140 + sleep 1
110 end 141 end
111 142
112 Then /^(?:|I )should see JSON:$/ do |expected_json| 143 Then /^(?:|I )should see JSON:$/ do |expected_json|
@@ -260,6 +291,21 @@ Then /^display &quot;([^\&quot;]*)&quot;$/ do |element| @@ -260,6 +291,21 @@ Then /^display &quot;([^\&quot;]*)&quot;$/ do |element|
260 evaluate_script("jQuery('#{element}').show() && false;") 291 evaluate_script("jQuery('#{element}').show() && false;")
261 end 292 end
262 293
  294 +Then /^I fill in tinyMCE "(.*?)" with "(.*?)"$/ do |field, content|
  295 + n = 0
  296 + begin
  297 + execute_script("tinymce.editors['#{field}'].setContent('#{content}')")
  298 + rescue Selenium::WebDriver::Error::JavascriptError
  299 + n += 1
  300 + if n < 5
  301 + sleep 1
  302 + retry
  303 + else
  304 + raise
  305 + end
  306 + end
  307 +end
  308 +
263 Then /^there should be a div with class "([^"]*)"$/ do |klass| 309 Then /^there should be a div with class "([^"]*)"$/ do |klass|
264 should have_selector("div.#{klass}") 310 should have_selector("div.#{klass}")
265 end 311 end
lib/acts_as_customizable.rb
@@ -90,7 +90,7 @@ module Customizable @@ -90,7 +90,7 @@ module Customizable
90 custom_values.each_pair do |key, value| 90 custom_values.each_pair do |key, value|
91 custom_field = environment.custom_fields.detect{|cf|cf.name==key} 91 custom_field = environment.custom_fields.detect{|cf|cf.name==key}
92 next if custom_field.blank? 92 next if custom_field.blank?
93 - custom_field_value = self.custom_field_values.detect{|cv| cv.custom_field.name==key} 93 + custom_field_value = self.custom_field_values(true).detect{|cv| cv.custom_field.name==key}
94 94
95 if custom_field_value.nil? 95 if custom_field_value.nil?
96 custom_field_value = CustomFieldValue.new 96 custom_field_value = CustomFieldValue.new
lib/authenticated_system.rb
@@ -23,17 +23,6 @@ module AuthenticatedSystem @@ -23,17 +23,6 @@ module AuthenticatedSystem
23 def current_user 23 def current_user
24 @current_user ||= begin 24 @current_user ||= begin
25 id = session[:user] 25 id = session[:user]
26 -  
27 - session_id = cookies[:_noosfero_session]  
28 - if id.blank? && session_id.present?  
29 - Session.connection.clear_query_cache  
30 - session_obj = Session.where(session_id: session_id).first  
31 - if session_obj.present?  
32 - session = session_obj.data  
33 - id = session_obj.user_id  
34 - end  
35 - end  
36 -  
37 user = User.where(id: id).first if id 26 user = User.where(id: id).first if id
38 user.session = session if user 27 user.session = session if user
39 User.current = user 28 User.current = user
lib/feed_handler.rb
@@ -60,7 +60,7 @@ class FeedHandler @@ -60,7 +60,7 @@ class FeedHandler
60 def process(container) 60 def process(container)
61 begin 61 begin
62 container.class.transaction do 62 container.class.transaction do
63 - if container.update_errors > FeedHandler.max_errors && container.fetched_at < (Time.now - FeedHandler.disabled_period) 63 + if failed_too_many_times(container) && enough_time_since_last_failure(container)
64 container.enabled = true 64 container.enabled = true
65 container.update_errors = 0 65 container.update_errors = 0
66 container.save 66 container.save
@@ -110,4 +110,12 @@ class FeedHandler @@ -110,4 +110,12 @@ class FeedHandler
110 url =~ URI.regexp('http') || url =~ URI.regexp('https') 110 url =~ URI.regexp('http') || url =~ URI.regexp('https')
111 end 111 end
112 112
  113 + def failed_too_many_times(container)
  114 + container.update_errors > FeedHandler.max_errors
  115 + end
  116 +
  117 + def enough_time_since_last_failure(container)
  118 + container.fetched_at.nil? || container.fetched_at < (Time.now - FeedHandler.disabled_period)
  119 + end
  120 +
113 end 121 end
lib/noosfero/multi_tenancy.rb
@@ -22,6 +22,18 @@ module Noosfero @@ -22,6 +22,18 @@ module Noosfero
22 end 22 end
23 end 23 end
24 24
  25 + class Middleware
  26 + def initialize(app)
  27 + @app = app
  28 + end
  29 +
  30 + def call(env)
  31 + request = Rack::Request.new(env)
  32 + Noosfero::MultiTenancy.setup!(request.host)
  33 + @app.call(env)
  34 + end
  35 + end
  36 +
25 private 37 private
26 38
27 def self.load_map 39 def self.load_map
plugins/comment_paragraph/controllers/profile/comment_paragraph_plugin_profile_controller.rb
1 require 'csv' 1 require 'csv'
2 -class CommentParagraphPluginProfileController < ProfileController 2 +class CommentParagraphPluginProfileController < CommentController
3 append_view_path File.join(File.dirname(__FILE__) + '/../../views') 3 append_view_path File.join(File.dirname(__FILE__) + '/../../views')
4 4
5 def view_comments 5 def view_comments
@@ -12,6 +12,16 @@ class CommentParagraphPluginProfileController &lt; ProfileController @@ -12,6 +12,16 @@ class CommentParagraphPluginProfileController &lt; ProfileController
12 render :partial => 'comment/comment.html.erb', :collection => @comments 12 render :partial => 'comment/comment.html.erb', :collection => @comments
13 end 13 end
14 14
  15 + def comment_form
  16 + @page = profile.articles.find(params[:article_id])
  17 + render :partial => 'comment/comment_form', :locals => {
  18 + :comment => Comment.new,
  19 + :display_link => true,
  20 + :cancel_triggers_hide => true,
  21 + :paragraph_uuid => params[:paragraph_uuid]
  22 + }
  23 + end
  24 +
15 include CommentParagraphPlugin::CommentsReport 25 include CommentParagraphPlugin::CommentsReport
16 26
17 def export_comments 27 def export_comments
plugins/comment_paragraph/lib/comment_paragraph_plugin/macros/allow_comment.rb
@@ -10,7 +10,8 @@ class CommentParagraphPlugin::AllowComment &lt; Noosfero::Plugin::Macro @@ -10,7 +10,8 @@ class CommentParagraphPlugin::AllowComment &lt; Noosfero::Plugin::Macro
10 def parse(params, inner_html, source) 10 def parse(params, inner_html, source)
11 paragraph_uuid = params[:paragraph_uuid] 11 paragraph_uuid = params[:paragraph_uuid]
12 article = source 12 article = source
13 - count = article.paragraph_comments.without_spam.in_paragraph(paragraph_uuid).count 13 + @paragraph_comments_counts ||= article.paragraph_comments.without_spam.group(:paragraph_uuid).reorder(:paragraph_uuid).count
  14 + count = @paragraph_comments_counts.fetch(paragraph_uuid, 0)
14 15
15 proc { 16 proc {
16 if controller.kind_of?(ContentViewerController) && article.comment_paragraph_plugin_activated? 17 if controller.kind_of?(ContentViewerController) && article.comment_paragraph_plugin_activated?
plugins/comment_paragraph/lib/ext/article.rb
@@ -36,7 +36,7 @@ class Article @@ -36,7 +36,7 @@ class Article
36 if body && (body_changed? || setting_changed?(:comment_paragraph_plugin_activate)) 36 if body && (body_changed? || setting_changed?(:comment_paragraph_plugin_activate))
37 updated = body_changed? ? body_change[1] : body 37 updated = body_changed? ? body_change[1] : body
38 doc = Nokogiri::HTML(updated) 38 doc = Nokogiri::HTML(updated)
39 - doc.css('li, body > div, body > span, body > p').each do |paragraph| 39 + (doc.css('li') + doc.css('body > div, body > span, body > p')).each do |paragraph|
40 next if paragraph.css('[data-macro="comment_paragraph_plugin/allow_comment"]').present? || paragraph.content.blank? 40 next if paragraph.css('[data-macro="comment_paragraph_plugin/allow_comment"]').present? || paragraph.content.blank?
41 41
42 commentable = Nokogiri::XML::Node.new("span", doc) 42 commentable = Nokogiri::XML::Node.new("span", doc)
plugins/comment_paragraph/public/comment_paragraph_macro.js
@@ -80,6 +80,12 @@ jQuery(document).ready(function($) { @@ -80,6 +80,12 @@ jQuery(document).ready(function($) {
80 container.find('.display-comment-form').show(); 80 container.find('.display-comment-form').show();
81 } 81 }
82 }); 82 });
  83 + var formDiv = container.find('.side-comment .post_comment_box');
  84 + if(formDiv.find('.page-comment-form').length==0) {
  85 + $.ajax(formDiv.data('comment_paragraph_form_url')).done(function(data) {
  86 + formDiv.append(data);
  87 + });
  88 + }
83 }); 89 });
84 90
85 91
plugins/comment_paragraph/test/functional/comment_paragraph_plugin_profile_controller_test.rb
@@ -10,6 +10,9 @@ class CommentParagraphPluginProfileControllerTest &lt; ActionController::TestCase @@ -10,6 +10,9 @@ class CommentParagraphPluginProfileControllerTest &lt; ActionController::TestCase
10 @profile = create_user('testuser').person 10 @profile = create_user('testuser').person
11 @article = profile.articles.build(:name => 'test') 11 @article = profile.articles.build(:name => 'test')
12 @article.save! 12 @article.save!
  13 + @environment = Environment.default
  14 + @environment.enabled_plugins = ['CommentParagraphPlugin']
  15 + @environment.save!
13 end 16 end
14 attr_reader :article, :profile 17 attr_reader :article, :profile
15 18
@@ -39,6 +42,14 @@ class CommentParagraphPluginProfileControllerTest &lt; ActionController::TestCase @@ -39,6 +42,14 @@ class CommentParagraphPluginProfileControllerTest &lt; ActionController::TestCase
39 assert_match /d comment/, @response.body 42 assert_match /d comment/, @response.body
40 end 43 end
41 44
  45 + should 'load the comment form for a paragraph' do
  46 + login_as('testuser')
  47 + comment = fast_create(Comment, :source_id => article, :author_id => profile, :title => 'a comment', :body => 'lalala', :paragraph_uuid => 0)
  48 + xhr :get, :comment_form, :profile => @profile.identifier, :article_id => article.id, :paragraph_uuid => 0
  49 + assert_select ".page-comment-form"
  50 + assert_select "#comment_paragraph_uuid[value=?]", '0'
  51 + end
  52 +
42 should 'export comments as CSV' do 53 should 'export comments as CSV' do
43 comment1 = fast_create(Comment, :created_at => Time.now - 1.days, :source_id => article, :author_id => profile, :title => 'a comment', :body => 'a comment', :paragraph_uuid => nil) 54 comment1 = fast_create(Comment, :created_at => Time.now - 1.days, :source_id => article, :author_id => profile, :title => 'a comment', :body => 'a comment', :paragraph_uuid => nil)
44 comment2 = fast_create(Comment, :created_at => Time.now - 2.days, :source_id => article, :author_id => profile, :title => 'b comment', :body => 'b comment', :paragraph_uuid => nil) 55 comment2 = fast_create(Comment, :created_at => Time.now - 2.days, :source_id => article, :author_id => profile, :title => 'b comment', :body => 'b comment', :paragraph_uuid => nil)
plugins/comment_paragraph/test/unit/allow_comment_test.rb
@@ -46,4 +46,13 @@ class AllowCommentTest &lt; ActiveSupport::TestCase @@ -46,4 +46,13 @@ class AllowCommentTest &lt; ActiveSupport::TestCase
46 assert_equal 'inner', instance_eval(&content) 46 assert_equal 'inner', instance_eval(&content)
47 end 47 end
48 48
  49 + should 'preload comment counts when parsing content' do
  50 + 3.times { fast_create(Comment, :paragraph_uuid => '2', :source_id => article.id) }
  51 + content = macro.parse({:paragraph_uuid => comment.paragraph_uuid}, article.body, article)
  52 + paragraph_comments_counts = macro.instance_variable_get(:@paragraph_comments_counts)
  53 + assert_equivalent ['1', '2'], paragraph_comments_counts.keys
  54 + assert_equal 1, paragraph_comments_counts['1']
  55 + assert_equal 3, paragraph_comments_counts['2']
  56 + end
  57 +
49 end 58 end
plugins/comment_paragraph/views/comment_paragraph_plugin_profile/_comment_paragraph.html.erb
@@ -11,14 +11,14 @@ @@ -11,14 +11,14 @@
11 </div> 11 </div>
12 12
13 <% load_comments_url = url_for({:profile => profile_identifier, :controller => 'comment_paragraph_plugin_profile', :action => 'view_comments', :paragraph_uuid => paragraph_uuid, :article_id => article_id}) %> 13 <% load_comments_url = url_for({:profile => profile_identifier, :controller => 'comment_paragraph_plugin_profile', :action => 'view_comments', :paragraph_uuid => paragraph_uuid, :article_id => article_id}) %>
  14 + <% load_comment_form_url = url_for({:profile => profile_identifier, :controller => 'comment_paragraph_plugin_profile', :action => 'comment_form', :paragraph_uuid => paragraph_uuid, :article_id => article_id}) %>
14 15
15 <div class="side-comment" data-comment_paragraph_url="<%= load_comments_url %>"> 16 <div class="side-comment" data-comment_paragraph_url="<%= load_comments_url %>">
16 <div class="article-comments-list"> 17 <div class="article-comments-list">
17 <div class="loading"></div> 18 <div class="loading"></div>
18 </div> 19 </div>
19 <div class ="article-comments-list-more"></div> 20 <div class ="article-comments-list-more"></div>
20 - <div class='post_comment_box closed'>  
21 - <%= render :partial => 'comment/comment_form', :locals => {:comment => Comment.new, :display_link => true, :cancel_triggers_hide => true, :paragraph_uuid => paragraph_uuid}%> 21 + <div class='post_comment_box closed' data-comment_paragraph_form_url="<%= load_comment_form_url %>">
22 </div> 22 </div>
23 </div> 23 </div>
24 </div> 24 </div>
public/javascripts/application.js
@@ -568,12 +568,6 @@ function userDataCallback(data) { @@ -568,12 +568,6 @@ function userDataCallback(data) {
568 // logged in 568 // logged in
569 jQuery('head').append('<meta content="authenticity_token" name="csrf-param" />'); 569 jQuery('head').append('<meta content="authenticity_token" name="csrf-param" />');
570 jQuery('head').append('<meta content="'+jQuery.cookie("_noosfero_.XSRF-TOKEN")+'" name="csrf-token" />'); 570 jQuery('head').append('<meta content="'+jQuery.cookie("_noosfero_.XSRF-TOKEN")+'" name="csrf-token" />');
571 - jQuery.ajaxSetup({  
572 - cache: false,  
573 - headers: {  
574 - 'X-XSRF-TOKEN': jQuery.cookie("_noosfero_.XSRF-TOKEN")  
575 - }  
576 - });  
577 } 571 }
578 if (data.notice) { 572 if (data.notice) {
579 display_notice(data.notice); 573 display_notice(data.notice);
test/functional/account_controller_test.rb
@@ -108,6 +108,15 @@ class AccountControllerTest &lt; ActionController::TestCase @@ -108,6 +108,15 @@ class AccountControllerTest &lt; ActionController::TestCase
108 end 108 end
109 end 109 end
110 110
  111 + def test_shoud_save_with_custom_field_on_signup
  112 + assert_difference 'User.count' do
  113 + assert_difference 'CustomFieldValue.count' do
  114 + CustomField.create!(:name => "zombies", :format=>"String", :default_value => "awrrr", :customized_type=>"Profile", :active => true, :required => true, :signup => true, :environment => Environment.default)
  115 + new_user({},{"profile_data"=> {"custom_values"=>{"zombies"=>{"value"=>"BRAINSSS"}}}})
  116 + end
  117 + end
  118 + end
  119 +
111 def test_should_logout 120 def test_should_logout
112 login_as :johndoe 121 login_as :johndoe
113 get :logout 122 get :logout
test/functional/application_controller_test.rb
@@ -478,30 +478,6 @@ class ApplicationControllerTest &lt; ActionController::TestCase @@ -478,30 +478,6 @@ class ApplicationControllerTest &lt; ActionController::TestCase
478 assert_response :forbidden 478 assert_response :forbidden
479 end 479 end
480 480
481 - if ActiveRecord::Base.connection.adapter_name == 'PostgreSQL'  
482 -  
483 - should 'change postgresql schema' do  
484 - uses_host 'schema1.com'  
485 - Noosfero::MultiTenancy.expects(:on?).returns(true)  
486 - Noosfero::MultiTenancy.expects(:mapping).returns({ 'schema1.com' => 'schema1' }).at_least_once  
487 - exception = assert_raise(ActiveRecord::StatementInvalid) { get :index }  
488 -  
489 - # we have switched to a new database schema; depending on the PostgreSQL  
490 - # version, we will receive either an error message because the schema  
491 - # does not exist, or an error saying that whatever table we need can't be  
492 - # found.  
493 - assert_match /(SET search_path TO schema1|PG::UndefinedTable)/, exception.message  
494 - end  
495 -  
496 - should 'not change postgresql schema if multitenancy is off' do  
497 - uses_host 'schema1.com'  
498 - Noosfero::MultiTenancy.stubs(:on?).returns(false)  
499 - Noosfero::MultiTenancy.stubs(:mapping).returns({ 'schema1.com' => 'schema1' })  
500 - assert_nothing_raised(ActiveRecord::StatementInvalid) { get :index }  
501 - end  
502 -  
503 - end  
504 -  
505 should 'register search_term occurrence on find_by_contents' do 481 should 'register search_term occurrence on find_by_contents' do
506 controller = ApplicationController.new 482 controller = ApplicationController.new
507 controller.stubs(:environment).returns(Environment.default) 483 controller.stubs(:environment).returns(Environment.default)
test/functional/memberships_controller_test.rb
@@ -36,6 +36,17 @@ class MembershipsControllerTest &lt; ActionController::TestCase @@ -36,6 +36,17 @@ class MembershipsControllerTest &lt; ActionController::TestCase
36 end 36 end
37 end 37 end
38 38
  39 + should 'be able to create a new community with custom field' do
  40 + assert_difference 'Community.count' do
  41 + assert_difference 'CustomFieldValue.count' do
  42 + CustomField.create!(:name => "zombies", :format=>"String", :default_value => "awrrr", :customized_type=>"Community", :active => true, :required => true, :signup => true, :environment => Environment.default)
  43 + post :new_community, :profile => profile.identifier, :community => { :name => 'My shiny new community', :description => 'This is a community devoted to anything interesting we find in the internet '}, "profile_data"=>{"custom_values"=>{"zombies"=>{"value"=>"BRAINSSS"}}}
  44 + assert_response :redirect
  45 + assert Community.find_by_identifier('my-shiny-new-community').members.include?(profile), "Creator user should be added as member of the community just created"
  46 + end
  47 + end
  48 + end
  49 +
39 should 'link to new community creation in index' do 50 should 'link to new community creation in index' do
40 get :index, :profile => profile.identifier 51 get :index, :profile => profile.identifier
41 assert_tag :tag => 'a', :attributes => { :href => "/myprofile/#{profile.identifier}/memberships/new_community" } 52 assert_tag :tag => 'a', :attributes => { :href => "/myprofile/#{profile.identifier}/memberships/new_community" }
test/functional/tasks_controller_test.rb
@@ -360,6 +360,19 @@ class TasksControllerTest &lt; ActionController::TestCase @@ -360,6 +360,19 @@ class TasksControllerTest &lt; ActionController::TestCase
360 assert_select "#tasks_#{t.id}_task_name" 360 assert_select "#tasks_#{t.id}_task_name"
361 end 361 end
362 362
  363 + should "not crash when article suggestion task fails" do
  364 + TinyMceArticle.destroy_all
  365 + c = fast_create(Community)
  366 + c.affiliate(profile, Profile::Roles.all_roles(profile.environment.id))
  367 + @controller.stubs(:profile).returns(c)
  368 + t = SuggestArticle.create!(:article => {:name => 'test name', :abstract => 'test abstract', :body => 'test body'}, :name => 'some name', :email => 'test@localhost.com', :target => c)
  369 +
  370 + SuggestArticle.any_instance.stubs(:perform).raises('erro')
  371 + assert_nothing_raised do
  372 + post :close, :tasks => {t.id => { :task => {}, :decision => "finish"}}
  373 + end
  374 + end
  375 +
363 should "append hidden tag with type value from article suggestion" do 376 should "append hidden tag with type value from article suggestion" do
364 Task.destroy_all 377 Task.destroy_all
365 c = fast_create(Community) 378 c = fast_create(Community)
test/integration/multi_tenancy_test.rb 0 → 100644
@@ -0,0 +1,40 @@ @@ -0,0 +1,40 @@
  1 +require_relative "../test_helper"
  2 +
  3 +class MultiTenancyTest < ActionDispatch::IntegrationTest
  4 +
  5 + should 'change postgresql schema' do
  6 + host! 'schema1.com'
  7 + Noosfero::MultiTenancy.expects(:on?).at_least_once.returns(true)
  8 + Noosfero::MultiTenancy.expects(:mapping).returns({ 'schema1.com' => 'schema1' }).at_least_once
  9 + exception = assert_raise(ActiveRecord::StatementInvalid) { get '/' }
  10 +
  11 + # we have switched to a new database schema; depending on the PostgreSQL
  12 + # version, we will receive either an error message because the schema
  13 + # does not exist, or an error saying that whatever table we need can't be
  14 + # found.
  15 + assert_match /(SET search_path TO schema1|PG::UndefinedTable)/, exception.message
  16 + end
  17 +
  18 + should 'not change postgresql schema if multitenancy is off' do
  19 + host! 'schema1.com'
  20 + Noosfero::MultiTenancy.stubs(:on?).returns(false)
  21 + Noosfero::MultiTenancy.stubs(:mapping).returns({ 'schema1.com' => 'schema1' })
  22 + assert_nothing_raised(ActiveRecord::StatementInvalid) { get '/' }
  23 + end
  24 +
  25 + should 'find session from the correct database schema' do
  26 + Noosfero::MultiTenancy.expects(:on?).at_least_once.returns(true)
  27 + Noosfero::MultiTenancy.expects(:mapping).returns({ 'schema2.com' => 'public', 'schema1.com' => 'schema1' }).at_least_once
  28 +
  29 + user = create_user
  30 + session_obj = create(Session, user_id: user.id, session_id: 'some_id', data: {})
  31 + person_identifier = user.person.identifier
  32 +
  33 + Noosfero::MultiTenancy.setup!('schema1.com')
  34 + host! 'schema2.com'
  35 + cookies[:_noosfero_session] = session_obj.session_id
  36 + assert_nothing_raised { get "/myprofile/#{person_identifier}" }
  37 + assert_equal 'public', ActiveRecord::Base.connection.schema_search_path
  38 + end
  39 +
  40 +end
test/unit/feed_handler_test.rb
@@ -133,6 +133,14 @@ class FeedHandlerTest &lt; ActiveSupport::TestCase @@ -133,6 +133,14 @@ class FeedHandlerTest &lt; ActiveSupport::TestCase
133 133
134 assert container.enabled, 'must reenable container after <disabled_period> (%s)' % container_class 134 assert container.enabled, 'must reenable container after <disabled_period> (%s)' % container_class
135 end 135 end
  136 +
  137 + should "handle a feed that was never fetched successfully (#{container_class})" do
  138 + container = create(container_class)
  139 + container.update_errors = FeedHandler.max_errors + 1
  140 + container.fetched_at = nil
  141 + handler.expects(:actually_process_container).with(container)
  142 + handler.process(container)
  143 + end
136 end 144 end
137 145
138 should 'not crash even when finish fetch fails' do 146 should 'not crash even when finish fetch fails' do
test/unit/suggest_article_test.rb
@@ -242,4 +242,9 @@ class SuggestArticleTest &lt; ActiveSupport::TestCase @@ -242,4 +242,9 @@ class SuggestArticleTest &lt; ActiveSupport::TestCase
242 t.article_type == TinyMceArticle 242 t.article_type == TinyMceArticle
243 end 243 end
244 244
  245 + should 'fallback to tinymce when type parameter is blank' do
  246 + t = SuggestArticle.new
  247 + t.article = {:name => 'name', :body => 'body', :type => ''}
  248 + t.article_type == TinyMceArticle
  249 + end
245 end 250 end