Shrine 3.9.0
New features
-
Shrine.find_storagenow raisesShrine::MissingStorage(a subclass ofShrine::Error) when the storage isn't registered, instead of a genericShrine::Error. This is useful with thedynamic_storageplugin, where the resolver might fail to find its dependencies (e.g. a deleted DB record), and lets you rescue that case separately from other errors.begin Shrine.find_storage(:store) rescue Shrine::MissingStorage # handle missing storage specifically end -
The
url_optionsandupload_optionsplugins now accept aRegexpin place of a storage key. This is useful when storage keys are generated dynamically (e.g. via thedynamic_storageplugin), since it's not possible to list every storage key upfront. An exact storage key match always takes precedence over aRegexpmatch.plugin :url_options, /_store\z/ => { expires_in: 24*60*60 } plugin :upload_options, /_store\z/ => { acl: "private" } -
The
activerecordplugin now accepts an:attribute_typesoption. When enabled, it usestype_for_attribute(instead of justcolumns_hash) to detect whether the data attribute is JSON/JSONB, so Shrine also skips its own serialization for attributes declared via the Active Record Attributes API (not just real database columns). It defaults tofalsefor backwards compatibility with apps that might be relying on the previous double-serialization behavior.class Photo < ActiveRecord::Base # `image_data` is a text column include ImageUploader::Attachment(:image) attribute :image_data, :json end plugin :activerecord, attribute_types: true
Bug fixes
-
The
activerecordandsequelplugins no longer delete the previous attachment when the record being saved was just created. Previously, duplicating a persisted record (e.g. via#dup) and immediately assigning a new attachment before saving the duplicate could end up deleting the original record's attachment, since both records shared the same underlying file. -
The
remove_invalidplugin now correctly clears/reverts the model attribute after an invalid file is deassigned. Previously the record's raw attribute could be left out of sync with the attacher after validation failed. -
UploadedFile#tempfile(from thetempfileplugin) can now be called without opening the uploaded file first. Previously it raisedShrine::Errorunless the file was already open; now it downloads and caches the file on demand. If the uploaded file is open, its tempfile is still cleaned up when the file is closed; otherwise it's cleaned up whenever it becomes unreachable and is garbage collected, so it's still recommended to close the uploaded file when you're done with it for deterministic cleanup.