chamber 2.12.2 → 2.14.0

Sign up to get free protection for your applications and to get access to all the features.
Files changed (58) hide show
  1. checksums.yaml +5 -5
  2. checksums.yaml.gz.sig +0 -0
  3. data.tar.gz.sig +2 -2
  4. data/README.md +101 -26
  5. data/lib/chamber.rb +72 -10
  6. data/lib/chamber/adapters/cloud/circle_ci.rb +85 -0
  7. data/lib/chamber/adapters/cloud/heroku.rb +74 -0
  8. data/lib/chamber/binary/circle_ci.rb +122 -0
  9. data/lib/chamber/binary/heroku.rb +45 -16
  10. data/lib/chamber/binary/runner.rb +42 -26
  11. data/lib/chamber/binary/travis.rb +5 -3
  12. data/lib/chamber/commands/base.rb +10 -16
  13. data/lib/chamber/commands/cloud/base.rb +35 -0
  14. data/lib/chamber/commands/{heroku → cloud}/clear.rb +6 -8
  15. data/lib/chamber/commands/cloud/compare.rb +26 -0
  16. data/lib/chamber/commands/cloud/pull.rb +29 -0
  17. data/lib/chamber/commands/cloud/push.rb +44 -0
  18. data/lib/chamber/commands/comparable.rb +2 -2
  19. data/lib/chamber/commands/compare.rb +6 -9
  20. data/lib/chamber/commands/initialize.rb +26 -22
  21. data/lib/chamber/commands/securable.rb +10 -10
  22. data/lib/chamber/commands/secure.rb +2 -2
  23. data/lib/chamber/commands/show.rb +8 -8
  24. data/lib/chamber/commands/sign.rb +2 -2
  25. data/lib/chamber/commands/verify.rb +2 -2
  26. data/lib/chamber/configuration.rb +8 -3
  27. data/lib/chamber/context_resolver.rb +16 -7
  28. data/lib/chamber/encryption_methods/ssl.rb +21 -12
  29. data/lib/chamber/errors/environment_conversion.rb +8 -0
  30. data/lib/chamber/file.rb +22 -20
  31. data/lib/chamber/file_set.rb +21 -11
  32. data/lib/chamber/files/signature.rb +31 -23
  33. data/lib/chamber/filters/decryption_filter.rb +13 -11
  34. data/lib/chamber/filters/encryption_filter.rb +17 -8
  35. data/lib/chamber/filters/environment_filter.rb +21 -10
  36. data/lib/chamber/filters/failed_decryption_filter.rb +6 -6
  37. data/lib/chamber/filters/insecure_filter.rb +12 -3
  38. data/lib/chamber/filters/namespace_filter.rb +5 -5
  39. data/lib/chamber/filters/secure_filter.rb +5 -5
  40. data/lib/chamber/filters/translate_secure_keys_filter.rb +5 -5
  41. data/lib/chamber/instance.rb +48 -32
  42. data/lib/chamber/integrations/rails.rb +1 -1
  43. data/lib/chamber/integrations/sinatra.rb +6 -6
  44. data/lib/chamber/key_pair.rb +8 -8
  45. data/lib/chamber/keys/base.rb +35 -41
  46. data/lib/chamber/keys/decryption.rb +8 -14
  47. data/lib/chamber/keys/encryption.rb +8 -14
  48. data/lib/chamber/namespace_set.rb +2 -4
  49. data/lib/chamber/settings.rb +58 -54
  50. data/lib/chamber/types/secured.rb +8 -10
  51. data/lib/chamber/version.rb +1 -1
  52. data/templates/settings.yml +2 -0
  53. metadata +52 -41
  54. metadata.gz.sig +0 -0
  55. data/lib/chamber/commands/heroku.rb +0 -31
  56. data/lib/chamber/commands/heroku/compare.rb +0 -33
  57. data/lib/chamber/commands/heroku/pull.rb +0 -30
  58. data/lib/chamber/commands/heroku/push.rb +0 -27
@@ -112,19 +112,28 @@ require 'chamber/settings'
112
112
  #
113
113
  module Chamber
114
114
  class FileSet
115
- attr_reader :namespaces,
116
- :paths
117
115
  attr_accessor :decryption_keys,
118
116
  :encryption_keys,
119
- :basepath
117
+ :basepath,
118
+ :signature_name
119
+ attr_reader :namespaces,
120
+ :paths
120
121
 
