Commit 654f17a944eeda67088ceee8b5de763a6f7fda06

Authored by Antonio Terceiro
1 parent 7c606c01

UploadedFile: support site-wide configuration of max upload size

Configuration is done in config/noosfero.yml, key `max_upload_size`.
Supported value formats: 1KB, 1MB, 1GB, 1TB. MB is the default if the
unit is omitted.

5MB is still the default and will be used in case no configuration -- or
an invalid value -- is supplied.

Based on the original implementation proposal by Aurélio A. Heckert at
https://gitorious.org/noosfero/noosfero/merge_requests/345

ActionItem1780
app/models/uploaded_file.rb
... ... @@ -41,7 +41,25 @@ class UploadedFile < Article
41 41 end
42 42  
43 43 def self.max_size
44   - UploadedFile.attachment_options[:max_size]
  44 + default = 5.megabytes
  45 +
  46 + multipliers = {
  47 + :KB => :kilobytes,
  48 + :MB => :megabytes,
  49 + :GB => :gigabytes,
  50 + :TB => :terabytes,
  51 + }
  52 + max_upload_size = NOOSFERO_CONF['max_upload_size']
  53 +
  54 + if max_upload_size =~ /^(\d+(\.\d+)?)\s*(KB|MB|GB|TB)?$/
  55 + number = $1.to_f
  56 + unit = $3 || :MB
  57 + multiplier = multipliers[unit.to_sym]
  58 +
  59 + number.send(multiplier).to_i
  60 + else
  61 + default
  62 + end
45 63 end
46 64  
47 65 # FIXME need to define min/max file size
... ... @@ -52,9 +70,9 @@ class UploadedFile < Article
52 70 has_attachment :storage => :file_system,
53 71 :thumbnails => { :icon => [24,24], :thumb => '130x130>', :slideshow => '320x240>', :display => '640X480>' },
54 72 :thumbnail_class => Thumbnail,
55   - :max_size => 5.megabytes # remember to update validate message below
  73 + :max_size => self.max_size
56 74  
57   - validates_attachment :size => N_("%{fn} of uploaded file was larger than the maximum size of 5.0 MB").fix_i18n
  75 + validates_attachment :size => N_("%{fn} of uploaded file was larger than the maximum size of %{size}").sub('%{size}', self.max_size.to_humanreadable).fix_i18n
58 76  
59 77 delay_attachment_fu_thumbnails
60 78  
... ...
config/noosfero.yml.dist
... ... @@ -8,6 +8,7 @@ development:
8 8 gravatar: wavatar
9 9 googlemaps_initial_zoom: 4
10 10 exception_recipients: [admin@example.com]
  11 + max_upload_size: 5MB
11 12  
12 13 test:
13 14  
... ...
test/unit/uploaded_file_test.rb
... ... @@ -352,4 +352,26 @@ class UploadedFileTest < ActiveSupport::TestCase
352 352 assert_equal 1, ActionTracker::Record.find_all_by_verb('upload_image').count
353 353 end
354 354  
  355 + {
  356 + nil => 5.megabytes, # default
  357 + '1KB' => 1.kilobytes,
  358 + '2MB' => 2.megabyte,
  359 + '3GB' => 3.gigabytes,
  360 + '4TB' => 4.terabytes,
  361 + '6 MB' => 6.megabytes, # allow whitespace between number and unit
  362 + '0.5 GB' => 512.megabytes, # allow floating point numbers
  363 + '2' => 2.megabytes, # assume MB as unit by default
  364 + 'INVALID' => 5.megabytes, # use default for invalid input
  365 + '1ZYX' => 5.megabytes, # use default for invalid input
  366 + }.each do |input,output|
  367 + test 'maximum upload size: convert %s into %s' % [input, output] do
  368 + NOOSFERO_CONF.expects(:[]).with('max_upload_size').returns(input)
  369 + assert_equal output, UploadedFile.max_size
  370 + end
  371 + end
  372 + test 'max_size should always return an integer' do
  373 + NOOSFERO_CONF.expects(:[]).with('max_upload_size').returns("0.5 GB")
  374 + assert_instance_of Fixnum, UploadedFile.max_size
  375 + end
  376 +
355 377 end
... ...