carrierwave 2.2.2 → 3.1.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.
Files changed (41) hide show
  1. checksums.yaml +4 -4
  2. data/README.md +180 -62
  3. data/lib/carrierwave/compatibility/paperclip.rb +4 -2
  4. data/lib/carrierwave/downloader/base.rb +28 -14
  5. data/lib/carrierwave/downloader/remote_file.rb +13 -10
  6. data/lib/carrierwave/locale/en.yml +5 -3
  7. data/lib/carrierwave/mount.rb +36 -50
  8. data/lib/carrierwave/mounter.rb +118 -50
  9. data/lib/carrierwave/orm/activerecord.rb +21 -62
  10. data/lib/carrierwave/processing/mini_magick.rb +45 -14
  11. data/lib/carrierwave/processing/rmagick.rb +47 -20
  12. data/lib/carrierwave/processing/vips.rb +43 -12
  13. data/lib/carrierwave/sanitized_file.rb +58 -77
  14. data/lib/carrierwave/storage/abstract.rb +5 -5
  15. data/lib/carrierwave/storage/file.rb +6 -5
  16. data/lib/carrierwave/storage/fog.rb +86 -65
  17. data/lib/carrierwave/test/matchers.rb +11 -7
  18. data/lib/carrierwave/uploader/cache.rb +19 -11
  19. data/lib/carrierwave/uploader/callbacks.rb +1 -1
  20. data/lib/carrierwave/uploader/configuration.rb +18 -8
  21. data/lib/carrierwave/uploader/{content_type_whitelist.rb → content_type_allowlist.rb} +18 -16
  22. data/lib/carrierwave/uploader/{content_type_blacklist.rb → content_type_denylist.rb} +20 -15
  23. data/lib/carrierwave/uploader/dimension.rb +66 -0
  24. data/lib/carrierwave/uploader/{extension_whitelist.rb → extension_allowlist.rb} +17 -15
  25. data/lib/carrierwave/uploader/{extension_blacklist.rb → extension_denylist.rb} +19 -14
  26. data/lib/carrierwave/uploader/file_size.rb +2 -2
  27. data/lib/carrierwave/uploader/processing.rb +45 -7
  28. data/lib/carrierwave/uploader/proxy.rb +16 -3
  29. data/lib/carrierwave/uploader/store.rb +70 -6
  30. data/lib/carrierwave/uploader/url.rb +1 -1
  31. data/lib/carrierwave/uploader/versions.rb +158 -138
  32. data/lib/carrierwave/uploader.rb +10 -8
  33. data/lib/carrierwave/utilities/file_name.rb +47 -0
  34. data/lib/carrierwave/utilities/uri.rb +14 -11
  35. data/lib/carrierwave/utilities.rb +1 -0
  36. data/lib/carrierwave/validations/active_model.rb +4 -6
  37. data/lib/carrierwave/version.rb +1 -1
  38. data/lib/carrierwave.rb +18 -17
  39. data/lib/generators/templates/{uploader.rb → uploader.rb.erb} +1 -1
  40. data/lib/generators/uploader_generator.rb +3 -3
  41. metadata +37 -63
@@ -132,7 +132,7 @@ module CarrierWave
132
132
  # end
133
133
  #
134
134
  def mount_uploader(column, uploader=nil, options={}, &block)
135
- mount_base(column, uploader, options, &block)
135
+ mount_base(column, uploader, options.merge(multiple: false), &block)
136
136
 
137
137
  mod = Module.new
138
138
  include mod
@@ -163,21 +163,13 @@ module CarrierWave
163
163
  end
164
164
 
165
165
  def remote_#{column}_url=(url)
