carrierwave 3.0.6 → 3.1.0.beta
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +4 -4
- data/README.md +60 -12
- data/lib/carrierwave/downloader/base.rb +1 -1
- data/lib/carrierwave/processing/mini_magick.rb +29 -0
- data/lib/carrierwave/processing/rmagick.rb +36 -5
- data/lib/carrierwave/processing/vips.rb +31 -0
- data/lib/carrierwave/sanitized_file.rb +11 -2
- data/lib/carrierwave/uploader/cache.rb +1 -1
- data/lib/carrierwave/uploader/configuration.rb +6 -4
- data/lib/carrierwave/uploader/content_type_allowlist.rb +1 -1
- data/lib/carrierwave/uploader/content_type_denylist.rb +2 -2
- data/lib/carrierwave/uploader/extension_allowlist.rb +1 -1
- data/lib/carrierwave/uploader/extension_denylist.rb +2 -2
- data/lib/carrierwave/uploader/store.rb +26 -0
- data/lib/carrierwave/uploader/versions.rb +1 -1
- data/lib/carrierwave/version.rb +1 -1
- data/lib/carrierwave.rb +9 -0
- metadata +4 -18
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA256:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: 94f7caad86544528c7b1d7acdecd8bfe3d5d94e53469890899578c47dd142f91
|
4
|
+
data.tar.gz: 1d572604e7b5b89639286ae6f7d087f513a53cf3adf4028138bdea0be6d538a6
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: 19f434816a0cde1b473525dc383cd61f7b0899ddb7c2230a95053ba43ee6287d0a9dcb6dd322bd016ed582140d2e54fc5f5385741c91e09df3201c6f39ed4083
|
7
|
+
data.tar.gz: 127a4ac2b998d373d5774cbfeef32c49f31d9fe44f30416738945b61c6316ce093f4c2607aeb9c6cfb4c7286684926491755572eb8fd696b4b0195bdcd07a07e
|
data/README.md
CHANGED
@@ -659,14 +659,17 @@ end
|
|
659
659
|
## Testing with CarrierWave
|
660
660
|
|
661
661
|
It's a good idea to test your uploaders in isolation. In order to speed up your
|
662
|
-
tests, it's recommended to switch off processing in your tests, and to use the
|
663
|
-
|
662
|
+
tests, it's recommended to switch off processing in your tests, and to use the file storage.
|
663
|
+
Also, you can disable SSRF protection at your own risk using the `skip_ssrf_protection` configuration.
|
664
|
+
|
665
|
+
In Rails you could do that by adding an initializer with:
|
664
666
|
|
665
667
|
```ruby
|
666
668
|
if Rails.env.test? or Rails.env.cucumber?
|
667
669
|
CarrierWave.configure do |config|
|
668
670
|
config.storage = :file
|
669
671
|
config.enable_processing = false
|
672
|
+
config.skip_ssrf_protection = true
|
670
673
|
end
|
671
674
|
end
|
672
675
|
```
|
@@ -764,6 +767,10 @@ CarrierWave.configure do |config|
|
|
764
767
|
config.fog_directory = 'name_of_bucket' # required
|
765
768
|
config.fog_public = false # optional, defaults to true
|
766
769
|
config.fog_attributes = { cache_control: "public, max-age=#{365.days.to_i}" } # optional, defaults to {}
|
770
|
+
# Use this if you have AWS S3 ACLs disabled.
|
771
|
+
# config.fog_attributes = { 'x-amz-acl' => 'bucket-owner-full-control' }
|
772
|
+
# Use this if you have Google Cloud Storage uniform bucket-level access enabled.
|
773
|
+
# config.fog_attributes = { uniform: true }
|
767
774
|
# For an application which utilizes multiple servers but does not need caches persisted across requests,
|
768
775
|
# uncomment the line :file instead of the default :storage. Otherwise, it will use AWS as the temp cache store.
|
769
776
|
# config.cache_storage = :file
|
@@ -797,7 +804,7 @@ gem "fog"
|
|
797
804
|
```
|
798
805
|
|
799
806
|
You'll need to configure a directory (also known as a container), username and API key in the initializer.
|
800
|
-
For the sake of performance it is assumed that the directory already exists, so please create it if
|
807
|
+
For the sake of performance it is assumed that the directory already exists, so please create it if needs to be.
|
801
808
|
|
802
809
|
Using a US-based account:
|
803
810
|
|
@@ -856,7 +863,7 @@ gem "fog-google"
|
|
856
863
|
```
|
857
864
|
|
858
865
|
You'll need to configure a directory (also known as a bucket) and the credentials in the initializer.
|
859
|
-
For the sake of performance it is assumed that the directory already exists, so please create it if
|
866
|
+
For the sake of performance it is assumed that the directory already exists, so please create it if needs to be.
|
860
867
|
|
861
868
|
Please read the [fog-google README](https://github.com/fog/fog-google/blob/master/README.md) on how to get credentials.
|
862
869
|
|
@@ -970,14 +977,6 @@ class AvatarUploader < CarrierWave::Uploader::Base
|
|
970
977
|
end
|
971
978
|
```
|
972
979
|
|
973
|
-
#### List of available processing methods:
|
974
|
-
|
975
|
-
- `convert` - Changes the image encoding format to the given format(eg. jpg). This operation is treated specially to trigger the change of the file extension, so it matches with the format of the resulting file.
|
976
|
-
- `resize_to_limit` - Resize the image to fit within the specified dimensions while retaining the original aspect ratio. Will only resize the image if it is larger than the specified dimensions. The resulting image may be shorter or narrower than specified in the smaller dimension but will not be larger than the specified values.
|
977
|
-
- `resize_to_fit` - Resize the image to fit within the specified dimensions while retaining the original aspect ratio. The image may be shorter or narrower than specified in the smaller dimension but will not be larger than the specified values.
|
978
|
-
- `resize_to_fill` - Resize the image to fit within the specified dimensions while retaining the aspect ratio of the original image. If necessary, crop the image in the larger dimension. Optionally, a "gravity" may be specified, for example "Center", or "NorthEast".
|
979
|
-
- `resize_and_pad` - Resize the image to fit within the specified dimensions while retaining the original aspect ratio. If necessary, will pad the remaining area with the given color, which defaults to transparent (for gif and png, white for jpeg). Optionally, a "gravity" may be specified, as above.
|
980
|
-
|
981
980
|
See `carrierwave/processing/mini_magick.rb` for details.
|
982
981
|
|
983
982
|
### Using RMagick
|
@@ -1009,6 +1008,54 @@ end
|
|
1009
1008
|
Check out the manipulate! method, which makes it easy for you to write your own
|
1010
1009
|
manipulation methods.
|
1011
1010
|
|
1011
|
+
### Using Vips
|
1012
|
+
|
1013
|
+
CarrierWave version 2.2.0 added support for the `libvips` image processing library, through [ImageProcessing::Vips](https://github.com/janko/image_processing/blob/master/doc/vips.md). Its functionality matches that of the RMagick and MiniMagick processors, but it uses less memory and offers [faster processing](https://github.com/libvips/libvips/wiki/Speed-and-memory-use). To use the Vips processing module you must first install `libvips`, for example:
|
1014
|
+
|
1015
|
+
````bash
|
1016
|
+
$ sudo apt install libvips
|
1017
|
+
````
|
1018
|
+
|
1019
|
+
You also need to tell your uploader to use Vips:
|
1020
|
+
|
1021
|
+
````ruby
|
1022
|
+
class ImageFileUploader < CarrierWave::Uploader::Base
|
1023
|
+
include CarrierWave::Vips
|
1024
|
+
end
|
1025
|
+
````
|
1026
|
+
|
1027
|
+
### List of available processing methods:
|
1028
|
+
|
1029
|
+
> [!NOTE]
|
1030
|
+
> While the intention is to provide uniform interfaces to al three processing libraries the availability and implementation of processing methods can <a href="supported-processing-methods">vary slightly between them</a>.
|
1031
|
+
|
1032
|
+
- `convert` - Changes the image encoding format to the given format (eg. jpg). This operation is treated specially to trigger the change of the file extension, so it matches with the format of the resulting file.
|
1033
|
+
- `resize_to_limit` - Resize the image to fit within the specified dimensions while retaining the original aspect ratio. Will only resize the image if it is larger than the specified dimensions. The resulting image may be shorter or narrower than specified in the smaller dimension but will not be larger than the specified values.
|
1034
|
+
- `resize_to_fit` - Resize the image to fit within the specified dimensions while retaining the original aspect ratio. The image may be shorter or narrower than specified in the smaller dimension but will not be larger than the specified values.
|
1035
|
+
- `resize_to_fill` - Resize the image to fit within the specified dimensions while retaining the aspect ratio of the original image. If necessary, crop the image in the larger dimension. Optionally, a "gravity" may be specified, for example "Center", or "NorthEast".
|
1036
|
+
- `resize_and_pad` - Resize the image to fit within the specified dimensions while retaining the original aspect ratio. If necessary, will pad the remaining area with the given color, which defaults to transparent (for gif and png, white for jpeg). Optionally, a "gravity" may be specified, as above.
|
1037
|
+
- `crop` - Crop the image to the contents of a box with the specified height and width, positioned a given number of pixels from the top and left. The original image edge will be retained should the bottom and/or right edge of the box fall outside the image bounds.
|
1038
|
+
|
1039
|
+
#### Supported processing methods
|
1040
|
+
|
1041
|
+
The following table shows which processing methods are supported by each processing library, and which parameters they accept:
|
1042
|
+
|
1043
|
+
Method|RMagick|MiniMagick|Vips
|
1044
|
+
------|-----------------|-----------------|-----------------|
|
1045
|
+
`convert`|`format`|`format`, `page`<sup>1</sup>|`format`, `page`<sup>1</sup>
|
1046
|
+
`resize_to_limit`|`width`, `height`|`width`, `height`|`width`, `height`
|
1047
|
+
`resize_to_fit`|`width`, `height`|`width`, `height`|`width`, `height`
|
1048
|
+
`resize_to_fill`|`width`, `height`, `gravity`<sup>2</sup>|`width`, `height`, `gravity`<sup>2</sup>|`width`, `height`
|
1049
|
+
`resize_and_pad`|`width`, `height`, `background`, `gravity`<sup>2</sup>|`width`, `height`, `background`, `gravity`<sup>2</sup>|`width`, `height`, `background`, `gravity`<sup>2</sup>
|
1050
|
+
`resize_to_geometry_string`|`geometry_string`<sup>3</sup>|*not implemented*|*not implemented*
|
1051
|
+
`crop`|`left`, `top`, `width`, `height`|`left`, `top`, `width`, `height`|`left`, `top`, `width`, `height`
|
1052
|
+
|
1053
|
+
<sup>1</sup>`page` refers to the page number when converting from PDF, frame number when converting from GIF, and layer number when converting from PSD.
|
1054
|
+
|
1055
|
+
<sup>2</sup>`gravity` refers to an image position given as one of `Center`, `North`, `NorthWest`, `West`, `SouthWest`, `South`, `SouthEast`, `East`, or `NorthEast`.
|
1056
|
+
|
1057
|
+
<sup>3</sup>`geometry_string` is an [ImageMagick geometry string](https://rmagick.github.io/imusage.html#geometry).
|
1058
|
+
|
1012
1059
|
## Migrating from Paperclip
|
1013
1060
|
|
1014
1061
|
If you are using Paperclip, you can use the provided compatibility module:
|
@@ -1133,6 +1180,7 @@ cache
|
|
1133
1180
|
process
|
1134
1181
|
remove
|
1135
1182
|
retrieve_from_cache
|
1183
|
+
retrieve_from_store
|
1136
1184
|
store
|
1137
1185
|
```
|
1138
1186
|
|
@@ -79,6 +79,10 @@ module CarrierWave
|
|
79
79
|
def resize_and_pad(width, height, background=:transparent, gravity='Center')
|
80
80
|
process :resize_and_pad => [width, height, background, gravity]
|
81
81
|
end
|
82
|
+
|
83
|
+
def crop(left, top, width, height)
|
84
|
+
process :crop => [left, top, width, height]
|
85
|
+
end
|
82
86
|
end
|
83
87
|
|
84
88
|
##
|
@@ -210,6 +214,31 @@ module CarrierWave
|
|
210
214
|
end
|
211
215
|
end
|
212
216
|
|
217
|
+
##
|
218
|
+
# Crop the image to the contents of a box positioned at [left] and [top], with the dimensions given
|
219
|
+
# by [width] and [height]. The original image bottom/right edge is preserved if the cropping box falls
|
220
|
+
# outside the image bounds.
|
221
|
+
#
|
222
|
+
# === Parameters
|
223
|
+
#
|
224
|
+
# [left (integer)] left edge of area to extract
|
225
|
+
# [top (integer)] top edge of area to extract
|
226
|
+
# [width (Integer)] width of area to extract
|
227
|
+
# [height (Integer)] height of area to extract
|
228
|
+
#
|
229
|
+
# === Yields
|
230
|
+
#
|
231
|
+
# [MiniMagick::Image] additional manipulations to perform
|
232
|
+
#
|
233
|
+
def crop(left, top, width, height, combine_options: {}, &block)
|
234
|
+
width, height = resolve_dimensions(width, height)
|
235
|
+
|
236
|
+
minimagick!(block) do |builder|
|
237
|
+
builder.crop(left, top, width, height)
|
238
|
+
.apply(combine_options)
|
239
|
+
end
|
240
|
+
end
|
241
|
+
|
213
242
|
##
|
214
243
|
# Returns the width of the image in pixels.
|
215
244
|
#
|
@@ -22,7 +22,7 @@ module CarrierWave
|
|
22
22
|
# end
|
23
23
|
#
|
24
24
|
# Or create your own helpers with the powerful manipulate! method. Check
|
25
|
-
# out the RMagick docs at
|
25
|
+
# out the RMagick docs at https://rmagick.github.io/ for more
|
26
26
|
# info
|
27
27
|
#
|
28
28
|
# class MyUploader < CarrierWave::Uploader::Base
|
@@ -102,12 +102,16 @@ module CarrierWave
|
|
102
102
|
def resize_to_geometry_string(geometry_string)
|
103
103
|
process :resize_to_geometry_string => [geometry_string]
|
104
104
|
end
|
105
|
+
|
106
|
+
def crop(left, top, width, height)
|
107
|
+
process :crop => [left, top, width, height]
|
108
|
+
end
|
105
109
|
end
|
106
110
|
|
107
111
|
##
|
108
112
|
# Changes the image encoding format to the given format
|
109
113
|
#
|
110
|
-
# See even
|
114
|
+
# See even https://rmagick.github.io/magick.html#formats
|
111
115
|
#
|
112
116
|
# === Parameters
|
113
117
|
#
|
@@ -161,7 +165,7 @@ module CarrierWave
|
|
161
165
|
# image may be shorter or narrower than specified in the smaller dimension
|
162
166
|
# but will not be larger than the specified values."
|
163
167
|
#
|
164
|
-
# See even
|
168
|
+
# See even https://rmagick.github.io/image3.html#resize_to_fit
|
165
169
|
#
|
166
170
|
# === Parameters
|
167
171
|
#
|
@@ -187,7 +191,7 @@ module CarrierWave
|
|
187
191
|
# specified dimensions while retaining the aspect ratio of the original
|
188
192
|
# image. If necessary, crop the image in the larger dimension."
|
189
193
|
#
|
190
|
-
# See even
|
194
|
+
# See even https://rmagick.github.io/image3.html#resize_to_fill
|
191
195
|
#
|
192
196
|
# === Parameters
|
193
197
|
#
|
@@ -260,6 +264,33 @@ module CarrierWave
|
|
260
264
|
end
|
261
265
|
end
|
262
266
|
|
267
|
+
##
|
268
|
+
# Crop the image to the contents of a box positioned at [left] and [top], with the dimensions given
|
269
|
+
# by [width] and [height]. The original image bottom/right edge is preserved if the cropping box falls
|
270
|
+
# outside the image bounds.
|
271
|
+
#
|
272
|
+
# === Parameters
|
273
|
+
#
|
274
|
+
# [left (integer)] left edge of area to extract
|
275
|
+
# [top (integer)] top edge of area to extract
|
276
|
+
# [width (Integer)] width of area to extract
|
277
|
+
# [height (Integer)] height of area to extract
|
278
|
+
#
|
279
|
+
# === Yields
|
280
|
+
#
|
281
|
+
# [Magick::Image] additional manipulations to perform
|
282
|
+
#
|
283
|
+
def crop(left, top, width, height, combine_options: {})
|
284
|
+
width = dimension_from width
|
285
|
+
height = dimension_from height
|
286
|
+
|
287
|
+
manipulate! do |img|
|
288
|
+
img.crop!(left, top, width, height)
|
289
|
+
img = yield(img) if block_given?
|
290
|
+
img
|
291
|
+
end
|
292
|
+
end
|
293
|
+
|
263
294
|
##
|
264
295
|
# Returns the width of the image.
|
265
296
|
#
|
@@ -377,7 +408,7 @@ module CarrierWave
|
|
377
408
|
proc do |img|
|
378
409
|
options.each do |k, v|
|
379
410
|
if v.is_a?(String) && (matches = v.match(/^["'](.+)["']/))
|
380
|
-
|
411
|
+
CarrierWave.deprecator.warn "Passing quoted strings like #{v} to #manipulate! is deprecated, pass them without quoting."
|
381
412
|
v = matches[1]
|
382
413
|
end
|
383
414
|
img.public_send(:"#{k}=", v)
|
@@ -78,6 +78,10 @@ module CarrierWave
|
|
78
78
|
def resize_and_pad(width, height, background=nil, gravity='centre', alpha=nil)
|
79
79
|
process :resize_and_pad => [width, height, background, gravity, alpha]
|
80
80
|
end
|
81
|
+
|
82
|
+
def crop(left, top, width, height)
|
83
|
+
process :crop => [left, top, width, height]
|
84
|
+
end
|
81
85
|
end
|
82
86
|
|
83
87
|
##
|
@@ -208,6 +212,33 @@ module CarrierWave
|
|
208
212
|
end
|
209
213
|
end
|
210
214
|
|
215
|
+
##
|
216
|
+
# Crop the image to the contents of a box positioned at [left] and [top], with the dimensions given
|
217
|
+
# by [width] and [height]. The original image bottom/right edge is preserved if the cropping box falls
|
218
|
+
# outside the image bounds.
|
219
|
+
#
|
220
|
+
# === Parameters
|
221
|
+
#
|
222
|
+
# [left (integer)] left edge of area to extract
|
223
|
+
# [top (integer)] top edge of area to extract
|
224
|
+
# [width (Integer)] width of area to extract
|
225
|
+
# [height (Integer)] height of area to extract
|
226
|
+
#
|
227
|
+
# === Yields
|
228
|
+
#
|
229
|
+
# [Vips::Image] additional manipulations to perform
|
230
|
+
#
|
231
|
+
def crop(left, top, width, height, combine_options: {})
|
232
|
+
width, height = resolve_dimensions(width, height)
|
233
|
+
width = vips_image.width - left if width + left > vips_image.width
|
234
|
+
height = vips_image.height - top if height + top > vips_image.height
|
235
|
+
|
236
|
+
vips! do |builder|
|
237
|
+
builder.crop(left, top, width, height)
|
238
|
+
.apply(combine_options)
|
239
|
+
end
|
240
|
+
end
|
241
|
+
|
211
242
|
##
|
212
243
|
# Returns the width of the image in pixels.
|
213
244
|
#
|
@@ -307,7 +307,7 @@ module CarrierWave
|
|
307
307
|
def declared_content_type
|
308
308
|
@declared_content_type ||
|
309
309
|
if @file.respond_to?(:content_type) && @file.content_type
|
310
|
-
@file.content_type.to_s.chomp
|
310
|
+
Marcel::MimeType.for(declared_type: @file.content_type.to_s.chomp)
|
311
311
|
end
|
312
312
|
end
|
313
313
|
|
@@ -321,7 +321,16 @@ module CarrierWave
|
|
321
321
|
|
322
322
|
def identified_content_type
|
323
323
|
with_io do |io|
|
324
|
-
Marcel::Magic.by_magic(io)
|
324
|
+
mimetype_by_magic = Marcel::Magic.by_magic(io)
|
325
|
+
mimetype_by_path = Marcel::Magic.by_path(path)
|
326
|
+
|
327
|
+
return nil if mimetype_by_magic.nil?
|
328
|
+
|
329
|
+
if mimetype_by_path&.child_of?(mimetype_by_magic.type)
|
330
|
+
mimetype_by_path.type
|
331
|
+
else
|
332
|
+
mimetype_by_magic.type
|
333
|
+
end
|
325
334
|
end
|
326
335
|
rescue Errno::ENOENT
|
327
336
|
nil
|
@@ -91,9 +91,9 @@ module CarrierWave
|
|
91
91
|
end
|
92
92
|
|
93
93
|
def sanitized_file
|
94
|
-
ActiveSupport::Deprecation.warn('#sanitized_file is deprecated, use #file instead.')
|
95
94
|
file
|
96
95
|
end
|
96
|
+
CarrierWave.deprecator.deprecate_methods(self, sanitized_file: :file)
|
97
97
|
|
98
98
|
##
|
99
99
|
# Returns a String which uniquely identifies the currently cached file for later retrieval
|
@@ -47,6 +47,7 @@ module CarrierWave
|
|
47
47
|
add_config :cache_only
|
48
48
|
add_config :download_retry_count
|
49
49
|
add_config :download_retry_wait_time
|
50
|
+
add_config :skip_ssrf_protection
|
50
51
|
|
51
52
|
# set default values
|
52
53
|
reset_config
|
@@ -156,19 +157,19 @@ module CarrierWave
|
|
156
157
|
def add_deprecated_config(name)
|
157
158
|
class_eval <<-RUBY, __FILE__, __LINE__ + 1
|
158
159
|
def self.#{name}(value=nil)
|
159
|
-
|
160
|
+
CarrierWave.deprecator.warn "##{name} is deprecated and has no effect"
|
160
161
|
end
|
161
162
|
|
162
163
|
def self.#{name}=(value)
|
163
|
-
|
164
|
+
CarrierWave.deprecator.warn "##{name} is deprecated and has no effect"
|
164
165
|
end
|
165
166
|
|
166
167
|
def #{name}=(value)
|
167
|
-
|
168
|
+
CarrierWave.deprecator.warn "##{name} is deprecated and has no effect"
|
168
169
|
end
|
169
170
|
|
170
171
|
def #{name}
|
171
|
-
|
172
|
+
CarrierWave.deprecator.warn "##{name} is deprecated and has no effect"
|
172
173
|
end
|
173
174
|
RUBY
|
174
175
|
end
|
@@ -216,6 +217,7 @@ module CarrierWave
|
|
216
217
|
config.ensure_multipart_form = true
|
217
218
|
config.download_retry_count = 0
|
218
219
|
config.download_retry_wait_time = 5
|
220
|
+
config.skip_ssrf_protection = false
|
219
221
|
end
|
220
222
|
end
|
221
223
|
end
|
@@ -36,7 +36,7 @@ module CarrierWave
|
|
36
36
|
def check_content_type_allowlist!(new_file)
|
37
37
|
allowlist = content_type_allowlist
|
38
38
|
if !allowlist && respond_to?(:content_type_whitelist) && content_type_whitelist
|
39
|
-
|
39
|
+
CarrierWave.deprecator.warn "#content_type_whitelist is deprecated, use #content_type_allowlist instead." unless instance_variable_defined?(:@content_type_whitelist_warned)
|
40
40
|
@content_type_whitelist_warned = true
|
41
41
|
allowlist = content_type_whitelist
|
42
42
|
end
|
@@ -36,14 +36,14 @@ module CarrierWave
|
|
36
36
|
def check_content_type_denylist!(new_file)
|
37
37
|
denylist = content_type_denylist
|
38
38
|
if !denylist && respond_to?(:content_type_blacklist) && content_type_blacklist
|
39
|
-
|
39
|
+
CarrierWave.deprecator.warn "#content_type_blacklist is deprecated, use #content_type_denylist instead." unless instance_variable_defined?(:@content_type_blacklist_warned)
|
40
40
|
@content_type_blacklist_warned = true
|
41
41
|
denylist = content_type_blacklist
|
42
42
|
end
|
43
43
|
|
44
44
|
return unless denylist
|
45
45
|
|
46
|
-
|
46
|
+
CarrierWave.deprecator.warn "Use of #content_type_denylist is deprecated for the security reason, use #content_type_allowlist instead to explicitly state what are safe to accept" unless instance_variable_defined?(:@content_type_denylist_warned)
|
47
47
|
@content_type_denylist_warned = true
|
48
48
|
|
49
49
|
content_type = new_file.content_type
|
@@ -39,7 +39,7 @@ module CarrierWave
|
|
39
39
|
def check_extension_allowlist!(new_file)
|
40
40
|
allowlist = extension_allowlist
|
41
41
|
if !allowlist && respond_to?(:extension_whitelist) && extension_whitelist
|
42
|
-
|
42
|
+
CarrierWave.deprecator.warn "#extension_whitelist is deprecated, use #extension_allowlist instead." unless instance_variable_defined?(:@extension_whitelist_warned)
|
43
43
|
@extension_whitelist_warned = true
|
44
44
|
allowlist = extension_whitelist
|
45
45
|
end
|
@@ -39,14 +39,14 @@ module CarrierWave
|
|
39
39
|
def check_extension_denylist!(new_file)
|
40
40
|
denylist = extension_denylist
|
41
41
|
if !denylist && respond_to?(:extension_blacklist) && extension_blacklist
|
42
|
-
|
42
|
+
CarrierWave.deprecator.warn "#extension_blacklist is deprecated, use #extension_denylist instead." unless instance_variable_defined?(:@extension_blacklist_warned)
|
43
43
|
@extension_blacklist_warned = true
|
44
44
|
denylist = extension_blacklist
|
45
45
|
end
|
46
46
|
|
47
47
|
return unless denylist
|
48
48
|
|
49
|
-
|
49
|
+
CarrierWave.deprecator.warn "Use of #extension_denylist is deprecated for the security reason, use #extension_allowlist instead to explicitly state what are safe to accept" unless instance_variable_defined?(:@extension_denylist_warned)
|
50
50
|
@extension_denylist_warned = true
|
51
51
|
|
52
52
|
extension = new_file.extension.to_s
|
@@ -14,6 +14,20 @@ module CarrierWave
|
|
14
14
|
@file, @filename, @cache_id, @identifier, @deduplication_index = nil
|
15
15
|
end
|
16
16
|
}
|
17
|
+
|
18
|
+
after :store, :show_warning_when_filename_is_unavailable
|
19
|
+
|
20
|
+
class_attribute :filename_safeguard_checked
|
21
|
+
end
|
22
|
+
|
23
|
+
module ClassMethods
|
24
|
+
private
|
25
|
+
|
26
|
+
def inherited(subclass)
|
27
|
+
# To perform the filename safeguard check once per a class
|
28
|
+
self.filename_safeguard_checked = false
|
29
|
+
super
|
30
|
+
end
|
17
31
|
end
|
18
32
|
|
19
33
|
##
|
@@ -133,6 +147,18 @@ module CarrierWave
|
|
133
147
|
forcing_extension(for_file)
|
134
148
|
end
|
135
149
|
|
150
|
+
def show_warning_when_filename_is_unavailable(_)
|
151
|
+
return if self.class.filename_safeguard_checked
|
152
|
+
self.class.filename_safeguard_checked = true
|
153
|
+
return if filename
|
154
|
+
|
155
|
+
warn <<~MESSAGE
|
156
|
+
[WARNING] Your uploader's #filename method defined at #{method(:filename).source_location.join(':')} didn't return value after storing the file.
|
157
|
+
It's likely that the method is safeguarded with `if original_filename`, which were necessary for pre-3.x CarrierWave but is no longer needed.
|
158
|
+
Removing it is recommended, as it is known to cause issues depending on the use case: https://github.com/carrierwaveuploader/carrierwave/issues/2708
|
159
|
+
MESSAGE
|
160
|
+
end
|
161
|
+
|
136
162
|
def storage
|
137
163
|
@storage ||= self.class.storage.new(self)
|
138
164
|
end
|
@@ -20,7 +20,7 @@ module CarrierWave
|
|
20
20
|
def build(superclass)
|
21
21
|
return @klass if @klass
|
22
22
|
@klass = Class.new(superclass)
|
23
|
-
superclass.const_set("#{@name.to_s.camelize}
|
23
|
+
superclass.const_set("VersionUploader#{@name.to_s.camelize}", @klass)
|
24
24
|
|
25
25
|
@klass.version_names += [@name]
|
26
26
|
@klass.versions = {}
|
data/lib/carrierwave/version.rb
CHANGED
data/lib/carrierwave.rb
CHANGED
@@ -3,6 +3,7 @@ require 'active_support/core_ext/object/blank'
|
|
3
3
|
require 'active_support/core_ext/object/try'
|
4
4
|
require 'active_support/core_ext/class/attribute'
|
5
5
|
require 'active_support/concern'
|
6
|
+
require 'active_support/deprecation'
|
6
7
|
|
7
8
|
module CarrierWave
|
8
9
|
|
@@ -21,6 +22,10 @@ module CarrierWave
|
|
21
22
|
def tmp_path
|
22
23
|
@tmp_path ||= File.expand_path(File.join('..', 'tmp'), root)
|
23
24
|
end
|
25
|
+
|
26
|
+
def deprecator
|
27
|
+
@deprecator ||= ActiveSupport::Deprecation.new("#{CarrierWave::VERSION.split('.')[0].to_i + 1}.0", "CarrierWave")
|
28
|
+
end
|
24
29
|
end
|
25
30
|
|
26
31
|
end
|
@@ -64,6 +69,10 @@ elsif defined?(Rails)
|
|
64
69
|
end
|
65
70
|
end
|
66
71
|
|
72
|
+
initializer "carrierwave.deprecator" do |app|
|
73
|
+
app.deprecators[:carrierwave] = CarrierWave.deprecator if app.respond_to?(:deprecators)
|
74
|
+
end
|
75
|
+
|
67
76
|
config.before_eager_load do
|
68
77
|
CarrierWave::Storage::Fog.eager_load
|
69
78
|
end
|
metadata
CHANGED
@@ -1,14 +1,14 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: carrierwave
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 3.0.
|
4
|
+
version: 3.1.0.beta
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Jonas Nicklas
|
8
8
|
autorequire:
|
9
9
|
bindir: bin
|
10
10
|
cert_chain: []
|
11
|
-
date: 2024-
|
11
|
+
date: 2024-09-01 00:00:00.000000000 Z
|
12
12
|
dependencies:
|
13
13
|
- !ruby/object:Gem::Dependency
|
14
14
|
name: activesupport
|
@@ -226,20 +226,6 @@ dependencies:
|
|
226
226
|
- - ">="
|
227
227
|
- !ruby/object:Gem::Version
|
228
228
|
version: '0'
|
229
|
-
- !ruby/object:Gem::Dependency
|
230
|
-
name: fog-rackspace
|
231
|
-
requirement: !ruby/object:Gem::Requirement
|
232
|
-
requirements:
|
233
|
-
- - ">="
|
234
|
-
- !ruby/object:Gem::Version
|
235
|
-
version: '0'
|
236
|
-
type: :development
|
237
|
-
prerelease: false
|
238
|
-
version_requirements: !ruby/object:Gem::Requirement
|
239
|
-
requirements:
|
240
|
-
- - ">="
|
241
|
-
- !ruby/object:Gem::Version
|
242
|
-
version: '0'
|
243
229
|
- !ruby/object:Gem::Dependency
|
244
230
|
name: mini_magick
|
245
231
|
requirement: !ruby/object:Gem::Requirement
|
@@ -396,9 +382,9 @@ required_ruby_version: !ruby/object:Gem::Requirement
|
|
396
382
|
version: 2.5.0
|
397
383
|
required_rubygems_version: !ruby/object:Gem::Requirement
|
398
384
|
requirements:
|
399
|
-
- - "
|
385
|
+
- - ">"
|
400
386
|
- !ruby/object:Gem::Version
|
401
|
-
version:
|
387
|
+
version: 1.3.1
|
402
388
|
requirements: []
|
403
389
|
rubygems_version: 3.4.10
|
404
390
|
signing_key:
|