Module: Sidekiq::EncryptedArgs
- Defined in:
- lib/sidekiq/encrypted_args.rb,
lib/sidekiq/encrypted_args/version.rb,
lib/sidekiq/encrypted_args/client_middleware.rb,
lib/sidekiq/encrypted_args/server_middleware.rb
Overview
Provides middleware for encrypting sensitive arguments in Sidekiq jobs.
This module allows you to specify which job arguments should be encrypted in Redis to protect sensitive information like API keys, passwords, or personally identifiable information.
Defined Under Namespace
Classes: ClientMiddleware, InvalidSecretError, ServerMiddleware
Constant Summary collapse
- VERSION =
The current version of the sidekiq-encrypted_args gem.
File.read(File.join(__dir__, "..", "..", "..", "VERSION")).chomp.freeze
Class Method Summary collapse
-
.configure!(secret: nil) ⇒ Object
Add the client and server middleware to the default Sidekiq middleware chains.
-
.decrypt(encrypted_data) ⇒ Object
Decrypt data.
-
.decrypt_after(middleware) ⇒ void
Insert the server decryption middleware after the specified middleware.
-
.decrypt_before(middleware) ⇒ void
Insert the server decryption middleware before the specified middleware.
-
.encrypt(data) ⇒ String?
Encrypt a value.
-
.encrypt_after(middleware) ⇒ void
Insert the client encryption middleware after the specified middleware.
-
.encrypt_before(middleware) ⇒ void
Insert the client encryption middleware before the specified middleware.
-
.encrypted?(value) ⇒ Boolean
Check if a value is encrypted.
-
.encrypted_args_option(worker_class, job) ⇒ Array<Integer>?
private
Private helper method to get the encrypted args option from an options hash.
-
.secret=(value) ⇒ void
Set the secret key used for encrypting arguments.
Class Method Details
.configure!(secret: nil) ⇒ Object
Add the client and server middleware to the default Sidekiq middleware chains. If you need to ensure the order of where the middleware is added, you can forgo this method and add it yourself.
This method prepends client middleware and appends server middleware.
62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 |
# File 'lib/sidekiq/encrypted_args.rb', line 62 def configure!(secret: nil) self.secret = secret unless secret.nil? encryptors # Calling encryptors will validate that a secret is set. Sidekiq.configure_client do |config| config.client_middleware do |chain| chain.prepend Sidekiq::EncryptedArgs::ClientMiddleware end end Sidekiq.configure_server do |config| config.server_middleware do |chain| chain.add Sidekiq::EncryptedArgs::ServerMiddleware end config.client_middleware do |chain| chain.prepend Sidekiq::EncryptedArgs::ClientMiddleware end end end |
.decrypt(encrypted_data) ⇒ Object
Decrypt data
an unencrypted string, then the string itself will be returned.
172 173 174 175 176 |
# File 'lib/sidekiq/encrypted_args.rb', line 172 def decrypt(encrypted_data) return encrypted_data unless SecretKeys::Encryptor.encrypted?(encrypted_data) json = decrypt_string(encrypted_data) JSON.parse(json) end |
.decrypt_after(middleware) ⇒ void
This method returns an undefined value.
Insert the server decryption middleware after the specified middleware.
134 135 136 137 138 139 140 |
# File 'lib/sidekiq/encrypted_args.rb', line 134 def decrypt_after(middleware) Sidekiq.configure_server do |config| config.server_middleware do |chain| chain.insert_after(middleware, Sidekiq::EncryptedArgs::ServerMiddleware) end end end |
.decrypt_before(middleware) ⇒ void
This method returns an undefined value.
Insert the server decryption middleware before the specified middleware.
122 123 124 125 126 127 128 |
# File 'lib/sidekiq/encrypted_args.rb', line 122 def decrypt_before(middleware) Sidekiq.configure_server do |config| config.server_middleware do |chain| chain.insert_before(middleware, Sidekiq::EncryptedArgs::ServerMiddleware) end end end |
.encrypt(data) ⇒ String?
Encrypt a value.
153 154 155 156 157 158 |
# File 'lib/sidekiq/encrypted_args.rb', line 153 def encrypt(data) return nil if data.nil? json = (data.respond_to?(:to_json) ? data.to_json : JSON.generate(data)) encrypt_string(json) end |
.encrypt_after(middleware) ⇒ void
This method returns an undefined value.
Insert the client encryption middleware after the specified middleware.
104 105 106 107 108 109 110 111 112 113 114 115 116 |
# File 'lib/sidekiq/encrypted_args.rb', line 104 def encrypt_after(middleware) Sidekiq.configure_client do |config| config.client_middleware do |chain| chain.insert_after(middleware, Sidekiq::EncryptedArgs::ClientMiddleware) end end Sidekiq.configure_server do |config| config.client_middleware do |chain| chain.insert_after(middleware, Sidekiq::EncryptedArgs::ClientMiddleware) end end end |
.encrypt_before(middleware) ⇒ void
This method returns an undefined value.
Insert the client encryption middleware before the specified middleware.
86 87 88 89 90 91 92 93 94 95 96 97 98 |
# File 'lib/sidekiq/encrypted_args.rb', line 86 def encrypt_before(middleware) Sidekiq.configure_client do |config| config.client_middleware do |chain| chain.insert_before(middleware, Sidekiq::EncryptedArgs::ClientMiddleware) end end Sidekiq.configure_server do |config| config.client_middleware do |chain| chain.insert_before(middleware, Sidekiq::EncryptedArgs::ClientMiddleware) end end end |
.encrypted?(value) ⇒ Boolean
Check if a value is encrypted.
181 182 183 |
# File 'lib/sidekiq/encrypted_args.rb', line 181 def encrypted?(value) SecretKeys::Encryptor.encrypted?(value) end |
.encrypted_args_option(worker_class, job) ⇒ Array<Integer>?
This method is part of a private API. You should avoid using this method if possible, as it may be removed or be changed in the future.
Private helper method to get the encrypted args option from an options hash. The value of this option
can be true or an array indicating if each positional argument should be encrypted, or a hash
with keys for the argument position and true as the value.
193 194 195 196 197 198 199 200 201 202 203 204 205 206 207 208 209 210 211 212 213 214 215 216 217 218 219 220 221 222 223 224 225 226 227 228 229 230 231 232 233 234 235 236 |
# File 'lib/sidekiq/encrypted_args.rb', line 193 def encrypted_args_option(worker_class, job) option = job["encrypted_args"] return nil if option.nil? return [] if option == false indexes = [] if option == true job["args"].size.times { |i| indexes << i } elsif option.is_a?(Hash) raise ArgumentError.new("Hash-based argument encryption is no longer supported.") else array_type = nil Array(option).each do |val| current_type = nil if val.is_a?(Integer) indexes << val current_type = :integer elsif val.is_a?(Symbol) || val.is_a?(String) if worker_class.is_a?(String) class_name = worker_class worker_class = constantize(worker_class) if worker_class.nil? raise ArgumentError.new("Cannot resolve worker class #{class_name.inspect} to look up named encrypted args; use integer positions instead.") end end position = perform_method_parameter_index(worker_class, val) if position.nil? raise ArgumentError.new("Encrypted arg #{val.inspect} is not a parameter of #{worker_class}#perform.") end indexes << position current_type = :symbol else raise ArgumentError.new("Encrypted args must be specified as integers or symbols.") end if array_type && current_type != array_type raise ArgumentError.new("Encrypted args cannot mix integers and symbols.") else array_type ||= current_type end end end indexes end |
.secret=(value) ⇒ void
This method returns an undefined value.
Set the secret key used for encrypting arguments. If this is not set,
the value will be loaded from the SIDEKIQ_ENCRYPTED_ARGS_SECRET environment
variable. If that value is not set either, an InvalidSecretError will be
raised when arguments are encrypted or decrypted.
You can set multiple secrets by passing an array if you need to roll your secrets. The left most value in the array will be used as the encryption secret, but all the values will be tried when decrypting. That way if you have scheduled jobs that were encrypted with a different secret, you can still make it available when decrypting the arguments when the job gets run. If you are using the environment variable, separate the keys with spaces.
42 43 44 45 46 |
# File 'lib/sidekiq/encrypted_args.rb', line 42 def secret=(value) @mutex.synchronize do @encryptors = make_encryptors(value).freeze end end |