121
- def initialize(options = {})
122
- self.namespaces = options[:namespaces] || {}
123
- self.decryption_keys = options[:decryption_keys]
124
- self.encryption_keys = options[:encryption_keys]
125
- self.paths = options.fetch(:files)
126
- self.basepath = options[:basepath]
122
+ # rubocop:disable Metrics/ParameterLists
123
+ def initialize(files:,
124
+ basepath: nil,
125
+ decryption_keys: nil,
126
+ encryption_keys: nil,
127
+ namespaces: {},
128
+ signature_name: nil)
129
+ self.basepath = basepath
130
+ self.decryption_keys = decryption_keys
131
+ self.encryption_keys = encryption_keys
132
+ self.namespaces = namespaces
133
+ self.paths = files
134
+ self.signature_name = signature_name
127
135
  end
136
+ # rubocop:enable Metrics/ParameterLists
128
137
 
129
138
  ###
130
139
  # Internal: Returns an Array of the ordered list of files that was processed
@@ -234,7 +243,8 @@ class FileSet
234
243
  File.new(path: file,
235
244
  namespaces: namespaces,
236
245
  decryption_keys: decryption_keys,
237
- encryption_keys: encryption_keys)
246
+ encryption_keys: encryption_keys,
247
+ signature_name: signature_name)
238
248
  end
239
249
 
240
250
  sorted_relevant_files += relevant_glob_files
@@ -247,7 +257,7 @@ class FileSet
247
257
  private
248
258
 
249
259
  def all_files
250
- @all_files ||= file_globs.map { |fg| Pathname.glob(fg) }.flatten.uniq.sort
260
+ @all_files ||= file_globs.map { |fg| Pathname.glob(fg) }.flatten.uniq.sort # rubocop:disable Performance/ChainArrayAllocation
251
261
  end
252
262
 
253
263
  def non_namespaced_files
@@ -7,35 +7,43 @@ require 'time'
7
7
  module Chamber
8
8
  module Files
9
9
  class Signature
10
- SIGNATURE_HEADER = '-----BEGIN CHAMBER SIGNATURE-----'
11
- SIGNATURE_FOOTER = '-----END CHAMBER SIGNATURE-----'
12
- SIGNATURE_IN_SIGNATURE_FILE_PATTERN = /#{SIGNATURE_HEADER}\n(.*)\n#{SIGNATURE_FOOTER}/
10
+ SIGNATURE_HEADER = '-----BEGIN CHAMBER SIGNATURE-----'
11
+ SIGNATURE_HEADER_PATTERN = /-----BEGIN\sCHAMBER\sSIGNATURE-----/.freeze
12
+ SIGNATURE_FOOTER = '-----END CHAMBER SIGNATURE-----'
13
+ SIGNATURE_FOOTER_PATTERN = /-----END\sCHAMBER\sSIGNATURE-----/.freeze
14
+ SIGNATURE_IN_FILE_PATTERN = /
15
+ #{SIGNATURE_HEADER_PATTERN}\n # Header
16
+ (.*)\n # Signature Body
17
+ #{SIGNATURE_FOOTER_PATTERN} # Footer
18
+ /x.freeze
13
19
 
14
20
  attr_accessor :settings_content,
15
- :settings_filename
21
+ :settings_filename,
22
+ :signature_name
16
23
 
17
24
  attr_reader :signature_key
18
25
 
19
- def initialize(settings_filename, settings_content, signature_key)
26
+ def initialize(settings_filename, settings_content, signature_key, signature_name)
20
27
  self.signature_key = signature_key
21
28
  self.settings_content = settings_content
22
29
  self.settings_filename = Pathname.new(settings_filename)
30
+ self.signature_name = signature_name
23
31
  end
24
32
 
25
33
  def signature_key=(keyish)
26
- @signature_key ||= if keyish.is_a?(OpenSSL::PKey::RSA)
27
- keyish
28
- elsif ::File.readable?(::File.expand_path(keyish))
29
- file_contents = ::File.read(::File.expand_path(keyish))
30
- OpenSSL::PKey::RSA.new(file_contents)
31
- else
32
- OpenSSL::PKey::RSA.new(keyish)
33
- end
34
+ @signature_key = if keyish.is_a?(OpenSSL::PKey::RSA)
35
+ keyish
36
+ elsif ::File.readable?(::File.expand_path(keyish))
37
+ file_contents = ::File.read(::File.expand_path(keyish))
38
+ OpenSSL::PKey::RSA.new(file_contents)
39
+ else
40
+ OpenSSL::PKey::RSA.new(keyish)
41
+ end
34
42
  end
35
43
 
