minimalist_authentication 2.6.2 → 3.0.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/README.md +25 -8
- data/app/views/passwords/edit.html.erb +2 -0
- data/lib/minimalist_authentication/configuration.rb +1 -1
- data/lib/minimalist_authentication/controller.rb +0 -4
- data/lib/minimalist_authentication/sessions.rb +7 -9
- data/lib/minimalist_authentication/test_helper.rb +1 -0
- data/lib/minimalist_authentication/user.rb +23 -50
- data/lib/minimalist_authentication/version.rb +1 -1
- data/lib/minimalist_authentication.rb +0 -3
- metadata +2 -4
- data/lib/minimalist_authentication/null_password.rb +0 -10
- data/lib/minimalist_authentication/password.rb +0 -46
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA256:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: a82f3a3833f400b37555173885d052000dfbd5e4a67da90068384558f8d97705
|
4
|
+
data.tar.gz: 48b819ddbb26a5cb5deaa03c5cd3ef943394e93d6390286d3f30cbae7e5e8477
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: c867bd7daebdce0f0998e78db4d05ed89bd8d3767d6bb0dc79e362f74ca8e2ac43e930dffb0f396d3d1f4f6b517d26fee00e03e06c32a8afd4b52fb0d03984b7
|
7
|
+
data.tar.gz: de8329fcb5b6bd2d01e9a421818952e6f362d4ff16a3e060d30e5b3afbd4751d56e4c0d37b1a3d80d917baf48dea36b407a2fbfc8f647019fa896529d82bf3a2
|
data/README.md
CHANGED
@@ -16,12 +16,12 @@ $ bundle
|
|
16
16
|
|
17
17
|
Create a user model with **email** for an identifier:
|
18
18
|
```bash
|
19
|
-
bin/rails generate model user active:boolean email:string
|
19
|
+
bin/rails generate model user active:boolean email:string password_digest:string last_logged_in_at:datetime
|
20
20
|
```
|
21
21
|
|
22
22
|
OR create a user model with **username** for an identifier:
|
23
23
|
```bash
|
24
|
-
bin/rails generate model user active:boolean username:string
|
24
|
+
bin/rails generate model user active:boolean username:string password_digest:string last_logged_in_at:datetime
|
25
25
|
```
|
26
26
|
|
27
27
|
|
@@ -79,12 +79,11 @@ end
|
|
79
79
|
|
80
80
|
|
81
81
|
## Fixtures
|
82
|
-
Use **MinimalistAuthentication::
|
83
|
-
fixture users.
|
82
|
+
Use **MinimalistAuthentication::TestHelper::PASSWORD_DIGEST** to create a password_digest for fixture users.
|
84
83
|
```yaml
|
85
84
|
example_user:
|
86
|
-
email:
|
87
|
-
|
85
|
+
email: user@example.com
|
86
|
+
password_digest: <%= MinimalistAuthentication::TestHelper::PASSWORD_DIGEST %>
|
88
87
|
```
|
89
88
|
|
90
89
|
|
@@ -124,6 +123,8 @@ bin/rails generate migration AddEmailVerifiedAtToUsers email_verified_at:datetim
|
|
124
123
|
|
125
124
|
|
126
125
|
## Conversions
|
126
|
+
|
127
|
+
### Upgrading to Version 2.0
|
127
128
|
Pre 2.0 versions of MinimalistAuthentication supported multiple hash algorithms
|
128
129
|
and stored the hashed password and salt as separate fields in the database
|
129
130
|
(crypted_password and salt). The current version of MinimalistAuthentication
|
@@ -141,10 +142,26 @@ MinimalistAuthentication::Conversions::MergePasswordHash.run!
|
|
141
142
|
When the conversion is complete the **crypted_password**, **salt**, and
|
142
143
|
**using_digest_version** fields can safely be removed.
|
143
144
|
|
145
|
+
### Upgrading to Version 3.0
|
146
|
+
Version 3.0 of MinimalistAuthentication uses the Rails has_secure_password for authentication. This change requires either renaming the **password_hash** column to **password_digest** or adding an alias_attribute to map **password_digest** to **password_hash**.
|
144
147
|
|
145
|
-
|
146
|
-
|
148
|
+
#### Rename the **password_hash** column to **password_digest**
|
149
|
+
Add a migration to rename the column in your users table:
|
150
|
+
```bash
|
151
|
+
bin/rails generate migration rename_users_password_hash_to_password_digest
|
152
|
+
```
|
147
153
|
|
154
|
+
Update the change method:
|
155
|
+
```ruby
|
156
|
+
def change
|
157
|
+
rename_column :users, :password_hash, :password_digest
|
158
|
+
end
|
159
|
+
```
|
160
|
+
|
161
|
+
#### Alternatively, add **alias_attribute** to your user model
|
162
|
+
```ruby
|
163
|
+
alias_attribute :password_digest, :password_hash
|
164
|
+
```
|
148
165
|
|
149
166
|
## License
|
150
167
|
The gem is available as open source under the terms of the [MIT License](http://opensource.org/licenses/MIT)..
|
@@ -48,9 +48,5 @@ module MinimalistAuthentication
|
|
48
48
|
def store_location
|
49
49
|
session["return_to"] = url_for(request.params.merge(format: :html, only_path: true))
|
50
50
|
end
|
51
|
-
|
52
|
-
def redirect_back_or_default(default)
|
53
|
-
redirect_to(session.delete("return_to") || default)
|
54
|
-
end
|
55
51
|
end
|
56
52
|
end
|
@@ -5,6 +5,9 @@ module MinimalistAuthentication
|
|
5
5
|
extend ActiveSupport::Concern
|
6
6
|
|
7
7
|
included do
|
8
|
+
# URL to redirect to after successful login
|
9
|
+
attr_accessor :return_to
|
10
|
+
|
8
11
|
skip_before_action :authorization_required, only: %i[new create]
|
9
12
|
before_action :redirect_logged_in_users, only: :new
|
10
13
|
end
|
@@ -23,7 +26,7 @@ module MinimalistAuthentication
|
|
23
26
|
end
|
24
27
|
|
25
28
|
def destroy
|
26
|
-
|
29
|
+
reset_session
|
27
30
|
redirect_to logout_redirect_to, notice: t(".notice"), status: :see_other
|
28
31
|
end
|
29
32
|
|
@@ -38,7 +41,8 @@ module MinimalistAuthentication
|
|
38
41
|
end
|
39
42
|
|
40
43
|
def log_in_user
|
41
|
-
|
44
|
+
self.return_to = session["return_to"]
|
45
|
+
reset_session
|
42
46
|
authenticated_user.logged_in
|
43
47
|
session[MinimalistAuthentication.configuration.session_key] = authenticated_user.id
|
44
48
|
end
|
@@ -62,7 +66,7 @@ module MinimalistAuthentication
|
|
62
66
|
end
|
63
67
|
|
64
68
|
def after_authentication_success
|
65
|
-
|
69
|
+
redirect_to return_to || login_redirect_to
|
66
70
|
end
|
67
71
|
|
68
72
|
def attempting_to_verify?
|
@@ -80,12 +84,6 @@ module MinimalistAuthentication
|
|
80
84
|
user_params.values_at(*MinimalistAuthentication::Authenticator::LOGIN_FIELDS).compact.first
|
81
85
|
end
|
82
86
|
|
83
|
-
def scrub_session!
|
84
|
-
(session.keys - %w[session_id return_to]).each do |key|
|
85
|
-
session.delete(key)
|
86
|
-
end
|
87
|
-
end
|
88
|
-
|
89
87
|
def login_redirect_to
|
90
88
|
send(MinimalistAuthentication.configuration.login_redirect_path)
|
91
89
|
end
|
@@ -3,6 +3,7 @@
|
|
3
3
|
module MinimalistAuthentication
|
4
4
|
module TestHelper
|
5
5
|
PASSWORD = "test-password"
|
6
|
+
PASSWORD_DIGEST = BCrypt::Password.create(PASSWORD, cost: BCrypt::Engine::MIN_COST)
|
6
7
|
|
7
8
|
def login_as(user_fixture_name, password = PASSWORD)
|
8
9
|
post session_path, params: { user: { email: users(user_fixture_name).email, password: } }
|
@@ -9,20 +9,16 @@ module MinimalistAuthentication
|
|
9
9
|
GUEST_USER_EMAIL = "guest"
|
10
10
|
|
11
11
|
included do
|
12
|
-
|
13
|
-
attribute :password, :string
|
12
|
+
has_secure_password validations: false
|
14
13
|
|
15
14
|
# Force validations for a blank password.
|
16
15
|
attribute :password_required, :boolean, default: false
|
17
16
|
|
18
|
-
# Hashes and stores the password on save.
|
19
|
-
before_save :hash_password
|
20
|
-
|
21
17
|
# Email validations
|
22
18
|
validates(
|
23
19
|
:email,
|
24
20
|
format: { allow_blank: true, with: URI::MailTo::EMAIL_REGEXP },
|
25
|
-
uniqueness: { allow_blank: true, case_sensitive: false
|
21
|
+
uniqueness: { allow_blank: true, case_sensitive: false },
|
26
22
|
if: :validate_email?
|
27
23
|
)
|
28
24
|
validates(:email, presence: true, if: :validate_email_presence?)
|
@@ -35,6 +31,7 @@ module MinimalistAuthentication
|
|
35
31
|
presence: true,
|
36
32
|
if: :validate_password?
|
37
33
|
)
|
34
|
+
validate :password_exclusivity, if: :password?
|
38
35
|
|
39
36
|
# Active scope
|
40
37
|
scope :active, ->(state = true) { where(active: state) }
|
@@ -42,14 +39,6 @@ module MinimalistAuthentication
|
|
42
39
|
end
|
43
40
|
|
44
41
|
module ClassMethods
|
45
|
-
def authenticate(params)
|
46
|
-
ActiveSupport::Deprecation.warn(<<-MSG.squish)
|
47
|
-
Calling #{MinimalistAuthentication.configuration.user_model_name}::authenticate is deprecated.
|
48
|
-
Use MinimalistAuthentication::Authenticator.authenticated_user instead.
|
49
|
-
MSG
|
50
|
-
MinimalistAuthentication::Authenticator.authenticated_user(params)
|
51
|
-
end
|
52
|
-
|
53
42
|
# Returns a frozen user with the email set to GUEST_USER_EMAIL.
|
54
43
|
def guest
|
55
44
|
new(email: GUEST_USER_EMAIL).freeze
|
@@ -61,18 +50,11 @@ module MinimalistAuthentication
|
|
61
50
|
!active?
|
62
51
|
end
|
63
52
|
|
64
|
-
# Returns true if password matches the hashed_password, otherwise returns false.
|
65
|
-
# authentication the user's password_hash is updated if required.
|
53
|
+
# Returns true if password matches the hashed_password, otherwise returns false.
|
66
54
|
def authenticated?(password)
|
67
|
-
|
68
|
-
|
69
|
-
|
70
|
-
true
|
71
|
-
end
|
72
|
-
|
73
|
-
def logged_in
|
74
|
-
# Use update_column to avoid updated_on trigger
|
75
|
-
update_column(:last_logged_in_at, Time.current)
|
55
|
+
authenticate(password)
|
56
|
+
rescue ::BCrypt::Errors::InvalidHash
|
57
|
+
false
|
76
58
|
end
|
77
59
|
|
78
60
|
# Check if user is a guest based on their email attribute
|
@@ -80,9 +62,9 @@ module MinimalistAuthentication
|
|
80
62
|
email == GUEST_USER_EMAIL
|
81
63
|
end
|
82
64
|
|
83
|
-
def
|
84
|
-
|
85
|
-
|
65
|
+
def logged_in
|
66
|
+
# Use update_column to avoid updated_on trigger
|
67
|
+
update_column(:last_logged_in_at, Time.current)
|
86
68
|
end
|
87
69
|
|
88
70
|
# Minimum password length
|
@@ -91,48 +73,39 @@ module MinimalistAuthentication
|
|
91
73
|
# Maximum password length
|
92
74
|
def password_maximum = 40
|
93
75
|
|
94
|
-
|
95
|
-
|
96
|
-
|
97
|
-
def update_hash!(password)
|
98
|
-
self.password = password
|
99
|
-
return unless valid?
|
100
|
-
|
101
|
-
hash_password
|
102
|
-
save
|
76
|
+
# Checks for password presence
|
77
|
+
def password?
|
78
|
+
password.present?
|
103
79
|
end
|
104
80
|
|
105
|
-
|
106
|
-
def hash_password
|
107
|
-
return if password.blank?
|
108
|
-
|
109
|
-
self.password_hash = Password.create(password)
|
110
|
-
end
|
81
|
+
private
|
111
82
|
|
112
|
-
#
|
113
|
-
def
|
114
|
-
|
83
|
+
# Ensure password does not match username or email.
|
84
|
+
def password_exclusivity
|
85
|
+
%w[username email].each do |field|
|
86
|
+
errors.add(:password, "can not match #{field}") if password.casecmp?(try(field))
|
87
|
+
end
|
115
88
|
end
|
116
89
|
|
117
90
|
# Require password for active users that either do no have a password hash
|
118
91
|
# stored OR are attempting to set a new password. Set **password_required**
|
119
92
|
# to true to force validations even when the password field is blank.
|
120
93
|
def validate_password?
|
121
|
-
active? && (
|
94
|
+
active? && (password_digest.blank? || password? || password_required?)
|
122
95
|
end
|
123
96
|
|
124
|
-
# Validate email for
|
97
|
+
# Validate email for all users.
|
125
98
|
# Applications can turn off email validation by setting the validate_email
|
126
99
|
# configuration attribute to false.
|
127
100
|
def validate_email?
|
128
|
-
MinimalistAuthentication.configuration.validate_email
|
101
|
+
MinimalistAuthentication.configuration.validate_email
|
129
102
|
end
|
130
103
|
|
131
104
|
# Validate email presence for active users.
|
132
105
|
# Applications can turn off email presence validation by setting
|
133
106
|
# validate_email_presence configuration attribute to false.
|
134
107
|
def validate_email_presence?
|
135
|
-
MinimalistAuthentication.configuration.validate_email_presence && validate_email?
|
108
|
+
MinimalistAuthentication.configuration.validate_email_presence && validate_email? && active?
|
136
109
|
end
|
137
110
|
end
|
138
111
|
end
|
@@ -6,9 +6,6 @@ require "minimalist_authentication/configuration"
|
|
6
6
|
require "minimalist_authentication/user"
|
7
7
|
require "minimalist_authentication/verifiable_token"
|
8
8
|
require "minimalist_authentication/email_verification"
|
9
|
-
require "minimalist_authentication/password"
|
10
|
-
require "minimalist_authentication/null_password"
|
11
9
|
require "minimalist_authentication/controller"
|
12
10
|
require "minimalist_authentication/sessions"
|
13
11
|
require "minimalist_authentication/test_helper"
|
14
|
-
require "minimalist_authentication/conversions/merge_password_hash"
|
metadata
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: minimalist_authentication
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version:
|
4
|
+
version: 3.0.0
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Aaron Baldwin
|
@@ -9,7 +9,7 @@ authors:
|
|
9
9
|
autorequire:
|
10
10
|
bindir: bin
|
11
11
|
cert_chain: []
|
12
|
-
date: 2024-
|
12
|
+
date: 2024-11-03 00:00:00.000000000 Z
|
13
13
|
dependencies:
|
14
14
|
- !ruby/object:Gem::Dependency
|
15
15
|
name: bcrypt
|
@@ -84,8 +84,6 @@ files:
|
|
84
84
|
- lib/minimalist_authentication/conversions/merge_password_hash.rb
|
85
85
|
- lib/minimalist_authentication/email_verification.rb
|
86
86
|
- lib/minimalist_authentication/engine.rb
|
87
|
-
- lib/minimalist_authentication/null_password.rb
|
88
|
-
- lib/minimalist_authentication/password.rb
|
89
87
|
- lib/minimalist_authentication/sessions.rb
|
90
88
|
- lib/minimalist_authentication/test_helper.rb
|
91
89
|
- lib/minimalist_authentication/user.rb
|
@@ -1,46 +0,0 @@
|
|
1
|
-
# frozen_string_literal: true
|
2
|
-
|
3
|
-
module MinimalistAuthentication
|
4
|
-
class Password
|
5
|
-
class << self
|
6
|
-
# Create a bcrypt password hash with a calibrated cost factor.
|
7
|
-
def create(secret)
|
8
|
-
new ::BCrypt::Engine.hash_secret(secret, BCrypt::Engine.generate_salt(cost))
|
9
|
-
end
|
10
|
-
|
11
|
-
# Cache the calibrated bcrypt cost factor.
|
12
|
-
def cost
|
13
|
-
@cost ||= calibrate_cost
|
14
|
-
end
|
15
|
-
|
16
|
-
private
|
17
|
-
|
18
|
-
# Calibrates cost so that new user passwords can automatically take
|
19
|
-
# advantage of faster server hardware in the future.
|
20
|
-
# Sets cost to BCrypt::Engine::MIN_COST in the test environment
|
21
|
-
def calibrate_cost
|
22
|
-
::Rails.env.test? ? ::BCrypt::Engine::MIN_COST : ::BCrypt::Engine.calibrate(750)
|
23
|
-
end
|
24
|
-
end
|
25
|
-
|
26
|
-
attr_accessor :bcrypt_password
|
27
|
-
|
28
|
-
# Returns a password object wrapping a valid BCrypt password or a NullPassword
|
29
|
-
def initialize(password_hash)
|
30
|
-
self.bcrypt_password = ::BCrypt::Password.new(password_hash)
|
31
|
-
rescue ::BCrypt::Errors::InvalidHash
|
32
|
-
self.bcrypt_password = NullPassword.new
|
33
|
-
end
|
34
|
-
|
35
|
-
# Delegate methods to bcrypt_password
|
36
|
-
delegate :==, :to_s, :cost, to: :bcrypt_password
|
37
|
-
|
38
|
-
# Temporary access to checksum and salt for backwards compatibility
|
39
|
-
delegate :checksum, :salt, to: :bcrypt_password
|
40
|
-
|
41
|
-
# Checks if the password_hash cost factor is less than the current cost.
|
42
|
-
def stale?
|
43
|
-
cost < self.class.cost
|
44
|
-
end
|
45
|
-
end
|
46
|
-
end
|