166
- _mounter(:#{column}).remote_urls = [url]
166
+ _mounter(:#{column}).remote_urls = url
167
167
  end
168
168
 
169
169
  def remote_#{column}_request_header=(header)
170
170
  _mounter(:#{column}).remote_request_headers = [header]
171
171
  end
172
172
 
173
- def write_#{column}_identifier
174
- return if frozen?
175
- mounter = _mounter(:#{column})
176
-
177
- mounter.clear! if mounter.remove?
178
- write_uploader(mounter.serialization_column, mounter.identifiers.first)
179
- end
180
-
181
173
  def #{column}_identifier
182
174
  _mounter(:#{column}).read_identifiers[0]
183
175
  end
@@ -193,16 +185,6 @@ module CarrierWave
193
185
  def #{column}_download_error
194
186
  #{column}_download_errors.last
195
187
  end
196
-
197
- def store_previous_changes_for_#{column}
198
- attribute_changes = ::ActiveRecord.version.to_s.to_f >= 5.1 ? saved_changes : changes
199
- @_previous_changes_for_#{column} = attribute_changes[_mounter(:#{column}).serialization_column]
200
- end
201
-
202
- def remove_previously_stored_#{column}
203
- before, after = @_previous_changes_for_#{column}
204
- _mounter(:#{column}).remove_previous([before], [after])
205
- end
206
188
  RUBY
207
189
  end
208
190
 
@@ -295,7 +277,7 @@ module CarrierWave
295
277
  # end
296
278
  #
297
279
  def mount_uploaders(column, uploader=nil, options={}, &block)
298
- mount_base(column, uploader, options, &block)
280
+ mount_base(column, uploader, options.merge(multiple: true), &block)
299
281
 
300
282
  mod = Module.new
301
283
  include mod
@@ -334,35 +316,18 @@ module CarrierWave
334
316
  _mounter(:#{column}).remote_request_headers = headers
335
317
  end
336
318
 
337
- def write_#{column}_identifier
338
- return if frozen?
339
- mounter = _mounter(:#{column})
340
-
341
- mounter.clear! if mounter.remove?
342
- write_uploader(mounter.serialization_column, mounter.identifiers.presence)
343
- end
344
-
345
319
  def #{column}_identifiers
346
320
  _mounter(:#{column}).read_identifiers
347
321
  end
348
-
349
- def store_previous_changes_for_#{column}
350
- attribute_changes = ::ActiveRecord.version.to_s.to_f >= 5.1 ? saved_changes : changes
351
- @_previous_changes_for_#{column} = attribute_changes[_mounter(:#{column}).serialization_column]
352
- end
353
-
354
- def remove_previously_stored_#{column}
355
- _mounter(:#{column}).remove_previous(*@_previous_changes_for_#{column})
356
- end
357
322
  RUBY
358
323
  end
359
324
 
360
- private
325
+ private
361
326
 
362
327
  def mount_base(column, uploader=nil, options={}, &block)
363
328
  include CarrierWave::Mount::Extension
364
329
 
365
- uploader = build_uploader(uploader, &block)
330
+ uploader = build_uploader(uploader, column, &block)
366
331
  uploaders[column.to_sym] = uploader
367
332
  uploader_options[column.to_sym] = options
368
333
 
@@ -387,6 +352,8 @@ module CarrierWave
387
352
 
388
353
  def remove_#{column}!
389
354
  _mounter(:#{column}).remove!
355
+ self.remove_#{column} = true
356
+ write_#{column}_identifier
390
357
  end
391
358
 
392
359
  def remove_#{column}=(value)
@@ -413,22 +380,36 @@ module CarrierWave
413
380
  _mounter(:#{column}).download_errors
414
381
  end
415
382
 
383
+ def write_#{column}_identifier
384
+ _mounter(:#{column}).write_identifier
385
+ end
386
+
416
387
  def mark_remove_#{column}_false
417
388
  _mounter(:#{column}).remove = false
418
389
  end
390
+
391
+ def reset_previous_changes_for_#{column}
392
+ _mounter(:#{column}).reset_changes!
393
+ end
394
+
395
+ def remove_previously_stored_#{column}
396
+ _mounter(:#{column}).remove_previous
397
+ end
398
+
399
+ def remove_rolled_back_#{column}
400
+ _mounter(:#{column}).remove_added
401
+ end
419
402
  RUBY
420
403
  end
421
404
 
422
- def build_uploader(uploader, &block)
423
- return uploader if uploader && !block_given?
405
+ def build_uploader(uploader, column, &block)
406
+ uploader ||= CarrierWave::Uploader::Base
407
+ return uploader unless block_given?
424
408
 
425
- uploader = Class.new(uploader || CarrierWave::Uploader::Base)
426
- const_set("Uploader#{uploader.object_id}".tr('-', '_'), uploader)
409
+ uploader = Class.new(uploader)
410
+ const_set("CarrierWave#{column.to_s.camelize}Uploader", uploader)
427
411
 
428
- if block_given?
429
- uploader.class_eval(&block)
430
- uploader.recursively_apply_block_to_versions(&block)
431
- end
412
+ uploader.class_eval(&block)
432
413
 
433
414
  uploader
434
415
  end
@@ -447,11 +428,16 @@ module CarrierWave
447
428
 
448
429
  private
449
430
 
431
+ def initialize_dup(other)
432
+ @_mounters = @_mounters.dup
433
+ super
434
+ end
435
+
450
436
  def _mounter(column)
451
437
  # We cannot memoize in frozen objects :(
452
- return Mounter.new(self, column) if frozen?
438
+ return Mounter.build(self, column) if frozen?
453
439
  @_mounters ||= {}
454
- @_mounters[column] ||= Mounter.new(self, column)
440
+ @_mounters[column] ||= Mounter.build(self, column)
455
441
  end
456
442
 
457
443
  end # Extension
@@ -2,18 +2,49 @@ module CarrierWave
2
2
 
3
3
  # this is an internal class, used by CarrierWave::Mount so that
4
4
  # we don't pollute the model with a lot of methods.
5
- class Mounter #:nodoc:
6
- attr_reader :column, :record, :remote_urls, :integrity_errors,
7
- :processing_errors, :download_errors
8
- attr_accessor :remove, :remote_request_headers
5
+ class Mounter # :nodoc:
6
+ class Single < Mounter # :nodoc
7
+ def identifier
8
+ uploaders.first&.identifier
9
+ end
10
+
11
+ def temporary_identifier
12
+ temporary_identifiers.first
13
+ end
14
+ end
15
+
16
+ class Multiple < Mounter # :nodoc
17
+ def identifier
18
+ uploaders.map(&:identifier).presence
19
+ end
20
+
21
+ def temporary_identifier
22
+ temporary_identifiers.presence
23
+ end
24
+ end
25
+
26
+ def self.build(record, column)
27
+ if record.class.uploader_options[column][:multiple]
28
+ Multiple.new(record, column)
29
+ else
30
+ Single.new(record, column)
31
+ end
32
+ end
9
33
 
10
- def initialize(record, column, options={})
34
+ attr_reader :column, :record, :remote_urls, :remove,
35
+ :integrity_errors, :processing_errors, :download_errors
36
+ attr_accessor :remote_request_headers, :uploader_options
37
+
38
+ def initialize(record, column)
11
39
  @record = record
12
40
  @column = column
13
41
  @options = record.class.uploader_options[column]
14
42
  @download_errors = []
15
43
  @processing_errors = []
16
44
  @integrity_errors = []
45
+
46
+ @removed_uploaders = []
47
+ @added_uploaders = []
17
48
  end
18
49
 
19
50
  def uploader_class
@@ -35,7 +66,7 @@ module CarrierWave
35
66
  def uploaders
36
67
  @uploaders ||= read_identifiers.map do |identifier|
37
68
  uploader = blank_uploader
38
- uploader.retrieve_from_store!(identifier) if identifier.present?
69
+ uploader.retrieve_from_store!(identifier)
39
70
  uploader
40
71
  end
41
72
  end
@@ -46,7 +77,7 @@ module CarrierWave
46
77
  @uploaders = new_files.map do |new_file|
47
78
  handle_error do
48
79
  if new_file.is_a?(String)
49
- if (uploader = old_uploaders.detect { |uploader| uploader.identifier == new_file })
80
+ if (uploader = old_uploaders.detect { |old_uploader| old_uploader.identifier == new_file })
50
81
  uploader.staged = true
51
82
  uploader
52
83
  else
@@ -64,7 +95,9 @@ module CarrierWave
64
95
  uploader
65
96
  end
66
97
  end
67
- end.compact
98
+ end.reject(&:blank?)
99
+ @removed_uploaders += (old_uploaders - @uploaders)
100
+ write_temporary_identifier
68
101
  end
69
102
 
70
103
  def cache_names
@@ -76,33 +109,54 @@ module CarrierWave
76
109
  return if cache_names.blank?
77
110
  clear_unstaged
78
111
  cache_names.each do |cache_name|
79
- begin
80
- uploader = blank_uploader
81
- uploader.retrieve_from_cache!(cache_name)
82
- @uploaders << uploader
83
- rescue CarrierWave::InvalidParameter
84
- # ignore
85
- end
112
+ uploader = blank_uploader
113
+ uploader.retrieve_from_cache!(cache_name)
114
+ @uploaders << uploader
115
+ rescue CarrierWave::InvalidParameter
116
+ # ignore
86
117
  end
118
+ write_temporary_identifier
87
119
  end
88
120
 
89
121
  def remote_urls=(urls)
90
- return if urls.blank? || urls.all?(&:blank?)
91
-
122
+ if urls.nil?
123
+ urls = []
124
+ else
125
+ urls = Array.wrap(urls).reject(&:blank?)
126
+ return if urls.blank?
127
+ end
128
+ @download_errors.clear
92
129
  @remote_urls = urls
93
130
 
94
131
  clear_unstaged
95
- urls.zip(remote_request_headers || []).each do |url, header|
132
+ @remote_urls.zip(remote_request_headers || []) do |url, header|
96
133
  handle_error do
97
134
  uploader = blank_uploader
98
135
  uploader.download!(url, header || {})
99
136
  @uploaders << uploader
100
137
  end
101
138
  end
139
+ write_temporary_identifier
102
140
  end
103
141
 
104
142
  def store!
105
- uploaders.reject(&:blank?).each(&:store!)
143
+ uploaders.each(&:store!)
144
+ end
145
+
146
+ def write_identifier
147
+ return if record.frozen?
148
+
149
+ clear! if remove?
150
+
151
+ additions, remains = uploaders.partition(&:cached?)
152
+ existing_identifiers = (@removed_uploaders + remains).map(&:identifier)
153
+ additions.each do |uploader|
154
+ uploader.deduplicate(existing_identifiers)
155
+ existing_identifiers << uploader.identifier
156
+ end
157
+ @added_uploaders += additions
158
+
159
+ record.write_uploader(serialization_column, identifier)
106
160
  end
107
161
 
108
162
  def urls(*args)
@@ -113,52 +167,50 @@ module CarrierWave
113
167
  uploaders.none?(&:present?)
114
168
  end
115
169
 
170
+ def remove=(value)
171
+ @remove = value
172
+ write_temporary_identifier
173
+ end
174
+
116
175
  def remove?
117
- remove.present? && (remove == true || remove !~ /\A0|false$\z/)
176
+ remove.present? && (remove.to_s !~ /\A0|false$\z/)
118
177
  end
119
178
 
120
179
  def remove!
121
- uploaders.reject(&:blank?).each(&:remove!)
122
- @uploaders = []
180
+ uploaders.each(&:remove!)
181
+ clear!
123
182
  end
124
183
 
125
184
  def clear!
185
+ @removed_uploaders += uploaders
186
+ @remove = nil
126
187
  @uploaders = []
127
188
  end
128
189
 
190
+ def reset_changes!
191
+ @removed_uploaders = []
192
+ @added_uploaders = []
193
+ end
194
+
129
195
  def serialization_column
130
196
  option(:mount_on) || column
131
197
  end
132
198
 
133
- def remove_previous(before=nil, after=nil)
134
- after ||= []
135
- return unless before
136
-
137
- # both 'before' and 'after' can be string when 'mount_on' option is set
138
- before = before.reject(&:blank?).map do |value|
139
- if value.is_a?(String)
140
- uploader = blank_uploader
141
- uploader.retrieve_from_store!(value)
142
- uploader
143
- else
144
- value
145
- end
146
- end
147
- after_paths = after.reject(&:blank?).map do |value|
148
- if value.is_a?(String)
149
- uploader = blank_uploader
150
- uploader.retrieve_from_store!(value)
151
- uploader
152
- else
153
- value
154
- end.path
155
- end
156
- before.each do |uploader|
157
- uploader.remove! if uploader.remove_previously_stored_files_after_update && !after_paths.include?(uploader.path)
158
- end
199
+ def remove_previous
200
+ current_paths = uploaders.map(&:path)
201
+ @removed_uploaders
202
+ .reject {|uploader| current_paths.include?(uploader.path) }
203
+ .each { |uploader| uploader.remove! if uploader.remove_previously_stored_files_after_update }
204
+ reset_changes!
159
205
  end
160
206
 
161
- attr_accessor :uploader_options
207
+ def remove_added
208
+ current_paths = (@removed_uploaders + uploaders.select(&:staged)).map(&:path)
209
+ @added_uploaders
210
+ .reject {|uploader| current_paths.include?(uploader.path) }
211
+ .each { |uploader| uploader.remove! }
212
+ reset_changes!
213
+ end
162
214
 
163
215
  private
164
216
 
@@ -169,7 +221,9 @@ module CarrierWave
169
221
 
170
222
  def clear_unstaged
171
223
  @uploaders ||= []
172
- @uploaders.keep_if(&:staged)
224
+ staged, unstaged = @uploaders.partition(&:staged)
225
+ @uploaders = staged
226
+ @removed_uploaders += unstaged
173
227
  end
174
228
 
175
229
  def handle_error
@@ -184,5 +238,19 @@ module CarrierWave
184
238
  @integrity_errors << e
185
239
  raise e unless option(:ignore_integrity_errors)
186
240
  end
241
+
242
+ def write_temporary_identifier
243
+ return if record.frozen?
244
+
245
+ record.write_uploader(serialization_column, temporary_identifier)
246
+ end
247
+
248
+ def temporary_identifiers
249
+ if remove?
250
+ []
251
+ else
252
+ uploaders.map { |uploader| uploader.temporary_identifier }
253
+ end
254
+ end
187
255
  end # Mounter
188
256
  end # CarrierWave
@@ -6,40 +6,6 @@ module CarrierWave
6
6
 
7
7
  include CarrierWave::Mount
8
8
 
9
- ##
10
- # See +CarrierWave::Mount#mount_uploader+ for documentation
11
- #
12
- def mount_uploader(column, uploader=nil, options={}, &block)
13
- super
14
-
15
- mod = Module.new
16
- prepend mod
17
- mod.class_eval <<-RUBY, __FILE__, __LINE__+1
18
- def remote_#{column}_url=(url)
19
- column = _mounter(:#{column}).serialization_column
20
- __send__(:"\#{column}_will_change!")
21
- super
22
- end
23
- RUBY
24
- end
25
-
26
- ##
27
- # See +CarrierWave::Mount#mount_uploaders+ for documentation
28
- #
29
- def mount_uploaders(column, uploader=nil, options={}, &block)
30
- super
31
-
32
- mod = Module.new
33
- prepend mod
34
- mod.class_eval <<-RUBY, __FILE__, __LINE__+1
35
- def remote_#{column}_urls=(url)
36
- column = _mounter(:#{column}).serialization_column
37
- __send__(:"\#{column}_will_change!")
38
- super
39
- end
40
- RUBY
41
- end
42
-
43
9
  private
44
10
 
45
11
  def mount_base(column, uploader=nil, options={}, &block)
@@ -56,39 +22,23 @@ module CarrierWave
56
22
  validates_processing_of column if uploader_option(column.to_sym, :validate_processing)
57
23
  validates_download_of column if uploader_option(column.to_sym, :validate_download)
58
24
 
25
+ after_save :"store_#{column}!"
59
26
  before_save :"write_#{column}_identifier"
60
- after_save :"store_previous_changes_for_#{column}"
27
+ if ::ActiveRecord.try(:run_after_transaction_callbacks_in_order_defined)
28
+ after_commit :"remove_previously_stored_#{column}", :on => :update
29
+ after_commit :"reset_previous_changes_for_#{column}"
30
+ after_commit :"mark_remove_#{column}_false", :on => :update
31
+ else
32
+ after_commit :"mark_remove_#{column}_false", :on => :update
33
+ after_commit :"reset_previous_changes_for_#{column}"
34
+ after_commit :"remove_previously_stored_#{column}", :on => :update
35
+ end
61
36
  after_commit :"remove_#{column}!", :on => :destroy
62
- after_commit :"mark_remove_#{column}_false", :on => :update
63
- after_commit :"remove_previously_stored_#{column}", :on => :update
64
- after_commit :"store_#{column}!", :on => [:create, :update]
37
+ after_rollback :"remove_rolled_back_#{column}"
65
38
 
66
39
  mod = Module.new
67
40
  prepend mod
68
41
  mod.class_eval <<-RUBY, __FILE__, __LINE__+1
69
- def #{column}=(new_file)
70
- column = _mounter(:#{column}).serialization_column
71
- if !(new_file.blank? && __send__(:#{column}).blank?)
72
- __send__(:"\#{column}_will_change!")
73
- end
74
-
75
- super
76
- end
77
-
78
- def remove_#{column}=(value)
79
- column = _mounter(:#{column}).serialization_column
80
- result = super
81
- __send__(:"\#{column}_will_change!") if _mounter(:#{column}).remove?
82
- result
83
- end
84
-
85
- def remove_#{column}!
86
- self.remove_#{column} = true
87
- write_#{column}_identifier
88
- self.remove_#{column} = false
89
- super
90
- end
91
-
92
42
  # Reset cached mounter on record reload
93
43
  def reload(*)
94
44
  @_mounters = nil
@@ -97,7 +47,16 @@ module CarrierWave
97
47
 
98
48
  # Reset cached mounter on record dup
99
49
  def initialize_dup(other)
100
- @_mounters = nil
50
+ old_uploaders = _mounter(:"#{column}").uploaders
51
+ super
52
+ @_mounters[:"#{column}"] = nil
53
+ # The attribute needs to be cleared to prevent it from picked up as identifier
54
+ write_attribute(_mounter(:#{column}).serialization_column, nil)
55
+ _mounter(:"#{column}").cache(old_uploaders)
56
+ end
57
+
58
+ def write_#{column}_identifier
59
+ return unless has_attribute?(_mounter(:#{column}).serialization_column)
101
60
  super
102
61
  end
103
62
  RUBY
@@ -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
  ##
@@ -88,7 +92,7 @@ module CarrierWave
88
92
  #
89
93
  # === Parameters
90
94
  #
91
- # [format (#to_s)] an abreviation of the format
95
+ # [format (#to_s)] an abbreviation of the format
92
96
  #
93
97
  # === Yields
94
98
  #
@@ -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
  #
@@ -262,9 +291,10 @@ module CarrierWave
262
291
  image = yield(image)
263
292
  FileUtils.mv image.path, current_path
264
293
 
265
- image.run_command("identify", current_path)
294
+ ::MiniMagick::Image.new(current_path).identify
266
295
  rescue ::MiniMagick::Error, ::MiniMagick::Invalid => e
267
- message = I18n.translate(:"errors.messages.mini_magick_processing_error", :e => e)
296
+ raise e if e.message =~ /(You must have .+ installed|is not installed|executable not found)/
297
+ message = I18n.translate(:"errors.messages.processing_error")
268
298
  raise CarrierWave::ProcessingError, message
269
299
  ensure
270
300
  image.destroy! if image
@@ -306,26 +336,27 @@ module CarrierWave
306
336
 
307
337
  if File.extname(result.path) != File.extname(current_path)
308
338
  move_to = current_path.chomp(File.extname(current_path)) + File.extname(result.path)
309
- file.content_type = ::MiniMime.lookup_by_filename(move_to).content_type
339
+ file.content_type = Marcel::Magic.by_path(move_to).try(:type)
310
340
  file.move_to(move_to, permissions, directory_permissions)
311
341
  end
312
342
  rescue ::MiniMagick::Error, ::MiniMagick::Invalid => e
313
- message = I18n.translate(:"errors.messages.mini_magick_processing_error", :e => e)
343
+ raise e if e.message =~ /(You must have .+ installed|is not installed|executable not found)/
344
+ message = I18n.translate(:"errors.messages.processing_error")
314
345
  raise CarrierWave::ProcessingError, message
315
346
  end
316
347
 
317
- private
348
+ private
318
349
 
319
- def resolve_dimensions(*dimensions)
320
- dimensions.map do |value|
321
- next value unless value.instance_of?(Proc)
322
- value.arity >= 1 ? value.call(self) : value.call
323
- end
350
+ def resolve_dimensions(*dimensions)
351
+ dimensions.map do |value|
352
+ next value unless value.instance_of?(Proc)
353
+ value.arity >= 1 ? value.call(self) : value.call
324
354
  end
355
+ end
325
356
 
326
- def mini_magick_image
327
- ::MiniMagick::Image.read(read)
328
- end
357
+ def mini_magick_image
358
+ ::MiniMagick::Image.read(read)
359
+ end
329
360
 
330
361
  end # MiniMagick
331
362
  end # CarrierWave