devise_security_extension 0.9.2 → 0.10.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +4 -4
- data/.gitignore +39 -0
- data/.rubocop.yml +38 -0
- data/Gemfile +1 -5
- data/Gemfile.lock +144 -141
- data/README.md +37 -11
- data/Rakefile +13 -29
- data/app/controllers/devise/paranoid_verification_code_controller.rb +42 -0
- data/app/controllers/devise/password_expired_controller.rb +16 -7
- data/app/views/devise/paranoid_verification_code/show.html.erb +10 -0
- data/config/locales/de.yml +2 -0
- data/config/locales/en.yml +6 -4
- data/config/locales/it.yml +10 -0
- data/devise_security_extension.gemspec +24 -104
- data/lib/devise_security_extension.rb +18 -8
- data/lib/devise_security_extension/controllers/helpers.rb +39 -6
- data/lib/devise_security_extension/hooks/paranoid_verification.rb +5 -0
- data/lib/devise_security_extension/hooks/session_limitable.rb +1 -0
- data/lib/devise_security_extension/models/paranoid_verification.rb +35 -0
- data/lib/devise_security_extension/models/password_archivable.rb +3 -7
- data/lib/devise_security_extension/models/password_expirable.rb +9 -5
- data/lib/devise_security_extension/patches/confirmations_controller_captcha.rb +3 -1
- data/lib/devise_security_extension/patches/confirmations_controller_security_question.rb +3 -1
- data/lib/devise_security_extension/patches/passwords_controller_captcha.rb +3 -1
- data/lib/devise_security_extension/patches/passwords_controller_security_question.rb +3 -1
- data/lib/devise_security_extension/patches/registrations_controller_captcha.rb +5 -3
- data/lib/devise_security_extension/patches/sessions_controller_captcha.rb +5 -3
- data/lib/devise_security_extension/patches/unlocks_controller_captcha.rb +3 -1
- data/lib/devise_security_extension/patches/unlocks_controller_security_question.rb +3 -1
- data/lib/devise_security_extension/routes.rb +4 -0
- data/lib/devise_security_extension/version.rb +3 -0
- data/lib/generators/devise_security_extension/install_generator.rb +16 -33
- data/lib/generators/templates/devise_security_extension.rb +38 -0
- data/test/dummy/Rakefile +6 -0
- data/test/dummy/app/controllers/application_controller.rb +2 -0
- data/test/dummy/app/controllers/foos_controller.rb +0 -0
- data/test/dummy/app/models/user.rb +2 -1
- data/test/dummy/app/views/foos/index.html.erb +0 -0
- data/test/dummy/config/application.rb +4 -2
- data/test/dummy/config/boot.rb +1 -1
- data/test/dummy/config/environments/test.rb +4 -2
- data/test/dummy/config/initializers/devise.rb +4 -4
- data/test/dummy/config/routes.rb +6 -0
- data/test/dummy/config/secrets.yml +3 -0
- data/test/dummy/db/migrate/20120508165529_create_tables.rb +4 -4
- data/test/dummy/db/migrate/20150402165590_add_verification_columns.rb +11 -0
- data/test/dummy/db/migrate/20150407162345_add_verification_attempt_column.rb +9 -0
- data/test/test_helper.rb +10 -0
- data/test/test_install_generator.rb +16 -0
- data/test/test_paranoid_verification.rb +124 -0
- data/test/test_password_archivable.rb +35 -21
- data/test/test_password_expired_controller.rb +24 -0
- metadata +104 -34
- data/VERSION +0 -1
- data/lib/devise_security_extension/models/security_question.rb +0 -3
- data/test/helper.rb +0 -22
- data/test/test_devise_security_extension.rb +0 -6
data/Rakefile
CHANGED
@@ -1,39 +1,23 @@
|
|
1
|
+
$:.unshift File.join(File.dirname(__FILE__), 'lib')
|
1
2
|
require 'rubygems'
|
2
3
|
require 'bundler'
|
3
|
-
|
4
|
-
|
5
|
-
|
6
|
-
$stderr.puts e.message
|
7
|
-
$stderr.puts "Run `bundle install` to install missing gems"
|
8
|
-
exit e.status_code
|
9
|
-
end
|
10
|
-
require 'rake'
|
4
|
+
require 'rake/testtask'
|
5
|
+
require 'rdoc/task'
|
6
|
+
require 'devise_security_extension/version'
|
11
7
|
|
12
|
-
|
13
|
-
|
14
|
-
# gem is a Gem::Specification... see http://docs.rubygems.org/read/chapter/20 for more options
|
15
|
-
gem.name = "devise_security_extension"
|
16
|
-
gem.homepage = "http://github.com/phatworx/devise_security_extension"
|
17
|
-
gem.license = "MIT"
|
18
|
-
gem.summary = %Q{Security extension for devise}
|
19
|
-
gem.description = %Q{An enterprise security extension for devise, trying to meet industrial standard security demands for web applications.}
|
20
|
-
gem.email = "team@phatworx.de"
|
21
|
-
gem.authors = ["Marco Scholl", "Alexander Dreher"]
|
22
|
-
end
|
23
|
-
Jeweler::RubygemsDotOrgTasks.new
|
8
|
+
desc 'Default: Run DeviseSecurityExtension unit tests'
|
9
|
+
task default: :test
|
24
10
|
|
25
|
-
|
26
|
-
|
27
|
-
|
28
|
-
|
29
|
-
|
11
|
+
Rake::TestTask.new(:test) do |t|
|
12
|
+
t.libs << 'lib'
|
13
|
+
t.libs << 'test'
|
14
|
+
t.test_files = FileList['test/*test*.rb']
|
15
|
+
t.verbose = true
|
16
|
+
t.warning = false
|
30
17
|
end
|
31
18
|
|
32
|
-
task :default => :test
|
33
|
-
|
34
|
-
require 'rdoc/task'
|
35
19
|
Rake::RDocTask.new do |rdoc|
|
36
|
-
version =
|
20
|
+
version = DeviseSecurityExtension::VERSION.dup
|
37
21
|
|
38
22
|
rdoc.rdoc_dir = 'rdoc'
|
39
23
|
rdoc.title = "devise_security_extension #{version}"
|
@@ -0,0 +1,42 @@
|
|
1
|
+
class Devise::ParanoidVerificationCodeController < DeviseController
|
2
|
+
skip_before_filter :handle_paranoid_verification
|
3
|
+
prepend_before_filter :authenticate_scope!, :only => [:show, :update]
|
4
|
+
|
5
|
+
def show
|
6
|
+
if !resource.nil? && resource.need_paranoid_verification?
|
7
|
+
respond_with(resource)
|
8
|
+
else
|
9
|
+
redirect_to :root
|
10
|
+
end
|
11
|
+
end
|
12
|
+
|
13
|
+
def update
|
14
|
+
if resource.verify_code(resource_params[:paranoid_verification_code])
|
15
|
+
warden.session(scope)['paranoid_verify'] = false
|
16
|
+
set_flash_message :notice, :updated
|
17
|
+
sign_in scope, resource, :bypass => true
|
18
|
+
redirect_to stored_location_for(scope) || :root
|
19
|
+
else
|
20
|
+
respond_with(resource, action: :show)
|
21
|
+
end
|
22
|
+
end
|
23
|
+
|
24
|
+
private
|
25
|
+
|
26
|
+
def resource_params
|
27
|
+
if params.respond_to?(:permit)
|
28
|
+
params.require(resource_name).permit(:paranoid_verification_code)
|
29
|
+
else
|
30
|
+
params[scope].slice(:paranoid_verification_code)
|
31
|
+
end
|
32
|
+
end
|
33
|
+
|
34
|
+
def scope
|
35
|
+
resource_name.to_sym
|
36
|
+
end
|
37
|
+
|
38
|
+
def authenticate_scope!
|
39
|
+
send(:"authenticate_#{resource_name}!")
|
40
|
+
self.resource = send("current_#{resource_name}")
|
41
|
+
end
|
42
|
+
end
|
@@ -1,13 +1,10 @@
|
|
1
1
|
class Devise::PasswordExpiredController < DeviseController
|
2
2
|
skip_before_filter :handle_password_change
|
3
|
+
before_filter :skip_password_change, only: [:show, :update]
|
3
4
|
prepend_before_filter :authenticate_scope!, :only => [:show, :update]
|
4
5
|
|
5
6
|
def show
|
6
|
-
|
7
|
-
respond_with(resource)
|
8
|
-
else
|
9
|
-
redirect_to :root
|
10
|
-
end
|
7
|
+
respond_with(resource)
|
11
8
|
end
|
12
9
|
|
13
10
|
def update
|
@@ -24,9 +21,21 @@ class Devise::PasswordExpiredController < DeviseController
|
|
24
21
|
end
|
25
22
|
|
26
23
|
private
|
27
|
-
|
28
|
-
|
24
|
+
|
25
|
+
def skip_password_change
|
26
|
+
return if !resource.nil? && resource.need_change_password?
|
27
|
+
redirect_to :root
|
28
|
+
end
|
29
|
+
|
30
|
+
def resource_params
|
31
|
+
permitted_params = [:current_password, :password, :password_confirmation]
|
32
|
+
|
33
|
+
if params.respond_to?(:permit)
|
34
|
+
params.require(resource_name).permit(*permitted_params)
|
35
|
+
else
|
36
|
+
params[scope].slice(*permitted_params)
|
29
37
|
end
|
38
|
+
end
|
30
39
|
|
31
40
|
def scope
|
32
41
|
resource_name.to_sym
|
@@ -0,0 +1,10 @@
|
|
1
|
+
<h2>Submit verification code</h2>
|
2
|
+
|
3
|
+
<%= form_for(resource, :as => resource_name, :url => [resource_name, :paranoid_verification_code], :html => { :method => :put }) do |f| %>
|
4
|
+
<%= devise_error_messages! %>
|
5
|
+
|
6
|
+
<p><%= f.label :paranoid_verification_code, 'Verification code' %><br />
|
7
|
+
<%= f.text_field :paranoid_verification_code, value: '' %></p>
|
8
|
+
|
9
|
+
<p><%= f.submit "Submit" %></p>
|
10
|
+
<% end %>
|
data/config/locales/de.yml
CHANGED
@@ -6,6 +6,8 @@ de:
|
|
6
6
|
password_format: "müssen große, kleine Buchstaben und Ziffern enthalten"
|
7
7
|
devise:
|
8
8
|
invalid_captcha: "Die Captchaeingabe ist nicht gültig!"
|
9
|
+
paranoid_verify:
|
10
|
+
code_required: "Bitte geben Sie den Code unser Support-Team zur Verfügung gestellt"
|
9
11
|
password_expired:
|
10
12
|
updated: "Das neue Passwort wurde übernommen."
|
11
13
|
change_required: "Ihr Passwort ist abgelaufen. Bitte vergeben sie ein neues Passwort!"
|
data/config/locales/en.yml
CHANGED
@@ -1,14 +1,16 @@
|
|
1
1
|
en:
|
2
2
|
errors:
|
3
3
|
messages:
|
4
|
-
taken_in_past: "was
|
5
|
-
equal_to_current_password: "must be different
|
4
|
+
taken_in_past: "was used previously."
|
5
|
+
equal_to_current_password: "must be different than the current password."
|
6
6
|
password_format: "must contain big, small letters and digits"
|
7
7
|
devise:
|
8
|
-
invalid_captcha: "The captcha input
|
8
|
+
invalid_captcha: "The captcha input was invalid."
|
9
|
+
paranoid_verify:
|
10
|
+
code_required: "Please enter the code our support team provided"
|
9
11
|
password_expired:
|
10
12
|
updated: "Your new password is saved."
|
11
|
-
change_required: "Your password is expired. Please renew your password
|
13
|
+
change_required: "Your password is expired. Please renew your password."
|
12
14
|
failure:
|
13
15
|
session_limited: 'Your login credentials were used in another browser. Please sign in again to continue in this browser.'
|
14
16
|
expired: 'Your account has expired due to inactivity. Please contact the site administrator.'
|
@@ -0,0 +1,10 @@
|
|
1
|
+
it:
|
2
|
+
errors:
|
3
|
+
messages:
|
4
|
+
taken_in_past: "e' stata gia' utilizzata in passato!"
|
5
|
+
equal_to_current_password: " deve essere differente dalla password corrente!"
|
6
|
+
devise:
|
7
|
+
invalid_captcha: "Il captcha inserito non e' valido!"
|
8
|
+
password_expired:
|
9
|
+
updated: "La tua nuova password e' stata salvata."
|
10
|
+
change_required: "La tua password e' scaduta. Si prega di rinnovarla!"
|
@@ -1,111 +1,31 @@
|
|
1
|
-
# Generated by jeweler
|
2
|
-
# DO NOT EDIT THIS FILE DIRECTLY
|
3
|
-
# Instead, edit Jeweler::Tasks in Rakefile, and run 'rake gemspec'
|
4
1
|
# -*- encoding: utf-8 -*-
|
5
|
-
|
2
|
+
$LOAD_PATH.unshift(File.expand_path('../lib', __FILE__))
|
3
|
+
require 'devise_security_extension/version'
|
6
4
|
|
7
5
|
Gem::Specification.new do |s|
|
8
|
-
s.name =
|
9
|
-
s.version
|
6
|
+
s.name = 'devise_security_extension'
|
7
|
+
s.version = DeviseSecurityExtension::VERSION.dup
|
8
|
+
s.platform = Gem::Platform::RUBY
|
9
|
+
s.licenses = ['MIT']
|
10
|
+
s.summary = 'Security extension for devise'
|
11
|
+
s.email = 'team@phatworx.de'
|
12
|
+
s.homepage = 'https://github.com/phatworx/devise_security_extension'
|
13
|
+
s.description = 'An enterprise security extension for devise, trying to meet industrial standard security demands for web applications.'
|
14
|
+
s.authors = ['Marco Scholl', 'Alexander Dreher']
|
10
15
|
|
11
|
-
s.
|
12
|
-
s.require_paths = ["lib"]
|
13
|
-
s.authors = ["Marco Scholl", "Alexander Dreher"]
|
14
|
-
s.date = "2015-04-02"
|
15
|
-
s.description = "An enterprise security extension for devise, trying to meet industrial standard security demands for web applications."
|
16
|
-
s.email = "team@phatworx.de"
|
17
|
-
s.extra_rdoc_files = [
|
18
|
-
"LICENSE.txt",
|
19
|
-
"README.md"
|
20
|
-
]
|
21
|
-
s.files = [
|
22
|
-
".document",
|
23
|
-
"Gemfile",
|
24
|
-
"Gemfile.lock",
|
25
|
-
"LICENSE.txt",
|
26
|
-
"README.md",
|
27
|
-
"Rakefile",
|
28
|
-
"VERSION",
|
29
|
-
"app/controllers/devise/password_expired_controller.rb",
|
30
|
-
"app/views/devise/password_expired/show.html.erb",
|
31
|
-
"config/locales/de.yml",
|
32
|
-
"config/locales/en.yml",
|
33
|
-
"devise_security_extension.gemspec",
|
34
|
-
"lib/devise_security_extension.rb",
|
35
|
-
"lib/devise_security_extension/controllers/helpers.rb",
|
36
|
-
"lib/devise_security_extension/hooks/expirable.rb",
|
37
|
-
"lib/devise_security_extension/hooks/password_expirable.rb",
|
38
|
-
"lib/devise_security_extension/hooks/session_limitable.rb",
|
39
|
-
"lib/devise_security_extension/models/expirable.rb",
|
40
|
-
"lib/devise_security_extension/models/old_password.rb",
|
41
|
-
"lib/devise_security_extension/models/password_archivable.rb",
|
42
|
-
"lib/devise_security_extension/models/password_expirable.rb",
|
43
|
-
"lib/devise_security_extension/models/secure_validatable.rb",
|
44
|
-
"lib/devise_security_extension/models/security_question.rb",
|
45
|
-
"lib/devise_security_extension/models/security_questionable.rb",
|
46
|
-
"lib/devise_security_extension/models/session_limitable.rb",
|
47
|
-
"lib/devise_security_extension/orm/active_record.rb",
|
48
|
-
"lib/devise_security_extension/models/database_authenticatable_patch.rb",
|
49
|
-
"lib/devise_security_extension/patches.rb",
|
50
|
-
"lib/devise_security_extension/patches/confirmations_controller_captcha.rb",
|
51
|
-
"lib/devise_security_extension/patches/confirmations_controller_security_question.rb",
|
52
|
-
"lib/devise_security_extension/patches/passwords_controller_captcha.rb",
|
53
|
-
"lib/devise_security_extension/patches/passwords_controller_security_question.rb",
|
54
|
-
"lib/devise_security_extension/patches/registrations_controller_captcha.rb",
|
55
|
-
"lib/devise_security_extension/patches/sessions_controller_captcha.rb",
|
56
|
-
"lib/devise_security_extension/patches/unlocks_controller_captcha.rb",
|
57
|
-
"lib/devise_security_extension/patches/unlocks_controller_security_question.rb",
|
58
|
-
"lib/devise_security_extension/rails.rb",
|
59
|
-
"lib/devise_security_extension/routes.rb",
|
60
|
-
"lib/devise_security_extension/schema.rb",
|
61
|
-
"lib/generators/devise_security_extension/install_generator.rb",
|
62
|
-
"test/dummy/app/models/.gitkeep",
|
63
|
-
"test/dummy/app/models/user.rb",
|
64
|
-
"test/dummy/config.ru",
|
65
|
-
"test/dummy/config/application.rb",
|
66
|
-
"test/dummy/config/boot.rb",
|
67
|
-
"test/dummy/config/database.yml",
|
68
|
-
"test/dummy/config/environment.rb",
|
69
|
-
"test/dummy/config/environments/test.rb",
|
70
|
-
"test/dummy/config/initializers/devise.rb",
|
71
|
-
"test/dummy/db/migrate/20120508165529_create_tables.rb",
|
72
|
-
"test/helper.rb",
|
73
|
-
"test/test_devise_security_extension.rb",
|
74
|
-
"test/test_password_archivable.rb"
|
75
|
-
]
|
76
|
-
s.homepage = "http://github.com/phatworx/devise_security_extension"
|
77
|
-
s.licenses = ["MIT"]
|
78
|
-
s.rubygems_version = "2.2.2"
|
79
|
-
s.summary = "Security extension for devise"
|
16
|
+
s.rubyforge_project = 'devise_security_extension'
|
80
17
|
|
81
|
-
|
82
|
-
|
18
|
+
s.files = `git ls-files`.split("\n")
|
19
|
+
s.test_files = `git ls-files -- test/*`.split("\n")
|
20
|
+
s.require_paths = ['lib']
|
21
|
+
s.required_ruby_version = '>= 1.9.3'
|
83
22
|
|
84
|
-
|
85
|
-
|
86
|
-
|
87
|
-
|
88
|
-
|
89
|
-
|
90
|
-
|
91
|
-
|
92
|
-
else
|
93
|
-
s.add_dependency(%q<rails>, [">= 3.1.1"])
|
94
|
-
s.add_dependency(%q<devise>, [">= 2.0.0"])
|
95
|
-
s.add_dependency(%q<rails_email_validator>, [">= 0"])
|
96
|
-
s.add_dependency(%q<easy_captcha>, [">= 0"])
|
97
|
-
s.add_dependency(%q<bundler>, [">= 1.0.0"])
|
98
|
-
s.add_dependency(%q<jeweler>, ["~> 2.0.1"])
|
99
|
-
s.add_dependency(%q<sqlite3>, [">= 0"])
|
100
|
-
end
|
101
|
-
else
|
102
|
-
s.add_dependency(%q<rails>, [">= 3.1.1"])
|
103
|
-
s.add_dependency(%q<devise>, [">= 2.0.0"])
|
104
|
-
s.add_dependency(%q<rails_email_validator>, [">= 0"])
|
105
|
-
s.add_dependency(%q<easy_captcha>, [">= 0"])
|
106
|
-
s.add_dependency(%q<bundler>, [">= 1.0.0"])
|
107
|
-
s.add_dependency(%q<jeweler>, ["~> 2.0.1"])
|
108
|
-
s.add_dependency(%q<sqlite3>, [">= 0"])
|
109
|
-
end
|
23
|
+
s.add_runtime_dependency 'railties', '>= 3.2.6', '< 5.0'
|
24
|
+
s.add_runtime_dependency 'devise', '>= 3.0.0', '< 4.0'
|
25
|
+
s.add_development_dependency 'bundler', '>= 1.3.0', '< 2.0'
|
26
|
+
s.add_development_dependency 'sqlite3', '~> 1.3.10'
|
27
|
+
s.add_development_dependency 'rubocop', '~> 0'
|
28
|
+
s.add_development_dependency 'minitest'
|
29
|
+
s.add_development_dependency 'easy_captcha', '~> 0'
|
30
|
+
s.add_development_dependency 'rails_email_validator', '~> 0'
|
110
31
|
end
|
111
|
-
|
@@ -14,7 +14,7 @@ module Devise
|
|
14
14
|
mattr_accessor :password_regex
|
15
15
|
@@password_regex = /(?=.*\d)(?=.*[a-z])(?=.*[A-Z])/
|
16
16
|
|
17
|
-
#
|
17
|
+
# Number of old passwords in archive
|
18
18
|
mattr_accessor :password_archiving_count
|
19
19
|
@@password_archiving_count = 5
|
20
20
|
|
@@ -62,11 +62,19 @@ module Devise
|
|
62
62
|
mattr_accessor :captcha_for_confirmation
|
63
63
|
@@captcha_for_confirmation = false
|
64
64
|
|
65
|
+
# captcha integration for confirmation form
|
66
|
+
mattr_accessor :verification_code_generator
|
67
|
+
@@verification_code_generator = -> { SecureRandom.hex[0..4] }
|
68
|
+
|
65
69
|
# Time period for account expiry from last_activity_at
|
66
70
|
mattr_accessor :expire_after
|
67
71
|
@@expire_after = 90.days
|
68
72
|
mattr_accessor :delete_expired_after
|
69
73
|
@@delete_expired_after = 90.days
|
74
|
+
|
75
|
+
# paranoid_verification will regenerate verifacation code after faild attempt
|
76
|
+
mattr_accessor :paranoid_code_regenerate_after_attempt
|
77
|
+
@@paranoid_code_regenerate_after_attempt = 10
|
70
78
|
end
|
71
79
|
|
72
80
|
# an security extension for devise
|
@@ -80,17 +88,19 @@ module DeviseSecurityExtension
|
|
80
88
|
end
|
81
89
|
|
82
90
|
# modules
|
83
|
-
Devise.add_module :password_expirable, :
|
84
|
-
Devise.add_module :secure_validatable, :
|
85
|
-
Devise.add_module :password_archivable, :
|
86
|
-
Devise.add_module :session_limitable, :
|
87
|
-
Devise.add_module :
|
88
|
-
Devise.add_module :
|
91
|
+
Devise.add_module :password_expirable, controller: :password_expirable, model: 'devise_security_extension/models/password_expirable', route: :password_expired
|
92
|
+
Devise.add_module :secure_validatable, model: 'devise_security_extension/models/secure_validatable'
|
93
|
+
Devise.add_module :password_archivable, model: 'devise_security_extension/models/password_archivable'
|
94
|
+
Devise.add_module :session_limitable, model: 'devise_security_extension/models/session_limitable'
|
95
|
+
Devise.add_module :session_non_transferable, model: 'devise_security_extension/models/session_non_transferable'
|
96
|
+
Devise.add_module :expirable, model: 'devise_security_extension/models/expirable'
|
97
|
+
Devise.add_module :security_questionable, model: 'devise_security_extension/models/security_questionable'
|
98
|
+
Devise.add_module :paranoid_verification, controller: :paranoid_verification_code, model: 'devise_security_extension/models/paranoid_verification', route: :verification_code
|
89
99
|
|
90
100
|
# requires
|
91
101
|
require 'devise_security_extension/routes'
|
92
102
|
require 'devise_security_extension/rails'
|
93
103
|
require 'devise_security_extension/orm/active_record'
|
94
104
|
require 'devise_security_extension/models/old_password'
|
95
|
-
require 'devise_security_extension/models/security_question'
|
96
105
|
require 'devise_security_extension/models/database_authenticatable_patch'
|
106
|
+
require 'devise_security_extension/models/paranoid_verification'
|
@@ -5,13 +5,14 @@ module DeviseSecurityExtension
|
|
5
5
|
|
6
6
|
included do
|
7
7
|
before_filter :handle_password_change
|
8
|
+
before_filter :handle_paranoid_verification
|
8
9
|
end
|
9
|
-
|
10
|
+
|
10
11
|
module ClassMethods
|
11
12
|
# helper for captcha
|
12
13
|
def init_recover_password_captcha
|
13
14
|
include RecoverPasswordCaptcha
|
14
|
-
end
|
15
|
+
end
|
15
16
|
end
|
16
17
|
|
17
18
|
module RecoverPasswordCaptcha
|
@@ -26,11 +27,33 @@ module DeviseSecurityExtension
|
|
26
27
|
|
27
28
|
# lookup if an password change needed
|
28
29
|
def handle_password_change
|
30
|
+
return if warden.nil?
|
31
|
+
|
29
32
|
if not devise_controller? and not ignore_password_expire? and not request.format.nil? and request.format.html?
|
30
33
|
Devise.mappings.keys.flatten.any? do |scope|
|
31
34
|
if signed_in?(scope) and warden.session(scope)['password_expired']
|
32
|
-
|
33
|
-
|
35
|
+
# re-check to avoid infinite loop if date changed after login attempt
|
36
|
+
if send(:"current_#{scope}").try(:need_change_password?)
|
37
|
+
session["#{scope}_return_to"] = request.original_fullpath if request.get?
|
38
|
+
redirect_for_password_change scope
|
39
|
+
return
|
40
|
+
else
|
41
|
+
warden.session(scope)[:password_expired] = false
|
42
|
+
end
|
43
|
+
end
|
44
|
+
end
|
45
|
+
end
|
46
|
+
end
|
47
|
+
|
48
|
+
# lookup if extra (paranoid) code verification is needed
|
49
|
+
def handle_paranoid_verification
|
50
|
+
return if warden.nil?
|
51
|
+
|
52
|
+
if !devise_controller? && !request.format.nil? && request.format.html?
|
53
|
+
Devise.mappings.keys.flatten.any? do |scope|
|
54
|
+
if signed_in?(scope) && warden.session(scope)['paranoid_verify']
|
55
|
+
session["#{scope}_return_to"] = request.original_fullpath if request.get?
|
56
|
+
redirect_for_paranoid_verification scope
|
34
57
|
return
|
35
58
|
end
|
36
59
|
end
|
@@ -42,15 +65,25 @@ module DeviseSecurityExtension
|
|
42
65
|
redirect_to change_password_required_path_for(scope), :alert => I18n.t('change_required', {:scope => 'devise.password_expired'})
|
43
66
|
end
|
44
67
|
|
68
|
+
def redirect_for_paranoid_verification(scope)
|
69
|
+
redirect_to paranoid_verification_code_path_for(scope), :alert => I18n.t('code_required', {:scope => 'devise.paranoid_verify'})
|
70
|
+
end
|
71
|
+
|
45
72
|
# path for change password
|
46
73
|
def change_password_required_path_for(resource_or_scope = nil)
|
47
74
|
scope = Devise::Mapping.find_scope!(resource_or_scope)
|
48
75
|
change_path = "#{scope}_password_expired_path"
|
49
76
|
send(change_path)
|
50
77
|
end
|
51
|
-
|
78
|
+
|
79
|
+
def paranoid_verification_code_path_for(resource_or_scope = nil)
|
80
|
+
scope = Devise::Mapping.find_scope!(resource_or_scope)
|
81
|
+
change_path = "#{scope}_paranoid_verification_code_path"
|
82
|
+
send(change_path)
|
83
|
+
end
|
84
|
+
|
52
85
|
protected
|
53
|
-
|
86
|
+
|
54
87
|
# allow to overwrite for some special handlings
|
55
88
|
def ignore_password_expire?
|
56
89
|
false
|