hestia 0.2.0 → 0.3.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/.travis.yml +8 -0
- data/Gemfile.rails50 +6 -0
- data/Gemfile.rails51 +6 -0
- data/README.md +3 -1
- data/hestia.gemspec +1 -1
- data/lib/hestia.rb +6 -0
- data/lib/hestia/message_multi_verifier.rb +5 -0
- data/lib/hestia/railtie.rb +4 -6
- data/lib/hestia/signed_cookie_jar_extension.rb +1 -0
- data/lib/hestia/signed_cookie_jar_extension/action_pack_5.rb +41 -0
- data/lib/hestia/version.rb +1 -1
- data/spec/hestia/message_multi_verifier_spec.rb +7 -4
- data/spec/hestia/signed_cookie_jar_extension/action_pack_5_spec.rb +103 -0
- data/spec/support/fake_cookie_jar.rb +11 -0
- metadata +12 -5
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA1:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: b0f6ffbc2dc06c7139b927a99e5f477395d1802b
|
4
|
+
data.tar.gz: 414c8a89a1886f14f86f10431b2a4909ce07ff46
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: 3ec6e236bcda0203191b22bd4e5535684365c6bbf2d564a26e8126191a333fb6c419f5f6f03dbaddbfa3d0bb5b6e1cfb9dbab4a2985fa60c039ff342dc097cc0
|
7
|
+
data.tar.gz: 7dfe2db894bf9c5f194319f0a3a1d95851b932a0434fa7630bed2c9da23e35f9b6cbe0bc35aa9bbcf070f583b4a563f81fbc864f3abc262b0c4b310c216e6c67
|
data/.travis.yml
CHANGED
data/Gemfile.rails50
ADDED
data/Gemfile.rails51
ADDED
data/README.md
CHANGED
@@ -37,6 +37,8 @@ We currently support (& test against):
|
|
37
37
|
* Rails 3.2
|
38
38
|
* Rails 4.1
|
39
39
|
* Rails 4.2
|
40
|
+
* Rails 5.0
|
41
|
+
* Rails 5.1
|
40
42
|
|
41
43
|
Pull requests always welcome to support other versions!
|
42
44
|
|
@@ -61,7 +63,7 @@ You should already have `Rails.application.config.secret_token` set to a value (
|
|
61
63
|
|
62
64
|
*You can also set `config.deprecated_secret_token` to an array of strings to allow incoming cookies to be valid when signed with any of the secrets.*
|
63
65
|
|
64
|
-
### Rails 4.1, 4.2
|
66
|
+
### Rails 4.1, 4.2, 5.0, 5.1
|
65
67
|
|
66
68
|
Following the instructions for Rails 3.2 should work, but make sure you haven't set `config.secret_key_base` to a value otherwise Rails will take over and upgrade your cookies from signed to encrypted ones.
|
67
69
|
|
data/hestia.gemspec
CHANGED
@@ -21,7 +21,7 @@ Gem::Specification.new do |spec|
|
|
21
21
|
spec.required_ruby_version = '>= 2.0'
|
22
22
|
|
23
23
|
spec.add_runtime_dependency "rack"
|
24
|
-
spec.add_runtime_dependency "actionpack", ">= 3.2.21", "< 5.
|
24
|
+
spec.add_runtime_dependency "actionpack", ">= 3.2.21", "< 5.2.0"
|
25
25
|
|
26
26
|
spec.add_development_dependency "bundler", "~> 1.7"
|
27
27
|
spec.add_development_dependency "rake", "~> 10.0"
|
data/lib/hestia.rb
CHANGED
@@ -2,4 +2,10 @@ module Hestia
|
|
2
2
|
autoload :MessageMultiVerifier, "hestia/message_multi_verifier"
|
3
3
|
autoload :SignedCookieJarExtension, "hestia/signed_cookie_jar_extension"
|
4
4
|
autoload :VERSION, "hestia/version"
|
5
|
+
|
6
|
+
def self.check_secret_key_base
|
7
|
+
if Rails.application.config.respond_to?(:secret_key_base) && Rails.application.config.secret_key_base
|
8
|
+
fail "Having `config.secret_token' and `config.secret_key_base' defined is not allowed in Hestia. Please refer to Hestia's Readme for more information."
|
9
|
+
end
|
10
|
+
end
|
5
11
|
end
|
@@ -1,4 +1,5 @@
|
|
1
1
|
require "active_support/message_verifier"
|
2
|
+
require "active_support/message_encryptor"
|
2
3
|
|
3
4
|
module Hestia
|
4
5
|
class MessageMultiVerifier
|
@@ -40,6 +41,10 @@ module Hestia
|
|
40
41
|
# Returns deserialized value
|
41
42
|
# Raises ActiveSupport::MessageVerifier::InvalidSignature
|
42
43
|
def verify(signed_message)
|
44
|
+
verified(signed_message)
|
45
|
+
end
|
46
|
+
|
47
|
+
def verified(signed_message)
|
43
48
|
errored_verifier_count = 0
|
44
49
|
|
45
50
|
# Make sure we check *all* verifiers, every time we're called, to prevent timing attacks.
|
data/lib/hestia/railtie.rb
CHANGED
@@ -11,13 +11,11 @@ module Hestia
|
|
11
11
|
when 3
|
12
12
|
Hestia::SignedCookieJarExtension::ActionPack3
|
13
13
|
when 4
|
14
|
-
|
15
|
-
fail "Having `config.secret_token' and `config.secret_key_base' defined is not allowed in Hestia. Please refer to Hestia's Readme for more information."
|
16
|
-
end
|
17
|
-
|
14
|
+
Hestia.check_secret_key_base
|
18
15
|
Hestia::SignedCookieJarExtension::ActionPack4
|
19
|
-
|
20
|
-
|
16
|
+
when 5
|
17
|
+
Hestia.check_secret_key_base
|
18
|
+
Hestia::SignedCookieJarExtension::ActionPack5
|
21
19
|
end
|
22
20
|
|
23
21
|
ActionDispatch::Cookies::SignedCookieJar.prepend(extension)
|
@@ -2,5 +2,6 @@ module Hestia
|
|
2
2
|
module SignedCookieJarExtension
|
3
3
|
autoload :ActionPack3, "hestia/signed_cookie_jar_extension/action_pack_3"
|
4
4
|
autoload :ActionPack4, "hestia/signed_cookie_jar_extension/action_pack_4"
|
5
|
+
autoload :ActionPack5, "hestia/signed_cookie_jar_extension/action_pack_5"
|
5
6
|
end
|
6
7
|
end
|
@@ -0,0 +1,41 @@
|
|
1
|
+
require 'active_support/version'
|
2
|
+
|
3
|
+
module Hestia
|
4
|
+
module SignedCookieJarExtension
|
5
|
+
module ActionPack5
|
6
|
+
# Public: overridden #initialize method
|
7
|
+
#
|
8
|
+
# In rails, `secrets' will be given the value of `Rails.application.config.secret_token'. That's the current secret token.
|
9
|
+
# This also reads from `Rails.application.config.deprecated_secret_token` for deprecated token(s) to use. It can be undefined, a
|
10
|
+
# string or an array of string.
|
11
|
+
#
|
12
|
+
# parent_jar [ActionDispatch::Cookies] the parent jar creating this signed cookie jar
|
13
|
+
# secret [String] current secret token. Used to verify & sign cookies.
|
14
|
+
#
|
15
|
+
def initialize(parent_jar)
|
16
|
+
super
|
17
|
+
|
18
|
+
# Find the deprecated secrets, if there are any
|
19
|
+
deprecated_secrets = if Rails.application.config.respond_to?(:deprecated_secret_token)
|
20
|
+
# This could be a single string!
|
21
|
+
Array(Rails.application.config.deprecated_secret_token)
|
22
|
+
else
|
23
|
+
[]
|
24
|
+
end
|
25
|
+
|
26
|
+
# Grab the `config.secret_token` value from its generator
|
27
|
+
active_secret = key_generator.generate_key(request.signed_cookie_salt)
|
28
|
+
|
29
|
+
# Take the deprecated secrets through the same generator code
|
30
|
+
deprecated_secrets.map do |secret|
|
31
|
+
ActiveSupport::LegacyKeyGenerator.new(secret).generate_key(request.signed_cookie_salt)
|
32
|
+
end
|
33
|
+
|
34
|
+
serializer = ActiveSupport.version.to_s > "4.1" ? ActiveSupport::MessageEncryptor::NullSerializer : ActionDispatch::Cookies::NullSerializer
|
35
|
+
|
36
|
+
# Finally, override @verifier with our own multi verifier containing all the secrets
|
37
|
+
@verifier = Hestia::MessageMultiVerifier.new(current_secret: active_secret, deprecated_secrets: deprecated_secrets, options: {serializer: serializer})
|
38
|
+
end
|
39
|
+
end
|
40
|
+
end
|
41
|
+
end
|
data/lib/hestia/version.rb
CHANGED
@@ -1,4 +1,5 @@
|
|
1
1
|
require_relative "../spec_helper"
|
2
|
+
require "action_pack/version"
|
2
3
|
|
3
4
|
module Hestia
|
4
5
|
describe MessageMultiVerifier do
|
@@ -91,11 +92,13 @@ module Hestia
|
|
91
92
|
multi_verifier.verify(legacy_cookie).must_equal "cookie dough"
|
92
93
|
end
|
93
94
|
|
94
|
-
|
95
|
-
|
95
|
+
if ActionPack::VERSION::MAJOR < 5
|
96
|
+
it "verifies a message of `nil' successfully" do
|
97
|
+
nil_cookie = singular_verifier.generate(nil)
|
96
98
|
|
97
|
-
|
98
|
-
|
99
|
+
singular_verifier.verify(nil_cookie).must_equal(nil)
|
100
|
+
multi_verifier.verify(nil_cookie).must_equal(nil)
|
101
|
+
end
|
99
102
|
end
|
100
103
|
|
101
104
|
it "verifies successfully when using custom digest" do
|
@@ -0,0 +1,103 @@
|
|
1
|
+
require_relative "../../spec_helper"
|
2
|
+
require_relative "../../support/fake_rails"
|
3
|
+
require_relative "../../support/fake_cookie_jar"
|
4
|
+
require "action_dispatch/middleware/cookies"
|
5
|
+
|
6
|
+
# Call our railtie block to setup the initializers array
|
7
|
+
require "hestia/railtie"
|
8
|
+
|
9
|
+
module Hestia
|
10
|
+
if ActionPack::VERSION::MAJOR == 5
|
11
|
+
describe SignedCookieJarExtension::ActionPack5 do
|
12
|
+
before do
|
13
|
+
Rails.clean
|
14
|
+
load_railtie
|
15
|
+
end
|
16
|
+
|
17
|
+
it "is prepended into signed cookie jar ancestors" do
|
18
|
+
ActionDispatch::Cookies::SignedCookieJar.ancestors.first.must_equal SignedCookieJarExtension::ActionPack5
|
19
|
+
end
|
20
|
+
|
21
|
+
it "defines initialize" do
|
22
|
+
# #initialize doesn't show up in {instance_,}methods({false,true}) for some reason, so do this instead
|
23
|
+
# This will throw a NameError if we don't define it
|
24
|
+
SignedCookieJarExtension::ActionPack5.instance_method(:initialize)
|
25
|
+
end
|
26
|
+
|
27
|
+
describe "signed cookie jar instance with no deprecated token" do
|
28
|
+
before do
|
29
|
+
@secret = "a" * 30
|
30
|
+
@parent_jar = FakeCookieJar.new(@secret)
|
31
|
+
@jar = ActionDispatch::Cookies::SignedCookieJar.new(@parent_jar)
|
32
|
+
end
|
33
|
+
|
34
|
+
it "calls the original initialize method" do
|
35
|
+
@jar.instance_variable_get(:@parent_jar).must_equal @parent_jar
|
36
|
+
end
|
37
|
+
|
38
|
+
describe "validator" do
|
39
|
+
before do
|
40
|
+
@verifier = @jar.instance_variable_get(:@verifier)
|
41
|
+
end
|
42
|
+
it "is a multi message validator" do
|
43
|
+
@verifier.must_be_kind_of(MessageMultiVerifier)
|
44
|
+
end
|
45
|
+
|
46
|
+
it "has the correct secrets stored" do
|
47
|
+
secrets = @verifier.instance_variable_get(:@verifiers).map { |x| x.instance_variable_get(:@secret) }
|
48
|
+
secrets.must_equal [@secret]
|
49
|
+
end
|
50
|
+
end
|
51
|
+
end
|
52
|
+
|
53
|
+
describe "signed cookie jar instance with deprecated token" do
|
54
|
+
before do
|
55
|
+
@secret = "a" * 30
|
56
|
+
@parent_jar = FakeCookieJar.new(@secret)
|
57
|
+
@deprecated_secret = "b" * 30
|
58
|
+
Rails.application.config.deprecated_secret_token = @deprecated_secret
|
59
|
+
@jar = ActionDispatch::Cookies::SignedCookieJar.new(@parent_jar)
|
60
|
+
end
|
61
|
+
|
62
|
+
it "calls the original initialize method" do
|
63
|
+
@jar.instance_variable_get(:@parent_jar).must_equal @parent_jar
|
64
|
+
end
|
65
|
+
|
66
|
+
describe "validator" do
|
67
|
+
before do
|
68
|
+
@verifier = @jar.instance_variable_get(:@verifier)
|
69
|
+
end
|
70
|
+
it "is a multi message validator" do
|
71
|
+
@verifier.must_be_kind_of(MessageMultiVerifier)
|
72
|
+
end
|
73
|
+
|
74
|
+
it "has the correct secrets stored" do
|
75
|
+
secrets = @verifier.instance_variable_get(:@verifiers).map { |x| x.instance_variable_get(:@secret) }
|
76
|
+
secrets.must_equal [@secret, @deprecated_secret]
|
77
|
+
end
|
78
|
+
end
|
79
|
+
end
|
80
|
+
|
81
|
+
describe "with secret_key_base defined in config" do
|
82
|
+
it "blows up" do
|
83
|
+
Rails.clean
|
84
|
+
|
85
|
+
Rails.application.config.secret_token = "a" * 64
|
86
|
+
Rails.application.config.secret_key_base = "b" * 64
|
87
|
+
|
88
|
+
-> { load_railtie }.must_raise(RuntimeError)
|
89
|
+
end
|
90
|
+
end
|
91
|
+
|
92
|
+
private
|
93
|
+
|
94
|
+
def load_railtie
|
95
|
+
if (init = Rails::Railtie.initializers.first)
|
96
|
+
_, _, block = init
|
97
|
+
block.call
|
98
|
+
end
|
99
|
+
end
|
100
|
+
|
101
|
+
end
|
102
|
+
end
|
103
|
+
end
|
@@ -0,0 +1,11 @@
|
|
1
|
+
class FakeCookieJar
|
2
|
+
attr_reader :request, :key_generator, :signed_cookie_salt, :cookies_digest
|
3
|
+
|
4
|
+
def initialize(secret)
|
5
|
+
@secret = secret
|
6
|
+
@request = self
|
7
|
+
@signed_cookie_salt = nil
|
8
|
+
@cookies_digest = nil
|
9
|
+
@key_generator = ActiveSupport::LegacyKeyGenerator.new(@secret)
|
10
|
+
end
|
11
|
+
end
|
metadata
CHANGED
@@ -1,14 +1,14 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: hestia
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 0.
|
4
|
+
version: 0.3.0
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Caius Durling
|
8
8
|
autorequire:
|
9
9
|
bindir: bin
|
10
10
|
cert_chain: []
|
11
|
-
date:
|
11
|
+
date: 2017-11-30 00:00:00.000000000 Z
|
12
12
|
dependencies:
|
13
13
|
- !ruby/object:Gem::Dependency
|
14
14
|
name: rack
|
@@ -33,7 +33,7 @@ dependencies:
|
|
33
33
|
version: 3.2.21
|
34
34
|
- - "<"
|
35
35
|
- !ruby/object:Gem::Version
|
36
|
-
version: 5.
|
36
|
+
version: 5.2.0
|
37
37
|
type: :runtime
|
38
38
|
prerelease: false
|
39
39
|
version_requirements: !ruby/object:Gem::Requirement
|
@@ -43,7 +43,7 @@ dependencies:
|
|
43
43
|
version: 3.2.21
|
44
44
|
- - "<"
|
45
45
|
- !ruby/object:Gem::Version
|
46
|
-
version: 5.
|
46
|
+
version: 5.2.0
|
47
47
|
- !ruby/object:Gem::Dependency
|
48
48
|
name: bundler
|
49
49
|
requirement: !ruby/object:Gem::Requirement
|
@@ -100,6 +100,8 @@ files:
|
|
100
100
|
- Gemfile.rails3
|
101
101
|
- Gemfile.rails41
|
102
102
|
- Gemfile.rails42
|
103
|
+
- Gemfile.rails50
|
104
|
+
- Gemfile.rails51
|
103
105
|
- LICENSE.txt
|
104
106
|
- README.md
|
105
107
|
- Rakefile
|
@@ -111,12 +113,15 @@ files:
|
|
111
113
|
- lib/hestia/signed_cookie_jar_extension.rb
|
112
114
|
- lib/hestia/signed_cookie_jar_extension/action_pack_3.rb
|
113
115
|
- lib/hestia/signed_cookie_jar_extension/action_pack_4.rb
|
116
|
+
- lib/hestia/signed_cookie_jar_extension/action_pack_5.rb
|
114
117
|
- lib/hestia/version.rb
|
115
118
|
- spec/hestia/message_multi_verifier_spec.rb
|
116
119
|
- spec/hestia/railtie_spec.rb
|
117
120
|
- spec/hestia/signed_cookie_jar_extension/action_pack_3_spec.rb
|
118
121
|
- spec/hestia/signed_cookie_jar_extension/action_pack_4_spec.rb
|
122
|
+
- spec/hestia/signed_cookie_jar_extension/action_pack_5_spec.rb
|
119
123
|
- spec/spec_helper.rb
|
124
|
+
- spec/support/fake_cookie_jar.rb
|
120
125
|
- spec/support/fake_rails.rb
|
121
126
|
homepage: https://github.com/fac/hestia
|
122
127
|
licenses:
|
@@ -138,7 +143,7 @@ required_rubygems_version: !ruby/object:Gem::Requirement
|
|
138
143
|
version: '0'
|
139
144
|
requirements: []
|
140
145
|
rubyforge_project:
|
141
|
-
rubygems_version: 2.6.
|
146
|
+
rubygems_version: 2.6.13
|
142
147
|
signing_key:
|
143
148
|
specification_version: 4
|
144
149
|
summary: Support for deprecating/rotating signed cookie secret tokens in rails
|
@@ -147,5 +152,7 @@ test_files:
|
|
147
152
|
- spec/hestia/railtie_spec.rb
|
148
153
|
- spec/hestia/signed_cookie_jar_extension/action_pack_3_spec.rb
|
149
154
|
- spec/hestia/signed_cookie_jar_extension/action_pack_4_spec.rb
|
155
|
+
- spec/hestia/signed_cookie_jar_extension/action_pack_5_spec.rb
|
150
156
|
- spec/spec_helper.rb
|
157
|
+
- spec/support/fake_cookie_jar.rb
|
151
158
|
- spec/support/fake_rails.rb
|