lockbox 2.1.0 → 2.2.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/CHANGELOG.md +4 -0
- data/LICENSE.txt +1 -1
- data/README.md +6 -6
- data/lib/lockbox/active_storage_extensions.rb +0 -13
- data/lib/lockbox/model.rb +12 -46
- data/lib/lockbox/version.rb +1 -1
- data/lib/lockbox.rb +4 -2
- metadata +3 -3
checksums.yaml
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
---
|
|
2
2
|
SHA256:
|
|
3
|
-
metadata.gz:
|
|
4
|
-
data.tar.gz:
|
|
3
|
+
metadata.gz: b3a6c05fd83da2e2fc8474f2daf3b55f27ee61dd8a86ff3264df772816bcf92b
|
|
4
|
+
data.tar.gz: d269773e126958e5288a2fcb48ee228dbcd3918648e02834057c8be04f36ec45
|
|
5
5
|
SHA512:
|
|
6
|
-
metadata.gz:
|
|
7
|
-
data.tar.gz:
|
|
6
|
+
metadata.gz: f05224cd3e90993ba6a5b7cadfd2bdac839e6590ae3a5702935dc1146b1349ce76d41d3de989f9e10b3510cf420a86936d283968cc343a7eaccfa119a4dff1b6
|
|
7
|
+
data.tar.gz: d185de56bd634a6ba6753d3a1acf91a7f3940edb02ccbcaa89b22839ef4e57e62a5c698074b6cff821bc5869e3b423dee94781fad4a7e0961794982fa2ed1faa
|
data/CHANGELOG.md
CHANGED
data/LICENSE.txt
CHANGED
data/README.md
CHANGED
|
@@ -72,7 +72,7 @@ Then follow the instructions below for the data you want to encrypt.
|
|
|
72
72
|
Create a migration with:
|
|
73
73
|
|
|
74
74
|
```ruby
|
|
75
|
-
class AddEmailCiphertextToUsers < ActiveRecord::Migration[8.
|
|
75
|
+
class AddEmailCiphertextToUsers < ActiveRecord::Migration[8.1]
|
|
76
76
|
def change
|
|
77
77
|
add_column :users, :email_ciphertext, :text
|
|
78
78
|
end
|
|
@@ -251,7 +251,7 @@ User.decrypt_email_ciphertext(user.email_ciphertext)
|
|
|
251
251
|
Create a migration with:
|
|
252
252
|
|
|
253
253
|
```ruby
|
|
254
|
-
class AddBodyCiphertextToRichTexts < ActiveRecord::Migration[8.
|
|
254
|
+
class AddBodyCiphertextToRichTexts < ActiveRecord::Migration[8.1]
|
|
255
255
|
def change
|
|
256
256
|
add_column :action_text_rich_texts, :body_ciphertext, :text
|
|
257
257
|
end
|
|
@@ -382,7 +382,7 @@ Encryption is applied to all versions after processing.
|
|
|
382
382
|
You can mount the uploader [as normal](https://github.com/carrierwaveuploader/carrierwave#activerecord). With Active Record, this involves creating a migration:
|
|
383
383
|
|
|
384
384
|
```ruby
|
|
385
|
-
class AddLicenseToUsers < ActiveRecord::Migration[8.
|
|
385
|
+
class AddLicenseToUsers < ActiveRecord::Migration[8.1]
|
|
386
386
|
def change
|
|
387
387
|
add_column :users, :license, :string
|
|
388
388
|
end
|
|
@@ -910,7 +910,7 @@ end
|
|
|
910
910
|
You can use `binary` columns for the ciphertext instead of `text` columns.
|
|
911
911
|
|
|
912
912
|
```ruby
|
|
913
|
-
class AddEmailCiphertextToUsers < ActiveRecord::Migration[8.
|
|
913
|
+
class AddEmailCiphertextToUsers < ActiveRecord::Migration[8.1]
|
|
914
914
|
def change
|
|
915
915
|
add_column :users, :email_ciphertext, :binary
|
|
916
916
|
end
|
|
@@ -961,7 +961,7 @@ end
|
|
|
961
961
|
Create a migration with:
|
|
962
962
|
|
|
963
963
|
```ruby
|
|
964
|
-
class MigrateToLockbox < ActiveRecord::Migration[8.
|
|
964
|
+
class MigrateToLockbox < ActiveRecord::Migration[8.1]
|
|
965
965
|
def change
|
|
966
966
|
add_column :users, :name_ciphertext, :text
|
|
967
967
|
add_column :users, :email_ciphertext, :text
|
|
@@ -994,7 +994,7 @@ end
|
|
|
994
994
|
Then remove the previous gem from your Gemfile and drop its columns.
|
|
995
995
|
|
|
996
996
|
```ruby
|
|
997
|
-
class RemovePreviousEncryptedColumns < ActiveRecord::Migration[8.
|
|
997
|
+
class RemovePreviousEncryptedColumns < ActiveRecord::Migration[8.1]
|
|
998
998
|
def change
|
|
999
999
|
remove_column :users, :encrypted_name, :text
|
|
1000
1000
|
remove_column :users, :encrypted_name_iv, :text
|
|
@@ -118,13 +118,6 @@ module Lockbox
|
|
|
118
118
|
super
|
|
119
119
|
end
|
|
120
120
|
|
|
121
|
-
if ActiveStorage::VERSION::STRING.to_f == 7.1 && ActiveStorage.version >= "7.1.4"
|
|
122
|
-
def transform_variants_later
|
|
123
|
-
blob.instance_variable_set(:@lockbox_encrypted, true) if Utils.encrypted_options(record, name)
|
|
124
|
-
super
|
|
125
|
-
end
|
|
126
|
-
end
|
|
127
|
-
|
|
128
121
|
def open(**options)
|
|
129
122
|
blob.open(**options) do |file|
|
|
130
123
|
options = Utils.encrypted_options(record, name)
|
|
@@ -149,12 +142,6 @@ module Lockbox
|
|
|
149
142
|
end
|
|
150
143
|
|
|
151
144
|
module Blob
|
|
152
|
-
if ActiveStorage::VERSION::STRING.to_f == 7.1 && ActiveStorage.version >= "7.1.4"
|
|
153
|
-
def preview_image_needed_before_processing_variants?
|
|
154
|
-
!instance_variable_defined?(:@lockbox_encrypted) && super
|
|
155
|
-
end
|
|
156
|
-
end
|
|
157
|
-
|
|
158
145
|
private
|
|
159
146
|
|
|
160
147
|
def extract_content_type(io)
|
data/lib/lockbox/model.rb
CHANGED
|
@@ -259,18 +259,16 @@ module Lockbox
|
|
|
259
259
|
result
|
|
260
260
|
end
|
|
261
261
|
|
|
262
|
-
|
|
263
|
-
|
|
264
|
-
|
|
265
|
-
end
|
|
262
|
+
def self.insert(attributes, **options)
|
|
263
|
+
super(lockbox_map_record_attributes(attributes), **options)
|
|
264
|
+
end
|
|
266
265
|
|
|
267
|
-
|
|
268
|
-
|
|
269
|
-
|
|
266
|
+
def self.insert!(attributes, **options)
|
|
267
|
+
super(lockbox_map_record_attributes(attributes), **options)
|
|
268
|
+
end
|
|
270
269
|
|
|
271
|
-
|
|
272
|
-
|
|
273
|
-
end
|
|
270
|
+
def self.upsert(attributes, **options)
|
|
271
|
+
super(lockbox_map_record_attributes(attributes, check_readonly: true), **options)
|
|
274
272
|
end
|
|
275
273
|
|
|
276
274
|
def self.insert_all(attributes, **options)
|
|
@@ -344,20 +342,9 @@ module Lockbox
|
|
|
344
342
|
end
|
|
345
343
|
|
|
346
344
|
# warn on default attributes
|
|
347
|
-
|
|
348
|
-
|
|
349
|
-
|
|
350
|
-
warn "[lockbox] WARNING: attributes with `:default` option are not supported. Use `after_initialize` instead."
|
|
351
|
-
end
|
|
352
|
-
elsif attributes_to_define_after_schema_loads.key?(name.to_s)
|
|
353
|
-
opt = attributes_to_define_after_schema_loads[name.to_s][1]
|
|
354
|
-
|
|
355
|
-
# not ideal, since NO_DEFAULT_PROVIDED is private
|
|
356
|
-
has_default = opt != ActiveRecord::Attributes::ClassMethods.const_get(:NO_DEFAULT_PROVIDED)
|
|
357
|
-
|
|
358
|
-
if has_default
|
|
359
|
-
warn "[lockbox] WARNING: attributes with `:default` option are not supported. Use `after_initialize` instead."
|
|
360
|
-
end
|
|
345
|
+
# TODO improve
|
|
346
|
+
if pending_attribute_modifications.any? { |v| v.is_a?(ActiveModel::AttributeRegistration::ClassMethods::PendingDefault) && v.name == name.to_s }
|
|
347
|
+
warn "[lockbox] WARNING: attributes with `:default` option are not supported. Use `after_initialize` instead."
|
|
361
348
|
end
|
|
362
349
|
|
|
363
350
|
# preference:
|
|
@@ -385,7 +372,7 @@ module Lockbox
|
|
|
385
372
|
when :array
|
|
386
373
|
serialize name, type: Array, coder: default_column_serializer || YAML
|
|
387
374
|
end
|
|
388
|
-
|
|
375
|
+
else
|
|
389
376
|
decorate_attributes([name]) do |attr_name, cast_type|
|
|
390
377
|
if cast_type.instance_of?(ActiveRecord::Type::Value)
|
|
391
378
|
original_type = pending_attribute_modifications.find { |v| v.is_a?(ActiveModel::AttributeRegistration::ClassMethods::PendingType) && v.name == original_name.to_s && !v.type.nil? }&.type
|
|
@@ -405,27 +392,6 @@ module Lockbox
|
|
|
405
392
|
cast_type
|
|
406
393
|
end
|
|
407
394
|
end
|
|
408
|
-
elsif !attributes_to_define_after_schema_loads.key?(name.to_s)
|
|
409
|
-
# when migrating it's best to specify the type directly
|
|
410
|
-
# however, we can try to use the original type if its already defined
|
|
411
|
-
if attributes_to_define_after_schema_loads.key?(original_name.to_s)
|
|
412
|
-
attribute name, attributes_to_define_after_schema_loads[original_name.to_s].first
|
|
413
|
-
elsif options[:migrating]
|
|
414
|
-
# we use the original attribute for serialization in the encrypt and decrypt methods
|
|
415
|
-
# so we can use a generic value here
|
|
416
|
-
attribute name, ActiveRecord::Type::Value.new
|
|
417
|
-
else
|
|
418
|
-
attribute name, :string
|
|
419
|
-
end
|
|
420
|
-
elsif attributes_to_define_after_schema_loads[name.to_s].first.is_a?(Proc)
|
|
421
|
-
# hack for Active Record 6.1+ to set string type after serialize
|
|
422
|
-
# otherwise, type gets set to ActiveModel::Type::Value
|
|
423
|
-
# which always returns false for changed_in_place?
|
|
424
|
-
# earlier versions of Active Record take the previous code path
|
|
425
|
-
attribute_type = attributes_to_define_after_schema_loads[name.to_s].first.call(nil)
|
|
426
|
-
if attribute_type.is_a?(ActiveRecord::Type::Serialized) && attribute_type.subtype.nil?
|
|
427
|
-
attribute name, ActiveRecord::Type::Serialized.new(ActiveRecord::Type::String.new, attribute_type.coder)
|
|
428
|
-
end
|
|
429
395
|
end
|
|
430
396
|
|
|
431
397
|
define_method("#{name}_was") do
|
data/lib/lockbox/version.rb
CHANGED
data/lib/lockbox.rb
CHANGED
|
@@ -98,8 +98,10 @@ end
|
|
|
98
98
|
if defined?(ActiveSupport.on_load)
|
|
99
99
|
ActiveSupport.on_load(:active_record) do
|
|
100
100
|
ar_version = ActiveRecord::VERSION::STRING.to_f
|
|
101
|
-
if ar_version < 7.
|
|
102
|
-
if ar_version >= 7.
|
|
101
|
+
if ar_version < 7.2
|
|
102
|
+
if ar_version >= 7.1
|
|
103
|
+
raise Lockbox::Error, "Active Record #{ActiveRecord::VERSION::STRING} requires Lockbox < 2.2"
|
|
104
|
+
elsif ar_version >= 7.0
|
|
103
105
|
raise Lockbox::Error, "Active Record #{ActiveRecord::VERSION::STRING} requires Lockbox < 2.1"
|
|
104
106
|
elsif ar_version >= 5.2
|
|
105
107
|
raise Lockbox::Error, "Active Record #{ActiveRecord::VERSION::STRING} requires Lockbox < 2"
|
metadata
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
|
2
2
|
name: lockbox
|
|
3
3
|
version: !ruby/object:Gem::Version
|
|
4
|
-
version: 2.
|
|
4
|
+
version: 2.2.0
|
|
5
5
|
platform: ruby
|
|
6
6
|
authors:
|
|
7
7
|
- Andrew Kane
|
|
@@ -48,14 +48,14 @@ required_ruby_version: !ruby/object:Gem::Requirement
|
|
|
48
48
|
requirements:
|
|
49
49
|
- - ">="
|
|
50
50
|
- !ruby/object:Gem::Version
|
|
51
|
-
version: '3.
|
|
51
|
+
version: '3.3'
|
|
52
52
|
required_rubygems_version: !ruby/object:Gem::Requirement
|
|
53
53
|
requirements:
|
|
54
54
|
- - ">="
|
|
55
55
|
- !ruby/object:Gem::Version
|
|
56
56
|
version: '0'
|
|
57
57
|
requirements: []
|
|
58
|
-
rubygems_version:
|
|
58
|
+
rubygems_version: 4.0.6
|
|
59
59
|
specification_version: 4
|
|
60
60
|
summary: Modern encryption for Ruby and Rails
|
|
61
61
|
test_files: []
|