36
44
  def write
37
45
  signature_filename.write(<<-HEREDOC, 0, mode: 'w+')
38
- Signed By: #{`git config --get 'user.name'`.chomp}
46
+ Signed By: #{signature_name}
39
47
  Signed At: #{Time.now.utc.iso8601}
40
48
 
41
49
  #{SIGNATURE_HEADER}
@@ -55,20 +63,20 @@ Signed At: #{Time.now.utc.iso8601}
55
63
  end
56
64
 
57
65
  def raw_signature
58
- @raw_signature ||= signature_key.
59
- sign(digest, settings_content)
66
+ @raw_signature ||= signature_key
67
+ .sign(digest, settings_content)
60
68
  end
61
69
 
62
70
  def signature_filename
63
- @signature_filename ||= settings_filename.
64
- sub('.yml', '.sig').
65
- sub('.erb', '')
71
+ @signature_filename ||= settings_filename
72
+ .sub('.yml', '.sig')
73
+ .sub('.erb', '')
66
74
  end
67
75
 
68
76
  def encoded_signature_content
69
- @encoded_signature_content ||= signature_filename.
70
- read.
71
- match(SIGNATURE_IN_SIGNATURE_FILE_PATTERN) do |match|
77
+ @encoded_signature_content ||= signature_filename
78
+ .read
79
+ .match(SIGNATURE_IN_FILE_PATTERN) do |match|
72
80
  match[1]
73
81
  end
74
82
  end
@@ -78,7 +86,7 @@ Signed At: #{Time.now.utc.iso8601}
78
86
  end
79
87
 
80
88
  def digest
81
- @digest ||= OpenSSL::Digest::SHA512.new
89
+ @digest ||= OpenSSL::Digest.new('SHA512')
82
90
  end
83
91
  end
84
92
  end
@@ -12,35 +12,35 @@ require 'chamber/errors/decryption_failure'
12
12
  module Chamber
13
13
  module Filters
14
14
  class DecryptionFilter
