rodauth 2.5.0 → 2.10.0
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +4 -4
- data/CHANGELOG +42 -0
- data/MIT-LICENSE +1 -1
- data/README.rdoc +18 -6
- data/doc/argon2.rdoc +49 -0
- data/doc/base.rdoc +3 -2
- data/doc/guides/migrate_password_hash_algorithm.rdoc +15 -0
- data/doc/json.rdoc +47 -0
- data/doc/jwt.rdoc +1 -28
- data/doc/jwt_refresh.rdoc +8 -0
- data/doc/login_password_requirements_base.rdoc +1 -1
- data/doc/recovery_codes.rdoc +2 -1
- data/doc/release_notes/2.10.0.txt +47 -0
- data/doc/release_notes/2.6.0.txt +37 -0
- data/doc/release_notes/2.7.0.txt +33 -0
- data/doc/release_notes/2.8.0.txt +20 -0
- data/doc/release_notes/2.9.0.txt +21 -0
- data/doc/remember.rdoc +1 -1
- data/javascript/webauthn_auth.js +9 -9
- data/javascript/webauthn_setup.js +9 -6
- data/lib/rodauth.rb +14 -6
- data/lib/rodauth/features/argon2.rb +69 -0
- data/lib/rodauth/features/base.rb +12 -3
- data/lib/rodauth/features/confirm_password.rb +2 -2
- data/lib/rodauth/features/disallow_password_reuse.rb +20 -7
- data/lib/rodauth/features/json.rb +189 -0
- data/lib/rodauth/features/jwt.rb +22 -170
- data/lib/rodauth/features/jwt_refresh.rb +63 -13
- data/lib/rodauth/features/login_password_requirements_base.rb +4 -0
- data/lib/rodauth/features/otp.rb +0 -2
- data/lib/rodauth/features/recovery_codes.rb +22 -1
- data/lib/rodauth/features/remember.rb +6 -1
- data/lib/rodauth/features/update_password_hash.rb +1 -1
- data/lib/rodauth/features/verify_account.rb +6 -7
- data/lib/rodauth/features/webauthn_verify_account.rb +1 -1
- data/lib/rodauth/migrations.rb +31 -5
- data/lib/rodauth/version.rb +1 -1
- metadata +55 -24
@@ -132,11 +132,16 @@ module Rodauth
|
|
132
132
|
opts = Hash[remember_cookie_options]
|
133
133
|
opts[:value] = "#{account_id}_#{convert_token_key(remember_key_value)}"
|
134
134
|
opts[:expires] = convert_timestamp(active_remember_key_ds.get(remember_deadline_column))
|
135
|
+
opts[:path] = "/" unless opts.key?(:path)
|
136
|
+
opts[:httponly] = true unless opts.key?(:httponly)
|
137
|
+
opts[:secure] = true unless opts.key?(:secure) || !request.ssl?
|
135
138
|
::Rack::Utils.set_cookie_header!(response.headers, remember_cookie_key, opts)
|
136
139
|
end
|
137
140
|
|
138
141
|
def forget_login
|
139
|
-
|
142
|
+
opts = Hash[remember_cookie_options]
|
143
|
+
opts[:path] = "/" unless opts.key?(:path)
|
144
|
+
::Rack::Utils.delete_cookie_header!(response.headers, remember_cookie_key, opts)
|
140
145
|
end
|
141
146
|
|
142
147
|
def get_remember_key
|
@@ -47,7 +47,6 @@ module Rodauth
|
|
47
47
|
:get_verify_account_key,
|
48
48
|
:get_verify_account_email_last_sent,
|
49
49
|
:remove_verify_account_key,
|
50
|
-
:resend_verify_account_view,
|
51
50
|
:send_verify_account_email,
|
52
51
|
:set_verify_account_email_last_sent,
|
53
52
|
:verify_account,
|
@@ -245,6 +244,12 @@ module Rodauth
|
|
245
244
|
end
|
246
245
|
end
|
247
246
|
|
247
|
+
def setup_account_verification
|
248
|
+
generate_verify_account_key_value
|
249
|
+
create_verify_account_key
|
250
|
+
send_verify_account_email
|
251
|
+
end
|
252
|
+
|
248
253
|
private
|
249
254
|
|
250
255
|
def _login_form_footer_links
|
@@ -276,12 +281,6 @@ module Rodauth
|
|
276
281
|
super
|
277
282
|
end
|
278
283
|
|
279
|
-
def setup_account_verification
|
280
|
-
generate_verify_account_key_value
|
281
|
-
create_verify_account_key
|
282
|
-
send_verify_account_email
|
283
|
-
end
|
284
|
-
|
285
284
|
def verify_account_check_already_logged_in
|
286
285
|
check_already_logged_in
|
287
286
|
end
|
@@ -29,7 +29,7 @@ module Rodauth
|
|
29
29
|
|
30
30
|
def before_verify_account
|
31
31
|
super
|
32
|
-
if features.include?(:
|
32
|
+
if features.include?(:json) && use_json? && !param_or_nil(webauthn_setup_param)
|
33
33
|
cred = new_webauthn_credential
|
34
34
|
json_response[webauthn_setup_param] = cred.as_json
|
35
35
|
json_response[webauthn_setup_challenge_param] = cred.challenge
|
data/lib/rodauth/migrations.rb
CHANGED
@@ -4,7 +4,8 @@ module Rodauth
|
|
4
4
|
def self.create_database_authentication_functions(db, opts={})
|
5
5
|
table_name = opts[:table_name] || :account_password_hashes
|
6
6
|
get_salt_name = opts[:get_salt_name] || :rodauth_get_salt
|
7
|
-
valid_hash_name = opts[:valid_hash_name] || :rodauth_valid_password_hash
|
7
|
+
valid_hash_name = opts[:valid_hash_name] || :rodauth_valid_password_hash
|
8
|
+
argon2 = opts[:argon2]
|
8
9
|
|
9
10
|
case db.database_type
|
10
11
|
when :postgres
|
@@ -14,12 +15,21 @@ module Rodauth
|
|
14
15
|
when 'uuid' then :uuid
|
15
16
|
else :int8
|
16
17
|
end
|
18
|
+
table_name = db.literal(table_name) unless table_name.is_a?(String)
|
17
19
|
|
20
|
+
argon_sql = <<END
|
21
|
+
CASE
|
22
|
+
WHEN password_hash ~ '^\\$argon2id'
|
23
|
+
THEN substring(password_hash from '\\$argon2id\\$v=\\d+\\$m=\\d+,t=\\d+,p=\\d+\\$.+\\$')
|
24
|
+
ELSE substr(password_hash, 0, 30)
|
25
|
+
END INTO salt
|
26
|
+
END
|
18
27
|
db.run <<END
|
19
28
|
CREATE OR REPLACE FUNCTION #{get_salt_name}(acct_id #{primary_key_type}) RETURNS text AS $$
|
20
29
|
DECLARE salt text;
|
21
30
|
BEGIN
|
22
|
-
SELECT
|
31
|
+
SELECT
|
32
|
+
#{argon2 ? argon_sql : "substr(password_hash, 0, 30) INTO salt"}
|
23
33
|
FROM #{table_name}
|
24
34
|
WHERE acct_id = id;
|
25
35
|
RETURN salt;
|
@@ -43,12 +53,20 @@ SECURITY DEFINER
|
|
43
53
|
SET search_path = #{search_path};
|
44
54
|
END
|
45
55
|
when :mysql
|
56
|
+
argon_sql = <<END
|
57
|
+
CASE
|
58
|
+
WHEN password_hash REGEXP '^.argon2id'
|
59
|
+
THEN left(password_hash, CHAR_LENGTH(password_hash) - INSTR(REVERSE(password_hash), '$'))
|
60
|
+
ELSE substr(password_hash, 1, 30)
|
61
|
+
END
|
62
|
+
END
|
46
63
|
db.run <<END
|
47
64
|
CREATE FUNCTION #{get_salt_name}(acct_id int8) RETURNS varchar(255)
|
48
65
|
SQL SECURITY DEFINER
|
49
66
|
READS SQL DATA
|
50
67
|
BEGIN
|
51
|
-
RETURN (SELECT
|
68
|
+
RETURN (SELECT
|
69
|
+
#{argon2 ? argon_sql : "substr(password_hash, 1, 30)"}
|
52
70
|
FROM #{table_name}
|
53
71
|
WHERE acct_id = id);
|
54
72
|
END;
|
@@ -71,13 +89,21 @@ RETURN valid;
|
|
71
89
|
END;
|
72
90
|
END
|
73
91
|
when :mssql
|
92
|
+
argon_sql = <<END
|
93
|
+
CASE
|
94
|
+
WHEN password_hash LIKE '[$]argon2id%'
|
95
|
+
THEN left(password_hash, len(password_hash) - charindex('$', reverse(password_hash)))
|
96
|
+
ELSE substring(password_hash, 0, 30)
|
97
|
+
END
|
98
|
+
END
|
74
99
|
db.run <<END
|
75
100
|
CREATE FUNCTION #{get_salt_name}(@account_id bigint) RETURNS nvarchar(255)
|
76
101
|
WITH EXECUTE AS OWNER
|
77
102
|
AS
|
78
103
|
BEGIN
|
79
104
|
DECLARE @salt nvarchar(255);
|
80
|
-
SELECT @salt =
|
105
|
+
SELECT @salt =
|
106
|
+
#{argon2 ? argon_sql : "substring(password_hash, 0, 30)"}
|
81
107
|
FROM #{table_name}
|
82
108
|
WHERE id = @account_id;
|
83
109
|
RETURN @salt;
|
@@ -107,7 +133,7 @@ END
|
|
107
133
|
def self.drop_database_authentication_functions(db, opts={})
|
108
134
|
table_name = opts[:table_name] || :account_password_hashes
|
109
135
|
get_salt_name = opts[:get_salt_name] || :rodauth_get_salt
|
110
|
-
valid_hash_name = opts[:valid_hash_name] || :rodauth_valid_password_hash
|
136
|
+
valid_hash_name = opts[:valid_hash_name] || :rodauth_valid_password_hash
|
111
137
|
|
112
138
|
case db.database_type
|
113
139
|
when :postgres
|
data/lib/rodauth/version.rb
CHANGED
metadata
CHANGED
@@ -1,14 +1,14 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: rodauth
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 2.
|
4
|
+
version: 2.10.0
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Jeremy Evans
|
8
8
|
autorequire:
|
9
9
|
bindir: bin
|
10
10
|
cert_chain: []
|
11
|
-
date:
|
11
|
+
date: 2021-02-22 00:00:00.000000000 Z
|
12
12
|
dependencies:
|
13
13
|
- !ruby/object:Gem::Dependency
|
14
14
|
name: sequel
|
@@ -80,6 +80,20 @@ dependencies:
|
|
80
80
|
- - ">="
|
81
81
|
- !ruby/object:Gem::Version
|
82
82
|
version: '0'
|
83
|
+
- !ruby/object:Gem::Dependency
|
84
|
+
name: argon2
|
85
|
+
requirement: !ruby/object:Gem::Requirement
|
86
|
+
requirements:
|
87
|
+
- - ">="
|
88
|
+
- !ruby/object:Gem::Version
|
89
|
+
version: '2'
|
90
|
+
type: :development
|
91
|
+
prerelease: false
|
92
|
+
version_requirements: !ruby/object:Gem::Requirement
|
93
|
+
requirements:
|
94
|
+
- - ">="
|
95
|
+
- !ruby/object:Gem::Version
|
96
|
+
version: '2'
|
83
97
|
- !ruby/object:Gem::Dependency
|
84
98
|
name: mail
|
85
99
|
requirement: !ruby/object:Gem::Requirement
|
@@ -140,14 +154,14 @@ dependencies:
|
|
140
154
|
name: webauthn
|
141
155
|
requirement: !ruby/object:Gem::Requirement
|
142
156
|
requirements:
|
143
|
-
- - "
|
157
|
+
- - ">="
|
144
158
|
- !ruby/object:Gem::Version
|
145
159
|
version: '2'
|
146
160
|
type: :development
|
147
161
|
prerelease: false
|
148
162
|
version_requirements: !ruby/object:Gem::Requirement
|
149
163
|
requirements:
|
150
|
-
- - "
|
164
|
+
- - ">="
|
151
165
|
- !ruby/object:Gem::Version
|
152
166
|
version: '2'
|
153
167
|
- !ruby/object:Gem::Dependency
|
@@ -237,28 +251,35 @@ extra_rdoc_files:
|
|
237
251
|
- README.rdoc
|
238
252
|
- CHANGELOG
|
239
253
|
- MIT-LICENSE
|
240
|
-
- doc/change_password_notify.rdoc
|
241
254
|
- doc/account_expiration.rdoc
|
255
|
+
- doc/active_sessions.rdoc
|
256
|
+
- doc/argon2.rdoc
|
257
|
+
- doc/audit_logging.rdoc
|
242
258
|
- doc/base.rdoc
|
243
259
|
- doc/change_login.rdoc
|
244
260
|
- doc/change_password.rdoc
|
245
|
-
- doc/
|
261
|
+
- doc/change_password_notify.rdoc
|
246
262
|
- doc/close_account.rdoc
|
247
|
-
- doc/
|
263
|
+
- doc/confirm_password.rdoc
|
248
264
|
- doc/create_account.rdoc
|
249
|
-
- doc/email_base.rdoc
|
250
265
|
- doc/disallow_common_passwords.rdoc
|
251
266
|
- doc/disallow_password_reuse.rdoc
|
252
|
-
- doc/
|
267
|
+
- doc/email_auth.rdoc
|
268
|
+
- doc/email_base.rdoc
|
269
|
+
- doc/http_basic_auth.rdoc
|
270
|
+
- doc/json.rdoc
|
253
271
|
- doc/jwt.rdoc
|
272
|
+
- doc/jwt_cors.rdoc
|
273
|
+
- doc/jwt_refresh.rdoc
|
254
274
|
- doc/lockout.rdoc
|
255
275
|
- doc/login.rdoc
|
276
|
+
- doc/login_password_requirements_base.rdoc
|
256
277
|
- doc/logout.rdoc
|
257
278
|
- doc/otp.rdoc
|
258
|
-
- doc/
|
259
|
-
- doc/jwt_cors.rdoc
|
279
|
+
- doc/password_complexity.rdoc
|
260
280
|
- doc/password_expiration.rdoc
|
261
281
|
- doc/password_grace_period.rdoc
|
282
|
+
- doc/password_pepper.rdoc
|
262
283
|
- doc/recovery_codes.rdoc
|
263
284
|
- doc/remember.rdoc
|
264
285
|
- doc/reset_password.rdoc
|
@@ -268,17 +289,11 @@ extra_rdoc_files:
|
|
268
289
|
- doc/two_factor_base.rdoc
|
269
290
|
- doc/update_password_hash.rdoc
|
270
291
|
- doc/verify_account.rdoc
|
271
|
-
- doc/email_auth.rdoc
|
272
|
-
- doc/jwt_refresh.rdoc
|
273
292
|
- doc/verify_account_grace_period.rdoc
|
274
293
|
- doc/verify_login_change.rdoc
|
275
294
|
- doc/webauthn.rdoc
|
276
295
|
- doc/webauthn_login.rdoc
|
277
296
|
- doc/webauthn_verify_account.rdoc
|
278
|
-
- doc/active_sessions.rdoc
|
279
|
-
- doc/audit_logging.rdoc
|
280
|
-
- doc/password_pepper.rdoc
|
281
|
-
- doc/release_notes/1.17.0.txt
|
282
297
|
- doc/release_notes/1.0.0.txt
|
283
298
|
- doc/release_notes/1.1.0.txt
|
284
299
|
- doc/release_notes/1.10.0.txt
|
@@ -288,7 +303,14 @@ extra_rdoc_files:
|
|
288
303
|
- doc/release_notes/1.14.0.txt
|
289
304
|
- doc/release_notes/1.15.0.txt
|
290
305
|
- doc/release_notes/1.16.0.txt
|
306
|
+
- doc/release_notes/1.17.0.txt
|
307
|
+
- doc/release_notes/1.18.0.txt
|
308
|
+
- doc/release_notes/1.19.0.txt
|
291
309
|
- doc/release_notes/1.2.0.txt
|
310
|
+
- doc/release_notes/1.20.0.txt
|
311
|
+
- doc/release_notes/1.21.0.txt
|
312
|
+
- doc/release_notes/1.22.0.txt
|
313
|
+
- doc/release_notes/1.23.0.txt
|
292
314
|
- doc/release_notes/1.3.0.txt
|
293
315
|
- doc/release_notes/1.4.0.txt
|
294
316
|
- doc/release_notes/1.5.0.txt
|
@@ -296,18 +318,17 @@ extra_rdoc_files:
|
|
296
318
|
- doc/release_notes/1.7.0.txt
|
297
319
|
- doc/release_notes/1.8.0.txt
|
298
320
|
- doc/release_notes/1.9.0.txt
|
299
|
-
- doc/release_notes/1.18.0.txt
|
300
|
-
- doc/release_notes/1.19.0.txt
|
301
|
-
- doc/release_notes/1.20.0.txt
|
302
|
-
- doc/release_notes/1.21.0.txt
|
303
|
-
- doc/release_notes/1.22.0.txt
|
304
|
-
- doc/release_notes/1.23.0.txt
|
305
321
|
- doc/release_notes/2.0.0.txt
|
306
322
|
- doc/release_notes/2.1.0.txt
|
323
|
+
- doc/release_notes/2.10.0.txt
|
307
324
|
- doc/release_notes/2.2.0.txt
|
308
325
|
- doc/release_notes/2.3.0.txt
|
309
326
|
- doc/release_notes/2.4.0.txt
|
310
327
|
- doc/release_notes/2.5.0.txt
|
328
|
+
- doc/release_notes/2.6.0.txt
|
329
|
+
- doc/release_notes/2.7.0.txt
|
330
|
+
- doc/release_notes/2.8.0.txt
|
331
|
+
- doc/release_notes/2.9.0.txt
|
311
332
|
files:
|
312
333
|
- CHANGELOG
|
313
334
|
- MIT-LICENSE
|
@@ -315,6 +336,7 @@ files:
|
|
315
336
|
- dict/top-10_000-passwords.txt
|
316
337
|
- doc/account_expiration.rdoc
|
317
338
|
- doc/active_sessions.rdoc
|
339
|
+
- doc/argon2.rdoc
|
318
340
|
- doc/audit_logging.rdoc
|
319
341
|
- doc/base.rdoc
|
320
342
|
- doc/change_login.rdoc
|
@@ -337,6 +359,7 @@ files:
|
|
337
359
|
- doc/guides/internals.rdoc
|
338
360
|
- doc/guides/links.rdoc
|
339
361
|
- doc/guides/login_return.rdoc
|
362
|
+
- doc/guides/migrate_password_hash_algorithm.rdoc
|
340
363
|
- doc/guides/password_column.rdoc
|
341
364
|
- doc/guides/password_confirmation.rdoc
|
342
365
|
- doc/guides/password_requirements.rdoc
|
@@ -349,6 +372,7 @@ files:
|
|
349
372
|
- doc/guides/status_column.rdoc
|
350
373
|
- doc/guides/totp_or_recovery.rdoc
|
351
374
|
- doc/http_basic_auth.rdoc
|
375
|
+
- doc/json.rdoc
|
352
376
|
- doc/jwt.rdoc
|
353
377
|
- doc/jwt_cors.rdoc
|
354
378
|
- doc/jwt_refresh.rdoc
|
@@ -388,10 +412,15 @@ files:
|
|
388
412
|
- doc/release_notes/1.9.0.txt
|
389
413
|
- doc/release_notes/2.0.0.txt
|
390
414
|
- doc/release_notes/2.1.0.txt
|
415
|
+
- doc/release_notes/2.10.0.txt
|
391
416
|
- doc/release_notes/2.2.0.txt
|
392
417
|
- doc/release_notes/2.3.0.txt
|
393
418
|
- doc/release_notes/2.4.0.txt
|
394
419
|
- doc/release_notes/2.5.0.txt
|
420
|
+
- doc/release_notes/2.6.0.txt
|
421
|
+
- doc/release_notes/2.7.0.txt
|
422
|
+
- doc/release_notes/2.8.0.txt
|
423
|
+
- doc/release_notes/2.9.0.txt
|
395
424
|
- doc/remember.rdoc
|
396
425
|
- doc/reset_password.rdoc
|
397
426
|
- doc/session_expiration.rdoc
|
@@ -411,6 +440,7 @@ files:
|
|
411
440
|
- lib/rodauth.rb
|
412
441
|
- lib/rodauth/features/account_expiration.rb
|
413
442
|
- lib/rodauth/features/active_sessions.rb
|
443
|
+
- lib/rodauth/features/argon2.rb
|
414
444
|
- lib/rodauth/features/audit_logging.rb
|
415
445
|
- lib/rodauth/features/base.rb
|
416
446
|
- lib/rodauth/features/change_login.rb
|
@@ -424,6 +454,7 @@ files:
|
|
424
454
|
- lib/rodauth/features/email_auth.rb
|
425
455
|
- lib/rodauth/features/email_base.rb
|
426
456
|
- lib/rodauth/features/http_basic_auth.rb
|
457
|
+
- lib/rodauth/features/json.rb
|
427
458
|
- lib/rodauth/features/jwt.rb
|
428
459
|
- lib/rodauth/features/jwt_cors.rb
|
429
460
|
- lib/rodauth/features/jwt_refresh.rb
|
@@ -535,7 +566,7 @@ required_rubygems_version: !ruby/object:Gem::Requirement
|
|
535
566
|
- !ruby/object:Gem::Version
|
536
567
|
version: '0'
|
537
568
|
requirements: []
|
538
|
-
rubygems_version: 3.
|
569
|
+
rubygems_version: 3.2.3
|
539
570
|
signing_key:
|
540
571
|
specification_version: 4
|
541
572
|
summary: Authentication and Account Management Framework for Rack Applications
|