diff --git a/Capfile b/Capfile
index 17e03a6f8..053d1feb9 100644
--- a/Capfile
+++ b/Capfile
@@ -9,6 +9,7 @@ require 'capistrano/bundler'
#require 'capistrano/rails/assets'
require 'capistrano/rails/migrations'
#require 'capistrano/passenger'
+require 'capistrano/delayed-job'
# Load custom tasks from `lib/capistrano/tasks` if you have any defined
Dir.glob('lib/capistrano/tasks/*.rake').each { |r| import r }
diff --git a/Gemfile b/Gemfile
index a986bf6e2..6913ddb52 100644
--- a/Gemfile
+++ b/Gemfile
@@ -43,6 +43,9 @@ gem 'paranoia'
gem 'savon'
gem 'dalli'
gem 'rollbar', '~> 2.2.1'
+gem 'delayed_job_active_record'
+gem 'daemons'
+gem 'devise-async'
gem 'ahoy_matey', '~> 1.2.1'
gem 'groupdate' # group temporary data
@@ -66,6 +69,7 @@ group :development, :test do
gem "capistrano-bundler", '1.1.4', require: false
gem "capistrano-rails", '1.1.3', require: false
gem "capistrano-rvm", require: false
+ gem 'capistrano3-delayed-job', '~> 1.0'
gem "bullet"
gem "faker"
end
diff --git a/Gemfile.lock b/Gemfile.lock
index 26b825c0d..7d5ebee59 100644
--- a/Gemfile.lock
+++ b/Gemfile.lock
@@ -79,6 +79,8 @@ GEM
capistrano-rvm (0.1.2)
capistrano (~> 3.0)
sshkit (~> 1.2)
+ capistrano3-delayed-job (1.4.0)
+ capistrano (>= 3.0.0)
capybara (2.5.0)
mime-types (>= 1.16)
nokogiri (>= 1.3.3)
@@ -107,9 +109,15 @@ GEM
simplecov (~> 0.10.0)
term-ansicolor (~> 1.3)
thor (~> 0.19.1)
+ daemons (1.2.3)
dalli (2.7.4)
database_cleaner (1.5.0)
debug_inspector (0.0.2)
+ delayed_job (4.0.6)
+ activesupport (>= 3.0, < 5.0)
+ delayed_job_active_record (4.0.3)
+ activerecord (>= 3.0, < 5.0)
+ delayed_job (>= 3.0, < 4.1)
devise (3.5.2)
bcrypt (~> 3.0)
orm_adapter (~> 0.1)
@@ -117,6 +125,8 @@ GEM
responders
thread_safe (~> 0.1)
warden (~> 1.2.3)
+ devise-async (0.10.1)
+ devise (~> 3.2)
diff-lcs (1.2.5)
docile (1.1.5)
domain_name (0.5.24)
@@ -238,7 +248,7 @@ GEM
orm_adapter (0.5.0)
paranoia (2.1.3)
activerecord (~> 4.0)
- pg (0.18.2)
+ pg (0.18.3)
poltergeist (1.6.0)
capybara (~> 2.1)
cliver (~> 0.3.1)
@@ -307,12 +317,12 @@ GEM
rspec-support (3.3.0)
ruby-progressbar (1.7.5)
sass (3.4.18)
- sass-rails (5.0.3)
+ sass-rails (5.0.4)
railties (>= 4.0.0, < 5.0)
sass (~> 3.1)
sprockets (>= 2.8, < 4.0)
sprockets-rails (>= 2.0, < 4.0)
- tilt (~> 1.1)
+ tilt (>= 1.1, < 3)
savon (2.11.1)
akami (~> 1.2)
builder (>= 2.1.2)
@@ -348,7 +358,7 @@ GEM
thor (0.19.1)
thread (0.2.2)
thread_safe (0.3.5)
- tilt (1.4.1)
+ tilt (2.0.1)
tins (1.6.0)
turbolinks (2.5.3)
coffee-rails
@@ -398,13 +408,17 @@ DEPENDENCIES
capistrano-bundler (= 1.1.4)
capistrano-rails (= 1.1.3)
capistrano-rvm
+ capistrano3-delayed-job (~> 1.0)
capybara
ckeditor
coffee-rails (~> 4.1.0)
coveralls
+ daemons
dalli
database_cleaner
+ delayed_job_active_record
devise
+ devise-async
email_spec
factory_girl_rails
faker
diff --git a/app/assets/images/header_bg.jpg b/app/assets/images/header_bg.jpg
index 8d991b8f8..78e357c44 100644
Binary files a/app/assets/images/header_bg.jpg and b/app/assets/images/header_bg.jpg differ
diff --git a/app/assets/javascripts/ckeditor/reinit.js b/app/assets/javascripts/ckeditor/reinit.js
new file mode 100644
index 000000000..fe8e8cff3
--- /dev/null
+++ b/app/assets/javascripts/ckeditor/reinit.js
@@ -0,0 +1,7 @@
+$(document).bind('page:change', function() {
+ if (typeof(CKEDITOR) != "undefined"){
+ for(name in CKEDITOR.instances){
+ try{CKEDITOR.replace(name);}catch(err){};
+ }
+ }
+});
\ No newline at end of file
diff --git a/app/controllers/comments_controller.rb b/app/controllers/comments_controller.rb
index f07507600..96aecf083 100644
--- a/app/controllers/comments_controller.rb
+++ b/app/controllers/comments_controller.rb
@@ -8,8 +8,8 @@ class CommentsController < ApplicationController
def create
if @comment.save
- Mailer.comment(@comment).deliver_now if email_on_debate_comment?
- Mailer.reply(@comment).deliver_now if email_on_comment_reply?
+ Mailer.comment(@comment).deliver_later if email_on_debate_comment?
+ Mailer.reply(@comment).deliver_later if email_on_comment_reply?
else
render :new
end
diff --git a/app/controllers/verification/email_controller.rb b/app/controllers/verification/email_controller.rb
index 1c07b1457..cb7542c80 100644
--- a/app/controllers/verification/email_controller.rb
+++ b/app/controllers/verification/email_controller.rb
@@ -16,7 +16,7 @@ class Verification::EmailController < ApplicationController
@email = Verification::Email.new(@verified_user)
if @email.save
current_user.reload
- Mailer.email_verification(current_user, @email.recipient, @email.encrypted_token).deliver_now
+ Mailer.email_verification(current_user, @email.recipient, @email.encrypted_token).deliver_later
redirect_to account_path, notice: t('verification.email.create.flash.success', email: @verified_user.email)
else
redirect_to verified_user_path, alert: t('verification.email.create.alert.failure')
diff --git a/app/models/user.rb b/app/models/user.rb
index d03cac6e4..7d6ca2380 100644
--- a/app/models/user.rb
+++ b/app/models/user.rb
@@ -6,7 +6,7 @@ class User < ActiveRecord::Base
apply_simple_captcha
devise :database_authenticatable, :registerable, :confirmable,
- :recoverable, :rememberable, :trackable, :validatable, :omniauthable
+ :recoverable, :rememberable, :trackable, :validatable, :omniauthable, :async
acts_as_voter
acts_as_paranoid column: :hidden_at
diff --git a/app/views/shared/_locale_switcher.html.erb b/app/views/shared/_locale_switcher.html.erb
index c95ad58a1..24165f2af 100644
--- a/app/views/shared/_locale_switcher.html.erb
+++ b/app/views/shared/_locale_switcher.html.erb
@@ -1,16 +1,18 @@
-
-
-
- <%= t("layouts.header.locale") %>
-
-
-
+<% if I18n.available_locales.size > 1 %>
+
+
+
+ <%= t("layouts.header.locale") %>
+
+
+
+<% end %>
diff --git a/bin/delayed_job b/bin/delayed_job
new file mode 100755
index 000000000..edf195985
--- /dev/null
+++ b/bin/delayed_job
@@ -0,0 +1,5 @@
+#!/usr/bin/env ruby
+
+require File.expand_path(File.join(File.dirname(__FILE__), '..', 'config', 'environment'))
+require 'delayed/command'
+Delayed::Command.new(ARGV).daemonize
diff --git a/config/application.rb b/config/application.rb
index 8cd17632d..76466329e 100644
--- a/config/application.rb
+++ b/config/application.rb
@@ -33,5 +33,6 @@ module Participacion
# Add lib to the autoload path
config.autoload_paths << Rails.root.join('lib')
config.time_zone = 'Madrid'
+ config.active_job.queue_adapter = :delayed_job
end
end
diff --git a/config/deploy.rb b/config/deploy.rb
index 5a8ec62aa..75a84a1e0 100644
--- a/config/deploy.rb
+++ b/config/deploy.rb
@@ -36,6 +36,8 @@ set :local_user, ENV['USER']
# Run test before deploy
set :tests, ["spec"]
+set :delayed_job_workers, 2
+
# Config files should be copied by deploy:setup_config
set(:config_files, %w(
log_rotation
@@ -57,4 +59,6 @@ namespace :deploy do
after :finishing, 'deploy:cleanup'
# Restart unicorn
after 'deploy:publishing', 'deploy:restart'
+ # Restart Delayed Jobs
+ after 'deploy:published', 'delayed_job:restart'
end
diff --git a/config/deploy/production.rb b/config/deploy/production.rb
index 83c691aa5..49968fc51 100644
--- a/config/deploy/production.rb
+++ b/config/deploy/production.rb
@@ -6,7 +6,7 @@ set :ssh_options, port: deploysecret(:ssh_port)
set :stage, :production
set :rails_env, :production
-server deploysecret(:server1), user: deploysecret(:user), roles: %w(web app db importer)
+#server deploysecret(:server1), user: deploysecret(:user), roles: %w(web app db importer)
server deploysecret(:server2), user: deploysecret(:user), roles: %w(web app db importer)
server deploysecret(:server3), user: deploysecret(:user), roles: %w(web app db importer)
server deploysecret(:server4), user: deploysecret(:user), roles: %w(web app db importer)
diff --git a/config/environments/production.rb b/config/environments/production.rb
index 941ac300e..5e4698336 100644
--- a/config/environments/production.rb
+++ b/config/environments/production.rb
@@ -78,4 +78,6 @@ Rails.application.configure do
# Do not dump schema after migrations.
config.active_record.dump_schema_after_migration = false
+
+ config.i18n.available_locales = [:es]
end
diff --git a/config/initializers/delayed_job_config.rb b/config/initializers/delayed_job_config.rb
new file mode 100644
index 000000000..07e961c9d
--- /dev/null
+++ b/config/initializers/delayed_job_config.rb
@@ -0,0 +1,13 @@
+if Rails.env.test? || Rails.env.development?
+ Delayed::Worker.delay_jobs = false
+else
+ Delayed::Worker.delay_jobs = true
+end
+Delayed::Worker.destroy_failed_jobs = false
+Delayed::Worker.sleep_delay = 2
+Delayed::Worker.max_attempts = 3
+Delayed::Worker.max_run_time = 30.seconds
+Delayed::Worker.read_ahead = 10
+Delayed::Worker.default_queue_name = 'default'
+Delayed::Worker.raise_signal_exceptions = :term
+Delayed::Worker.logger = Logger.new(File.join(Rails.root, 'log', 'delayed_job.log'))
\ No newline at end of file
diff --git a/config/initializers/devise_async.rb b/config/initializers/devise_async.rb
new file mode 100644
index 000000000..47b01e7f4
--- /dev/null
+++ b/config/initializers/devise_async.rb
@@ -0,0 +1,8 @@
+Devise::Async.setup do |config|
+ if Rails.env.test? || Rails.env.development?
+ config.enabled = false
+ else
+ config.enabled = true
+ end
+ config.backend = :delayed_job
+end
\ No newline at end of file
diff --git a/db/migrate/20150903200440_create_delayed_jobs.rb b/db/migrate/20150903200440_create_delayed_jobs.rb
new file mode 100644
index 000000000..27fdcf6cc
--- /dev/null
+++ b/db/migrate/20150903200440_create_delayed_jobs.rb
@@ -0,0 +1,22 @@
+class CreateDelayedJobs < ActiveRecord::Migration
+ def self.up
+ create_table :delayed_jobs, force: true do |table|
+ table.integer :priority, default: 0, null: false # Allows some jobs to jump to the front of the queue
+ table.integer :attempts, default: 0, null: false # Provides for retries, but still fail eventually.
+ table.text :handler, null: false # YAML-encoded string of the object that will do work
+ table.text :last_error # reason for last failure (See Note below)
+ table.datetime :run_at # When to run. Could be Time.zone.now for immediately, or sometime in the future.
+ table.datetime :locked_at # Set when a client is working on this object
+ table.datetime :failed_at # Set when all retries have failed (actually, by default, the record is deleted instead)
+ table.string :locked_by # Who is working on this object (if locked)
+ table.string :queue # The name of the queue this job is in
+ table.timestamps null: true
+ end
+
+ add_index :delayed_jobs, [:priority, :run_at], name: "delayed_jobs_priority"
+ end
+
+ def self.down
+ drop_table :delayed_jobs
+ end
+end
diff --git a/db/schema.rb b/db/schema.rb
index c6c4baf2a..13705eb14 100644
--- a/db/schema.rb
+++ b/db/schema.rb
@@ -11,7 +11,7 @@
#
# It's strongly recommended that you check this file into your version control system.
-ActiveRecord::Schema.define(version: 20150903171309) do
+ActiveRecord::Schema.define(version: 20150903200440) do
# These are extensions that must be enabled in order to support this database
enable_extension "plpgsql"
@@ -90,8 +90,8 @@ ActiveRecord::Schema.define(version: 20150903171309) do
t.integer "author_id"
t.datetime "created_at", null: false
t.datetime "updated_at", null: false
- t.datetime "hidden_at"
t.string "visit_id"
+ t.datetime "hidden_at"
t.integer "flags_count", default: 0
t.datetime "ignored_flag_at"
t.integer "cached_votes_total", default: 0
@@ -110,6 +110,22 @@ ActiveRecord::Schema.define(version: 20150903171309) do
add_index "debates", ["cached_votes_up"], name: "index_debates_on_cached_votes_up", using: :btree
add_index "debates", ["hidden_at"], name: "index_debates_on_hidden_at", using: :btree
+ create_table "delayed_jobs", force: :cascade do |t|
+ t.integer "priority", default: 0, null: false
+ t.integer "attempts", default: 0, null: false
+ t.text "handler", null: false
+ t.text "last_error"
+ t.datetime "run_at"
+ t.datetime "locked_at"
+ t.datetime "failed_at"
+ t.string "locked_by"
+ t.string "queue"
+ t.datetime "created_at"
+ t.datetime "updated_at"
+ end
+
+ add_index "delayed_jobs", ["priority", "run_at"], name: "delayed_jobs_priority", using: :btree
+
create_table "flags", force: :cascade do |t|
t.integer "user_id"
t.string "flaggable_type"
@@ -132,16 +148,6 @@ ActiveRecord::Schema.define(version: 20150903171309) do
add_index "identities", ["user_id"], name: "index_identities_on_user_id", using: :btree
- create_table "inappropiate_flags", force: :cascade do |t|
- t.integer "user_id"
- t.string "flaggable_type"
- t.integer "flaggable_id"
- t.datetime "created_at"
- t.datetime "updated_at"
- end
-
- add_index "inappropiate_flags", ["flaggable_type", "flaggable_id"], name: "index_inappropiate_flags_on_flaggable_type_and_flaggable_id", using: :btree
-
create_table "moderators", force: :cascade do |t|
t.integer "user_id"
end
@@ -211,13 +217,12 @@ ActiveRecord::Schema.define(version: 20150903171309) do
t.string "unconfirmed_email"
t.boolean "email_on_debate_comment", default: false
t.boolean "email_on_comment_reply", default: false
+ t.string "phone_number", limit: 30
t.string "official_position"
t.integer "official_level", default: 0
t.datetime "hidden_at"
- t.string "phone_number", limit: 30
- t.string "username"
- t.datetime "confirmed_hide_at"
t.string "sms_confirmation_code"
+ t.string "username"
t.string "document_number"
t.string "document_type"
t.datetime "residence_verified_at"
@@ -229,6 +234,7 @@ ActiveRecord::Schema.define(version: 20150903171309) do
t.string "unconfirmed_phone"
t.string "confirmed_phone"
t.datetime "letter_requested_at"
+ t.datetime "confirmed_hide_at"
t.string "letter_verification_code"
end
diff --git a/spec/features/debates_spec.rb b/spec/features/debates_spec.rb
index 7ea8ad459..433ce1083 100644
--- a/spec/features/debates_spec.rb
+++ b/spec/features/debates_spec.rb
@@ -69,6 +69,20 @@ feature 'Debates' do
expect(page).to have_content I18n.l(Debate.last.created_at.to_date)
end
+ scenario 'CKEditor is present before & after turbolinks update page', :js do
+ author = create(:user)
+ login_as(author)
+
+ visit new_debate_path
+
+ expect(page).to have_css "#cke_debate_description"
+
+ click_link 'Debates'
+ click_link 'Start a debate'
+
+ expect(page).to have_css "#cke_debate_description"
+ end
+
scenario 'Captcha is required for debate creation' do
login_as(create(:user))
diff --git a/spec/features/localization_spec.rb b/spec/features/localization_spec.rb
index 974753eb3..0066efbbd 100644
--- a/spec/features/localization_spec.rb
+++ b/spec/features/localization_spec.rb
@@ -32,4 +32,15 @@ feature 'Localization' do
expect(page).to_not have_content('Language')
expect(page).to have_select('locale-switcher', selected: 'EspaƱol')
end
+
+ scenario 'Locale switcher not present if only one locale' do
+ initial_locales = I18n.available_locales
+ I18n.available_locales = [:en]
+
+ visit '/'
+ expect(page).to_not have_content('Language')
+ expect(page).to_not have_css('div.locale')
+
+ I18n.available_locales = initial_locales
+ end
end