15
- BASE64_STRING_PATTERN = %r{\A[A-Za-z0-9\+/]{342}==\z}
15
+ BASE64_STRING_PATTERN = %r{\A[A-Za-z0-9+/]{342}==\z}.freeze
16
16
  LARGE_DATA_STRING_PATTERN = %r{
17
17
  \A # Beginning of String
18
18
  (
19
- [A-Za-z0-9\+\/#]*\={0,2} # Base64 Encoded Key
19
+ [A-Za-z0-9+/#]*={0,2} # Base64 Encoded Key
20
20
  )
21
21
  \# # Separator
22
22
  (
23
- [A-Za-z0-9\+\/#]*\={0,2} # Base64 Encoded IV
23
+ [A-Za-z0-9+/#]*={0,2} # Base64 Encoded IV
24
24
  )
25
25
  \# # Separator
26
26
  (
27
- [A-Za-z0-9\+\/#]*\={0,2} # Base64 Encoded Data
27
+ [A-Za-z0-9+/#]*={0,2} # Base64 Encoded Data
28
28
  )
29
29
  \z # End of String
30
- }x
30
+ }x.freeze
31
31
 
32
32
  attr_accessor :data,
33
33
  :secure_key_token
34
34
  attr_reader :decryption_keys
35
35
 
36
- def initialize(options = {})
37
- self.decryption_keys = options.fetch(:decryption_keys, {}) || {}
38
- self.data = options.fetch(:data).dup
39
- self.secure_key_token = /\A#{Regexp.escape(options.fetch(:secure_key_prefix))}/
36
+ def initialize(data:, secure_key_prefix:, decryption_keys: {}, **_args)
37
+ self.decryption_keys = decryption_keys || {}
38
+ self.data = data.dup
39
+ self.secure_key_token = /\A#{Regexp.escape(secure_key_prefix)}/
40
40
  end
41
41
 
42
- def self.execute(options = {})
43
- new(options).__send__(:execute)
42
+ def self.execute(**args)
43
+ new(**args).__send__(:execute)
44
44
  end
45
45
 
46
46
  protected
@@ -75,6 +75,7 @@ class DecryptionFilter
75
75
 
76
76
  private
77
77
 
78
+ # rubocop:disable Style/RedundantBegin
78
79
  def decrypt(key, value)
79
80
  method = decryption_method(value)
80
81
 
@@ -88,6 +89,7 @@ class DecryptionFilter
88
89
 
89
90
  value
90
91
  end
92
+ # rubocop:enable Style/RedundantBegin
91
93
 
92
94
  def decryption_method(value)
93
95
  if value.respond_to?(:match)
@@ -10,21 +10,30 @@ require 'chamber/encryption_methods/none'
10
10
  module Chamber
11
11
  module Filters
12
12
  class EncryptionFilter
13
- BASE64_STRING_PATTERN = %r{\A[A-Za-z0-9\+\/]{342}==\z}
14
- LARGE_DATA_STRING_PATTERN = %r{\A([A-Za-z0-9\+\/#]*\={0,2})#([A-Za-z0-9\+\/#]*\={0,2})#([A-Za-z0-9\+\/#]*\={0,2})\z} # rubocop:disable Metrics/LineLength
13
+ BASE64_STRING_PATTERN = %r{\A[A-Za-z0-9+/]{342}==\z}.freeze
14
+ BASE64_SUBSTRING_PATTERN = %r{[A-Za-z0-9+/#]*={0,2}}.freeze
15
+ LARGE_DATA_STRING_PATTERN = /
16
+ \A
17
+ (#{BASE64_SUBSTRING_PATTERN})
18
+ \#
19
+ (#{BASE64_SUBSTRING_PATTERN})
20
+ \#
21
+ (#{BASE64_SUBSTRING_PATTERN})
22
+ \z
23
+ /x.freeze
15
24
 
16
25
  attr_accessor :data,
17
26
  :secure_key_token
18
27
  attr_reader :encryption_keys
19
28
 
20
- def initialize(options = {})
21
- self.encryption_keys = options.fetch(:encryption_keys, {}) || {}
22
- self.data = options.fetch(:data).dup
23
- self.secure_key_token = /\A#{Regexp.escape(options.fetch(:secure_key_prefix))}/
29
+ def initialize(data:, secure_key_prefix:, encryption_keys: {}, **_args)
30
+ self.encryption_keys = encryption_keys || {}
31
+ self.data = data.dup
32
+ self.secure_key_token = /\A#{Regexp.escape(secure_key_prefix)}/
24
33
  end
25
34
 
26
- def self.execute(options = {})
27
- new(options).__send__(:execute)
35
+ def self.execute(**args)
36
+ new(**args).__send__(:execute)
28
37
  end
29
38
 
30
39
  protected
@@ -3,6 +3,8 @@
3
3
  require 'yaml'
4
4
  require 'hashie/mash'
5
5
 
6
+ require 'chamber/errors/environment_conversion'
7
+
6
8
  module Chamber
7
9
  module Filters
8
10
  class EnvironmentFilter
@@ -86,16 +88,16 @@ class EnvironmentFilter
86
88
  # }
87
89
  #
88
90
  #
89
- def self.execute(options = {})
90
- new(options).__send__(:execute)
91
+ def self.execute(**args)
92
+ new(**args).__send__(:execute)
91
93
  end
92
94
 
93
95
  attr_accessor :data,
94
96
  :secure_key_token
95
97
 
96
- def initialize(options = {})
97
- self.data = options.fetch(:data)
98
- self.secure_key_token = /\A#{Regexp.escape(options.fetch(:secure_key_prefix))}/
98
+ def initialize(data:, secure_key_prefix:, **_args)
99
+ self.data = data
100
+ self.secure_key_token = /\A#{Regexp.escape(secure_key_prefix)}/
99
101
  end
100
102
 
101
103
  protected
@@ -108,7 +110,9 @@ class EnvironmentFilter
108
110
  { key => execute(value, environment_keys) }
109
111
  end,
110
112
  lambda do |key, value, environment_key|
111
- { key => convert_environment_value(ENV[environment_key], value) }
113
+ { key => convert_environment_value(environment_key,
114
+ ENV[environment_key],
115
+ value) }
112
116
  end,
113
117
  )
114
118
  end
@@ -134,8 +138,7 @@ class EnvironmentFilter
134
138
  environment_hash
135
139
  end
136
140
 
137
- # rubocop:disable Metrics/CyclomaticComplexity
138
- def convert_environment_value(environment_value, settings_value)
141
+ def convert_environment_value(environment_key, environment_value, settings_value) # rubocop:disable Metrics/CyclomaticComplexity, Metrics/AbcSize
139
142
  return settings_value unless environment_value
140
143
  return if %w{___nil___ ___null___}.include?(environment_value)
141
144
 
@@ -159,13 +162,21 @@ class EnvironmentFilter
159
162
  fail ArgumentError, "Invalid value for Array: #{environment_value}"
160
163
  end
161
164
  end
162
- when 'Integer'
165
+ when 'Fixnum', 'Integer'
163
166
  Integer(environment_value)
164
167
  else
165
168
  environment_value
166
169
  end
170
+ rescue ArgumentError
171
+ raise Chamber::Errors::EnvironmentConversion, <<-HEREDOC
172
+ We attempted to convert '#{environment_key}' from '#{environment_value}' to a '#{settings_value.class.name}'.
173
+
174
+ Unfortunately, this did not go as planned. Please either verify that your value is convertable
175
+ or change the original YAML value to be something more generic (like a String).
176
+
177
+ For more information, see https://github.com/thekompanee/chamber/wiki/Environment-Variable-Coercions
178
+ HEREDOC
167
179
  end
168
- # rubocop:enable Metrics/CyclomaticComplexity
169
180
  end
170
181
  end
171
182
  end
@@ -5,18 +5,18 @@ require 'chamber/errors/decryption_failure'
5
5
  module Chamber
6
6
  module Filters
7
7
  class FailedDecryptionFilter
8
- BASE64_STRING_PATTERN = %r{\A[A-Za-z0-9\+/]{342}==\z}
8
+ BASE64_STRING_PATTERN = %r{\A[A-Za-z0-9+/]{342}==\z}.freeze
9
9
 
10
- def self.execute(options = {})
11
- new(options).__send__(:execute)
10
+ def self.execute(**args)
11
+ new(**args).__send__(:execute)
12
12
  end
13
13
 
14
14
  attr_accessor :data,
15
15
  :secure_key_token
16
16
 
17
- def initialize(options = {})
18
- self.data = options.fetch(:data).dup
19
- self.secure_key_token = /\A#{Regexp.escape(options.fetch(:secure_key_prefix))}/
17
+ def initialize(data:, secure_key_prefix:, **_args)
18
+ self.data = data.dup
19
+ self.secure_key_token = /\A#{Regexp.escape(secure_key_prefix)}/
20
20
  end
21
21
 
22
22
  protected
@@ -6,12 +6,21 @@ require 'chamber/filters/secure_filter'
6
6
  module Chamber
7
7
  module Filters
8
8
  class InsecureFilter < SecureFilter
9
- BASE64_STRING_PATTERN = %r{\A[A-Za-z0-9\+\/]{342}==\z}
10
- LARGE_DATA_STRING_PATTERN = %r{\A([A-Za-z0-9\+\/#]*\={0,2})#([A-Za-z0-9\+\/#]*\={0,2})#([A-Za-z0-9\+\/#]*\={0,2})\z} # rubocop:disable Metrics/LineLength
9
+ BASE64_STRING_PATTERN = %r{\A[A-Za-z0-9+/]{342}==\z}.freeze
10
+ BASE64_SUBSTRING_PATTERN = %r{[A-Za-z0-9+/#]*={0,2}}.freeze
11
+ LARGE_DATA_STRING_PATTERN = /
12
+ \A
13
+ (#{BASE64_SUBSTRING_PATTERN})
14
+ \#
15
+ (#{BASE64_SUBSTRING_PATTERN})
16
+ \#
17
+ (#{BASE64_SUBSTRING_PATTERN})
18
+ \z
19
+ /x.freeze
11
20
 
12
21
  protected
13
22
 
14
- def execute(raw_data = data)
23
+ def execute(raw_data = data) # rubocop:disable Metrics/CyclomaticComplexity
15
24
  securable_settings = super
16
25
  settings = Hashie::Mash.new
17
26
 
@@ -5,16 +5,16 @@ require 'hashie/mash'
5
5
  module Chamber
6
6
  module Filters
7
7
  class NamespaceFilter
8
- def self.execute(options = {})
9
- new(options).__send__(:execute)
8
+ def self.execute(**args)
9
+ new(**args).__send__(:execute)
10
10
  end
11
11
 
12
12
  attr_accessor :data,
13
13
  :namespaces
14
14
 
15
- def initialize(options = {})
16
- self.data = Hashie::Mash.new(options.fetch(:data))
17
- self.namespaces = options.fetch(:namespaces)
15
+ def initialize(data:, namespaces:, **_args)
16
+ self.data = Hashie::Mash.new(data)
17
+ self.namespaces = namespaces
18
18
  end
19
19
 
20
20
  protected
@@ -5,16 +5,16 @@ require 'hashie/mash'
5
5
  module Chamber
6
6
  module Filters
7
7
  class SecureFilter
8
- def self.execute(options = {})
9
- new(options).__send__(:execute)
8
+ def self.execute(**args)
9
+ new(**args).__send__(:execute)
10
10
  end
11
11
 
12
12
  attr_accessor :data,
13
13
  :secure_key_token
14
14
 
15
- def initialize(options = {})
16
- self.data = Hashie::Mash.new(options.fetch(:data))
17
- self.secure_key_token = /\A#{Regexp.escape(options.fetch(:secure_key_prefix))}/
15
+ def initialize(data:, secure_key_prefix:, **_args)
16
+ self.data = Hashie::Mash.new(data)
17
+ self.secure_key_token = /\A#{Regexp.escape(secure_key_prefix)}/
18
18
  end
19
19
 
20
20
  protected
@@ -5,16 +5,16 @@ require 'hashie/mash'
5
5
  module Chamber
6
6
  module Filters
7
7
  class TranslateSecureKeysFilter
8
- def self.execute(options = {})
9
- new(options).__send__(:execute)
8
+ def self.execute(**args)
9
+ new(**args).__send__(:execute)
10
10
  end
11
11
 
12
12
  attr_accessor :data,
13
13
  :secure_key_token
14
14
 
15
- def initialize(options = {})
16
- self.data = options.fetch(:data).dup
17
- self.secure_key_token = /\A#{Regexp.escape(options.fetch(:secure_key_prefix))}/
15
+ def initialize(data:, secure_key_prefix:, **_args)
16
+ self.data = data.dup
17
+ self.secure_key_token = /\A#{Regexp.escape(secure_key_prefix)}/
18
18
  end
19
19
 
20
20
  protected
@@ -9,15 +9,19 @@ class Instance
9
9
  attr_accessor :configuration,
10
10
  :files
11
11
 
12
- def initialize(options = {})
13
- self.configuration = Configuration.new options
14
- self.files = FileSet.new configuration.to_hash
12
+ def initialize(**args)
13
+ self.configuration = Configuration.new(**args)
14
+ self.files = FileSet.new(**configuration.to_hash)
15
15
  end
16
16
 
17
17
  def settings
18
18
  @settings ||= files.to_settings { |settings| @settings = settings }
19
19
  end
20
20
 
21
+ def [](key)
22
+ settings.[](key)
23
+ end
24
+
21
25
  def filenames
22
26
  files.filenames
23
27
  end
@@ -34,39 +38,51 @@ class Instance
34
38
  files.verify
35
39
  end
36
40
 
37
- def encrypt(data, options = {})
38
- config = configuration.to_hash.merge(options)
39
-
40
- Settings.
41
- new(
42
- config.merge(
43
- settings: data,
44
- pre_filters: [Filters::EncryptionFilter],
45
- post_filters: [],
46
- ),
47
- ).
48
- to_hash
41
+ def to_environment
42
+ settings.to_environment
43
+ end
44
+
45
+ def to_s(**args)
46
+ settings.to_s(**args)
47
+ end
48
+
49
+ def to_hash
50
+ settings.to_hash
51
+ end
52
+
53
+ def namespaces
54
+ settings.namespaces
49
55
  end
50
56
 
51
- def decrypt(data, options = {})
52
- config = configuration.to_hash.merge(options)
53
-
54
- Settings.
55
- new(
56
- config.merge(
57
- settings: data,
58
- pre_filters: [Filters::NamespaceFilter],
59
- post_filters: [
60
- Filters::DecryptionFilter,
61
- Filters::FailedDecryptionFilter,
62
- ],
63
- ),
64
- ).
65
- to_hash
57
+ def encrypt(data, **args)
58
+ config = configuration.to_hash.merge(**args)
59
+
60
+ Settings
61
+ .new(
62
+ **config.merge(
63
+ settings: data,
64
+ pre_filters: [Filters::EncryptionFilter],
65
+ post_filters: [],
66
+ ),
67
+ )
68
+ .to_hash
66
69
  end
67
70
 
68
- def to_s(options = {})
69
- settings.to_s(options)
71
+ def decrypt(data, **args)
72
+ config = configuration.to_hash.merge(**args)
73
+
74
+ Settings
75
+ .new(
76
+ **config.merge(
77
+ settings: data,
78
+ pre_filters: [Filters::NamespaceFilter],
79
+ post_filters: [
80
+ Filters::DecryptionFilter,
81
+ Filters::FailedDecryptionFilter,
82
+ ],
83
+ ),
84
+ )
85
+ .to_hash
70
86
  end
71
87
 
72
88
  def method_missing(name, *args)