kt-paperclip 4.4.0 → 5.4.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 (112) hide show
  1. checksums.yaml +4 -4
  2. data/.codeclimate.yml +17 -0
  3. data/.hound.yml +5 -16
  4. data/.travis.yml +15 -12
  5. data/Appraisals +4 -8
  6. data/CONTRIBUTING.md +16 -5
  7. data/Gemfile +3 -8
  8. data/LICENSE +1 -1
  9. data/NEWS +105 -31
  10. data/README.md +239 -153
  11. data/Rakefile +1 -1
  12. data/UPGRADING +12 -9
  13. data/features/basic_integration.feature +3 -2
  14. data/features/migration.feature +0 -24
  15. data/features/step_definitions/attachment_steps.rb +6 -6
  16. data/features/step_definitions/rails_steps.rb +29 -28
  17. data/features/step_definitions/s3_steps.rb +2 -2
  18. data/features/support/env.rb +1 -0
  19. data/features/support/paths.rb +1 -1
  20. data/features/support/rails.rb +0 -24
  21. data/gemfiles/4.2.gemfile +3 -5
  22. data/gemfiles/{3.2.gemfile → 5.0.gemfile} +4 -6
  23. data/lib/generators/paperclip/paperclip_generator.rb +9 -1
  24. data/lib/generators/paperclip/templates/paperclip_migration.rb.erb +1 -1
  25. data/lib/paperclip/attachment.rb +25 -14
  26. data/lib/paperclip/attachment_registry.rb +2 -1
  27. data/lib/paperclip/callbacks.rb +8 -6
  28. data/lib/paperclip/content_type_detector.rb +3 -2
  29. data/lib/paperclip/errors.rb +3 -1
  30. data/lib/paperclip/file_command_content_type_detector.rb +1 -1
  31. data/lib/paperclip/geometry_detector_factory.rb +2 -2
  32. data/lib/paperclip/glue.rb +1 -1
  33. data/lib/paperclip/has_attached_file.rb +7 -1
  34. data/lib/paperclip/helpers.rb +15 -11
  35. data/lib/paperclip/interpolations.rb +1 -1
  36. data/lib/paperclip/io_adapters/abstract_adapter.rb +29 -3
  37. data/lib/paperclip/io_adapters/attachment_adapter.rb +10 -5
  38. data/lib/paperclip/io_adapters/data_uri_adapter.rb +8 -8
  39. data/lib/paperclip/io_adapters/empty_string_adapter.rb +5 -4
  40. data/lib/paperclip/io_adapters/file_adapter.rb +12 -6
  41. data/lib/paperclip/io_adapters/http_url_proxy_adapter.rb +7 -7
  42. data/lib/paperclip/io_adapters/identity_adapter.rb +12 -6
  43. data/lib/paperclip/io_adapters/nil_adapter.rb +8 -5
  44. data/lib/paperclip/io_adapters/registry.rb +6 -2
  45. data/lib/paperclip/io_adapters/stringio_adapter.rb +9 -6
  46. data/lib/paperclip/io_adapters/uploaded_file_adapter.rb +10 -6
  47. data/lib/paperclip/io_adapters/uri_adapter.rb +17 -14
  48. data/lib/paperclip/matchers/validate_attachment_content_type_matcher.rb +4 -4
  49. data/lib/paperclip/media_type_spoof_detector.rb +3 -2
  50. data/lib/paperclip/processor.rb +5 -4
  51. data/lib/paperclip/schema.rb +4 -10
  52. data/lib/paperclip/storage/filesystem.rb +13 -2
  53. data/lib/paperclip/storage/fog.rb +19 -13
  54. data/lib/paperclip/storage/s3.rb +87 -58
  55. data/lib/paperclip/thumbnail.rb +18 -8
  56. data/lib/paperclip/url_generator.rb +18 -14
  57. data/lib/paperclip/validators/attachment_size_validator.rb +1 -7
  58. data/lib/paperclip/validators.rb +1 -1
  59. data/lib/paperclip/version.rb +3 -1
  60. data/lib/paperclip.rb +13 -12
  61. data/lib/tasks/paperclip.rake +18 -4
  62. data/paperclip.gemspec +13 -11
  63. data/spec/paperclip/attachment_processing_spec.rb +2 -4
  64. data/spec/paperclip/attachment_registry_spec.rb +28 -0
  65. data/spec/paperclip/attachment_spec.rb +72 -18
  66. data/spec/paperclip/content_type_detector_spec.rb +1 -1
  67. data/spec/paperclip/file_command_content_type_detector_spec.rb +15 -1
  68. data/spec/paperclip/has_attached_file_spec.rb +24 -8
  69. data/spec/paperclip/integration_spec.rb +4 -3
  70. data/spec/paperclip/io_adapters/abstract_adapter_spec.rb +76 -22
  71. data/spec/paperclip/io_adapters/attachment_adapter_spec.rb +6 -3
  72. data/spec/paperclip/io_adapters/data_uri_adapter_spec.rb +7 -1
  73. data/spec/paperclip/io_adapters/file_adapter_spec.rb +2 -2
  74. data/spec/paperclip/io_adapters/http_url_proxy_adapter_spec.rb +18 -1
  75. data/spec/paperclip/io_adapters/identity_adapter_spec.rb +1 -1
  76. data/spec/paperclip/io_adapters/registry_spec.rb +2 -2
  77. data/spec/paperclip/io_adapters/stringio_adapter_spec.rb +1 -1
  78. data/spec/paperclip/io_adapters/uploaded_file_adapter_spec.rb +5 -5
  79. data/spec/paperclip/io_adapters/uri_adapter_spec.rb +48 -3
  80. data/spec/paperclip/matchers/validate_attachment_content_type_matcher_spec.rb +10 -0
  81. data/spec/paperclip/media_type_spoof_detector_spec.rb +15 -0
  82. data/spec/paperclip/paperclip_spec.rb +15 -45
  83. data/spec/paperclip/processor_spec.rb +4 -4
  84. data/spec/paperclip/storage/fog_spec.rb +26 -0
  85. data/spec/paperclip/storage/s3_live_spec.rb +20 -14
  86. data/spec/paperclip/storage/s3_spec.rb +357 -190
  87. data/spec/paperclip/tempfile_spec.rb +35 -0
  88. data/spec/paperclip/thumbnail_spec.rb +38 -35
  89. data/spec/paperclip/url_generator_spec.rb +53 -42
  90. data/spec/paperclip/validators/attachment_size_validator_spec.rb +26 -20
  91. data/spec/paperclip/validators_spec.rb +5 -5
  92. data/spec/spec_helper.rb +6 -2
  93. data/spec/support/assertions.rb +12 -1
  94. data/spec/support/conditional_filter_helper.rb +5 -0
  95. data/spec/support/mock_attachment.rb +2 -0
  96. data/spec/support/mock_url_generator_builder.rb +2 -2
  97. data/spec/support/model_reconstruction.rb +10 -2
  98. data/spec/support/reporting.rb +11 -0
  99. metadata +69 -75
  100. data/cucumber/paperclip_steps.rb +0 -6
  101. data/gemfiles/4.1.gemfile +0 -19
  102. data/lib/paperclip/deprecations.rb +0 -42
  103. data/lib/paperclip/locales/de.yml +0 -18
  104. data/lib/paperclip/locales/es.yml +0 -18
  105. data/lib/paperclip/locales/ja.yml +0 -18
  106. data/lib/paperclip/locales/pt-BR.yml +0 -18
  107. data/lib/paperclip/locales/zh-CN.yml +0 -18
  108. data/lib/paperclip/locales/zh-HK.yml +0 -18
  109. data/lib/paperclip/locales/zh-TW.yml +0 -18
  110. data/spec/paperclip/deprecations_spec.rb +0 -65
  111. data/spec/support/deprecations.rb +0 -9
  112. data/spec/support/rails_helpers.rb +0 -7
data/Rakefile CHANGED
@@ -9,7 +9,7 @@ task :default => [:clean, :all]
9
9
  desc 'Test the paperclip plugin under all supported Rails versions.'
10
10
  task :all do |t|
11
11
  if ENV['BUNDLE_GEMFILE']
12
- exec('rake spec cucumber')
12
+ exec('rake spec && cucumber')
13
13
  else
14
14
  exec("rm -f gemfiles/*.lock")
15
15
  Rake::Task["appraisal:gemfiles"].execute
data/UPGRADING CHANGED
@@ -1,14 +1,17 @@
1
1
  ##################################################
2
- # NOTE FOR UPGRADING FROM PRE-3.0 VERSION #
2
+ # NOTE FOR UPGRADING FROM 4.3.0 OR EARLIER #
3
3
  ##################################################
4
4
 
5
- Paperclip 3.0 introduces a non-backward compatible change in your attachment
6
- path. This will help to prevent attachment name clashes when you have
7
- multiple attachments with the same name. If you didn't alter your
8
- attachment's path and are using Paperclip's default, you'll have to add
9
- `:path` and `:url` to your `has_attached_file` definition. For example:
5
+ Paperclip is now compatible with aws-sdk >= 2.0.0.
10
6
 
11
- has_attached_file :avatar,
12
- :path => ":rails_root/public/system/:attachment/:id/:style/:filename",
13
- :url => "/system/:attachment/:id/:style/:filename"
7
+ If you are using S3 storage, aws-sdk >= 2.0.0 requires you to make a few small
8
+ changes:
14
9
 
10
+ * You must set the `s3_region`
11
+ * If you are explicitly setting permissions anywhere, such as in an initializer,
12
+ note that the format of the permissions changed from using an underscore to
13
+ using a hyphen. For example, `:public_read` needs to be changed to
14
+ `public-read`.
15
+
16
+ For a walkthrough of upgrading from 4 to 5 and aws-sdk >= 2.0 you can watch
17
+ http://rubythursday.com/episodes/ruby-snack-27-upgrade-paperclip-and-aws-sdk-in-prep-for-rails-5
@@ -69,6 +69,7 @@ Feature: Rails integration
69
69
  bucket: paperclip
70
70
  access_key_id: access_key
71
71
  secret_access_key: secret_key
72
+ s3_region: us-west-2
72
73
  """
73
74
  And I start the rails application
74
75
  When I go to the new user page
@@ -76,5 +77,5 @@ Feature: Rails integration
76
77
  And I attach the file "spec/support/fixtures/5k.png" to "Attachment" on S3
77
78
  And I press "Submit"
78
79
  Then I should see "Name: something"
79
- And I should see an image with a path of "http://s3.amazonaws.com/paperclip/attachments/original/5k.png"
80
- And the file at "http://s3.amazonaws.com/paperclip/attachments/original/5k.png" should be uploaded to S3
80
+ And I should see an image with a path of "//s3.amazonaws.com/paperclip/attachments/original/5k.png"
81
+ And the file at "//s3.amazonaws.com/paperclip/attachments/original/5k.png" should be uploaded to S3
@@ -68,27 +68,3 @@ Feature: Migration
68
68
 
69
69
  When I rollback a migration
70
70
  Then I should not have attachment columns for "avatar"
71
-
72
- Scenario: Rails 3.2 change method
73
- Given I am using Rails newer than 3.1
74
- When I write to "db/migrate/01_create_users.rb" with:
75
- """
76
- class CreateUsers < ActiveRecord::Migration
77
- def self.up
78
- create_table :users
79
- end
80
- end
81
- """
82
- When I write to "db/migrate/02_add_attachment_to_users.rb" with:
83
- """
84
- class AddAttachmentToUsers < ActiveRecord::Migration
85
- def change
86
- add_attachment :users, :avatar
87
- end
88
- end
89
- """
90
- And I run a migration
91
- Then I should have attachment columns for "avatar"
92
-
93
- When I rollback a migration
94
- Then I should not have attachment columns for "avatar"
@@ -23,7 +23,7 @@ When /^I modify my attachment definition to:$/ do |definition|
23
23
  end
24
24
 
25
25
  When /^I upload the fixture "([^"]*)"$/ do |filename|
26
- run_simple %(bundle exec #{runner_command} "User.create!(:attachment => File.open('#{fixture_path(filename)}'))")
26
+ run_simple %(bundle exec rails runner "User.create!(:attachment => File.open('#{fixture_path(filename)}'))")
27
27
  end
28
28
 
29
29
  Then /^the attachment "([^"]*)" should have a dimension of (\d+x\d+)$/ do |filename, dimension|
@@ -56,7 +56,7 @@ Then /^the attachment should have the same content type as the fixture "([^"]*)"
56
56
  require "mime/types"
57
57
  end
58
58
 
59
- attachment_content_type = `bundle exec #{runner_command} "puts User.last.attachment_content_type"`.strip
59
+ attachment_content_type = `bundle exec rails runner "puts User.last.attachment_content_type"`.strip
60
60
  expected = MIME::Types.type_for(filename).first.content_type
61
61
  expect(attachment_content_type).to eq(expected)
62
62
  end
@@ -64,14 +64,14 @@ end
64
64
 
65
65
  Then /^the attachment should have the same file name as the fixture "([^"]*)"$/ do |filename|
66
66
  cd(".") do
67
- attachment_file_name = `bundle exec #{runner_command} "puts User.last.attachment_file_name"`.strip
67
+ attachment_file_name = `bundle exec rails runner "puts User.last.attachment_file_name"`.strip
68
68
  expect(attachment_file_name).to eq(File.name(fixture_path(filename)).to_s)
69
69
  end
70
70
  end
71
71
 
72
72
  Then /^the attachment should have the same file size as the fixture "([^"]*)"$/ do |filename|
73
73
  cd(".") do
74
- attachment_file_size = `bundle exec #{runner_command} "puts User.last.attachment_file_size"`.strip
74
+ attachment_file_size = `bundle exec rails runner "puts User.last.attachment_file_size"`.strip
75
75
  expect(attachment_file_size).to eq(File.size(fixture_path(filename)).to_s)
76
76
  end
77
77
  end
@@ -84,7 +84,7 @@ end
84
84
 
85
85
  Then /^I should have attachment columns for "([^"]*)"$/ do |attachment_name|
86
86
  cd(".") do
87
- columns = eval(`bundle exec #{runner_command} "puts User.columns.map{ |column| [column.name, column.type] }.inspect"`.strip)
87
+ columns = eval(`bundle exec rails runner "puts User.columns.map{ |column| [column.name, column.type] }.inspect"`.strip)
88
88
  expect_columns = [
89
89
  ["#{attachment_name}_file_name", :string],
90
90
  ["#{attachment_name}_content_type", :string],
@@ -97,7 +97,7 @@ end
97
97
 
98
98
  Then /^I should not have attachment columns for "([^"]*)"$/ do |attachment_name|
99
99
  cd(".") do
100
- columns = eval(`bundle exec #{runner_command} "puts User.columns.map{ |column| [column.name, column.type] }.inspect"`.strip)
100
+ columns = eval(`bundle exec rails runner "puts User.columns.map{ |column| [column.name, column.type] }.inspect"`.strip)
101
101
  expect_columns = [
102
102
  ["#{attachment_name}_file_name", :string],
103
103
  ["#{attachment_name}_content_type", :string],
@@ -1,34 +1,33 @@
1
1
  Given /^I generate a new rails application$/ do
2
2
  steps %{
3
- When I run `bundle exec #{new_application_command} #{APP_NAME} --skip-bundle`
3
+ When I successfully run `rails new #{APP_NAME} --skip-bundle`
4
4
  And I cd to "#{APP_NAME}"
5
+ }
6
+
7
+ FileUtils.chdir("tmp/aruba/testapp/")
8
+
9
+ steps %{
5
10
  And I turn off class caching
6
- And I fix the application.rb for 3.0.12
7
11
  And I write to "Gemfile" with:
8
12
  """
9
13
  source "http://rubygems.org"
10
14
  gem "rails", "#{framework_version}"
11
- gem "sqlite3", "1.3.8", :platform => [:ruby, :rbx]
15
+ gem "sqlite3", :platform => [:ruby, :rbx]
12
16
  gem "activerecord-jdbcsqlite3-adapter", :platform => :jruby
13
17
  gem "jruby-openssl", :platform => :jruby
14
18
  gem "capybara"
15
19
  gem "gherkin"
16
- gem "aws-sdk"
20
+ gem "aws-sdk", "~> 2.0.0"
17
21
  gem "racc", :platform => :rbx
18
22
  gem "rubysl", :platform => :rbx
19
23
  """
20
24
  And I remove turbolinks
25
+ And I comment out lines that contain "action_mailer" in "config/environments/*.rb"
21
26
  And I empty the application.js file
22
27
  And I configure the application to use "paperclip" from this project
23
28
  }
24
- end
25
29
 
26
- Given "I fix the application.rb for 3.0.12" do
27
- cd(".") do
28
- File.open("config/application.rb", "a") do |f|
29
- f << "ActionController::Base.config.relative_url_root = ''"
30
- end
31
- end
30
+ FileUtils.chdir("../../..")
32
31
  end
33
32
 
34
33
  Given "I allow the attachment to be submitted" do
@@ -51,6 +50,16 @@ Given "I remove turbolinks" do
51
50
  end
52
51
  end
53
52
 
53
+ Given /^I comment out lines that contain "([^"]+)" in "([^"]+)"$/ do |contains, glob|
54
+ cd(".") do
55
+ Dir.glob(glob).each do |file|
56
+ transform_file(file) do |content|
57
+ content.gsub(/^(.*?#{contains}.*?)$/) { |line| "# #{line}" }
58
+ end
59
+ end
60
+ end
61
+ end
62
+
54
63
  Given /^I attach :attachment$/ do
55
64
  attach_attachment("attachment")
56
65
  end
@@ -60,11 +69,7 @@ Given /^I attach :attachment with:$/ do |definition|
60
69
  end
61
70
 
62
71
  def attach_attachment(name, definition = nil)
63
- snippet = ""
64
- if using_protected_attributes?
65
- snippet += "attr_accessible :name, :#{name}\n"
66
- end
67
- snippet += "has_attached_file :#{name}"
72
+ snippet = "has_attached_file :#{name}"
68
73
  if definition
69
74
  snippet += ", \n"
70
75
  snippet += definition
@@ -86,19 +91,19 @@ Given "I empty the application.js file" do
86
91
  end
87
92
 
88
93
  Given /^I run a rails generator to generate a "([^"]*)" scaffold with "([^"]*)"$/ do |model_name, attributes|
89
- step %[I successfully run `bundle exec #{generator_command} scaffold #{model_name} #{attributes}`]
94
+ step %[I successfully run `rails generate scaffold #{model_name} #{attributes}`]
90
95
  end
91
96
 
92
97
  Given /^I run a paperclip generator to add a paperclip "([^"]*)" to the "([^"]*)" model$/ do |attachment_name, model_name|
93
- step %[I successfully run `bundle exec #{generator_command} paperclip #{model_name} #{attachment_name}`]
98
+ step %[I successfully run `rails generate paperclip #{model_name} #{attachment_name}`]
94
99
  end
95
100
 
96
101
  Given /^I run a migration$/ do
97
- step %[I successfully run `bundle exec rake db:migrate --trace`]
102
+ step %[I successfully run `rake db:migrate --trace`]
98
103
  end
99
104
 
100
105
  When /^I rollback a migration$/ do
101
- step %[I successfully run `bundle exec rake db:rollback STEPS=1 --trace`]
106
+ step %[I successfully run `rake db:rollback STEPS=1 --trace`]
102
107
  end
103
108
 
104
109
  Given /^I update my new user view to include the file upload field$/ do
@@ -144,8 +149,10 @@ end
144
149
 
145
150
  Given /^I start the rails application$/ do
146
151
  cd(".") do
152
+ require "rails"
147
153
  require "./config/environment"
148
- require "capybara/rails"
154
+ require "capybara"
155
+ Capybara.app = Rails.application
149
156
  end
150
157
  end
151
158
 
@@ -171,7 +178,7 @@ end
171
178
 
172
179
  When /^I configure the application to use "([^\"]+)" from this project$/ do |name|
173
180
  append_to_gemfile "gem '#{name}', :path => '#{PROJECT_ROOT}'"
174
- steps %{And I run `bundle install --local`}
181
+ steps %{And I successfully run `bundle install --local`}
175
182
  end
176
183
 
177
184
  When /^I configure the application to use "([^\"]+)"$/ do |gem_name|
@@ -190,12 +197,6 @@ When /^I comment out the gem "([^"]*)" from the Gemfile$/ do |gemname|
190
197
  comment_out_gem_in_gemfile gemname
191
198
  end
192
199
 
193
- Given /^I am using Rails newer than ([\d\.]+)$/ do |version|
194
- if framework_version < version
195
- pending "Not supported in Rails < #{version}"
196
- end
197
- end
198
-
199
200
  Given(/^I add a "(.*?)" processor in "(.*?)"$/) do |processor, directory|
200
201
  filename = "#{directory}/#{processor}.rb"
201
202
  cd(".") do
@@ -1,11 +1,11 @@
1
1
  When /^I attach the file "([^"]*)" to "([^"]*)" on S3$/ do |file_path, field|
2
2
  definition = Paperclip::AttachmentRegistry.definitions_for(User)[field.downcase.to_sym]
3
- path = "https://paperclip.s3.amazonaws.com#{definition[:path]}"
3
+ path = "https://paperclip.s3.us-west-2.amazonaws.com#{definition[:path]}"
4
4
  path.gsub!(':filename', File.basename(file_path))
5
5
  path.gsub!(/:([^\/\.]+)/) do |match|
6
6
  "([^\/\.]+)"
7
7
  end
8
- FakeWeb.register_uri(:put, Regexp.new(path), :body => "OK")
8
+ FakeWeb.register_uri(:put, Regexp.new(path), :body => "<xml></xml>")
9
9
  step "I attach the file \"#{file_path}\" to \"#{field}\""
10
10
  end
11
11
 
@@ -7,5 +7,6 @@ $CUCUMBER=1
7
7
  World(RSpec::Matchers)
8
8
 
9
9
  Before do
10
+ aruba.config.command_launcher = ENV.fetch("DEBUG", nil) ? :debug : :spawn
10
11
  @aruba_timeout_seconds = 120
11
12
  end
@@ -17,7 +17,7 @@ module NavigationHelpers
17
17
  page_name =~ /the (.*) page/
18
18
  path_components = $1.split(/\s+/)
19
19
  self.send(path_components.push('path').join('_').to_sym)
20
- rescue Object => e
20
+ rescue Object
21
21
  raise "Can't find mapping from \"#{page_name}\" to a path.\n" +
22
22
  "Now, go and add a mapping in #{__FILE__}"
23
23
  end
@@ -35,29 +35,5 @@ module RailsCommandHelpers
35
35
  def framework_major_version
36
36
  framework_version.split(".").first.to_i
37
37
  end
38
-
39
- def using_protected_attributes?
40
- framework_major_version < 4
41
- end
42
-
43
- def new_application_command
44
- "rails new"
45
- end
46
-
47
- def generator_command
48
- if framework_major_version >= 4
49
- "rails generate"
50
- else
51
- "script/rails generate"
52
- end
53
- end
54
-
55
- def runner_command
56
- if framework_major_version >= 4
57
- "rails runner"
58
- else
59
- "script/rails runner"
60
- end
61
- end
62
38
  end
63
39
  World(RailsCommandHelpers)
data/gemfiles/4.2.gemfile CHANGED
@@ -3,17 +3,15 @@
3
3
  source "https://rubygems.org"
4
4
 
5
5
  gem "sqlite3", "~> 1.3.8", :platforms => :ruby
6
- gem "jruby-openssl", :platforms => :jruby
7
- gem "activerecord-jdbcsqlite3-adapter", :platforms => :jruby
8
- gem "rubysl", :platforms => :rbx
9
- gem "racc", :platforms => :rbx
10
6
  gem "pry"
11
7
  gem "rails", "~> 4.2.0"
12
8
 
13
9
  group :development, :test do
14
- gem "mime-types", "~> 1.16"
10
+ gem "activerecord-import"
11
+ gem "mime-types"
15
12
  gem "builder"
16
13
  gem "rubocop", :require => false
14
+ gem "rspec"
17
15
  end
18
16
 
19
17
  gemspec :path => "../"
@@ -3,17 +3,15 @@
3
3
  source "https://rubygems.org"
4
4
 
5
5
  gem "sqlite3", "~> 1.3.8", :platforms => :ruby
6
- gem "jruby-openssl", :platforms => :jruby
7
- gem "activerecord-jdbcsqlite3-adapter", :platforms => :jruby
8
- gem "rubysl", :platforms => :rbx
9
- gem "racc", :platforms => :rbx
10
6
  gem "pry"
11
- gem "rails", "~> 3.2.0"
7
+ gem "rails", "~> 5.0.0"
12
8
 
13
9
  group :development, :test do
14
- gem "mime-types", "~> 1.16"
10
+ gem "activerecord-import"
11
+ gem "mime-types"
15
12
  gem "builder"
16
13
  gem "rubocop", :require => false
14
+ gem "rspec"
17
15
  end
18
16
 
19
17
  gemspec :path => "../"
@@ -13,7 +13,9 @@ class PaperclipGenerator < ActiveRecord::Generators::Base
13
13
  end
14
14
 
15
15
  def generate_migration
16
- migration_template "paperclip_migration.rb.erb", "db/migrate/#{migration_file_name}"
16
+ migration_template("paperclip_migration.rb.erb",
17
+ "db/migrate/#{migration_file_name}",
18
+ migration_version: migration_version)
17
19
  end
18
20
 
19
21
  def migration_name
@@ -27,4 +29,10 @@ class PaperclipGenerator < ActiveRecord::Generators::Base
27
29
  def migration_class_name
28
30
  migration_name.camelize
29
31
  end
32
+
33
+ def migration_version
34
+ if Rails.version.start_with? "5"
35
+ "[#{Rails::VERSION::MAJOR}.#{Rails::VERSION::MINOR}]"
36
+ end
37
+ end
30
38
  end
@@ -1,4 +1,4 @@
1
- class <%= migration_class_name %> < ActiveRecord::Migration
1
+ class <%= migration_class_name %> < ActiveRecord::Migration<%= migration_version %>
2
2
  def self.up
3
3
  change_table :<%= table_name %> do |t|
4
4
  <% attachment_names.each do |attachment| -%>
@@ -2,6 +2,7 @@
2
2
  require 'uri'
3
3
  require 'paperclip/url_generator'
4
4
  require 'active_support/deprecation'
5
+ require 'active_support/core_ext/string/inflections'
5
6
 
6
7
  module Paperclip
7
8
  # The Attachment class manages the files for a given attachment. It saves
@@ -32,6 +33,7 @@ module Paperclip
32
33
  :use_timestamp => true,
33
34
  :whiny => Paperclip.options[:whiny] || Paperclip.options[:whiny_thumbnails],
34
35
  :validate_media_type => true,
36
+ :adapter_options => { hash_digest: Digest::MD5 },
35
37
  :check_validity_before_processing => true
36
38
  }
37
39
  end
@@ -49,7 +51,8 @@ module Paperclip
49
51
  # +url+ - a relative URL of the attachment. This is interpolated using +interpolator+
50
52
  # +path+ - where on the filesystem to store the attachment. This is interpolated using +interpolator+
51
53
  # +styles+ - a hash of options for processing the attachment. See +has_attached_file+ for the details
52
- # +only_process+ - style args to be run through the post-processor. This defaults to the empty list
54
+ # +only_process+ - style args to be run through the post-processor. This defaults to the empty list (which is
55
+ # a special case that indicates all styles should be processed)
53
56
  # +default_url+ - a URL for the missing image
54
57
  # +default_style+ - the style to use when an argument is not specified e.g. #url, #path
55
58
  # +storage+ - the storage mechanism. Defaults to :filesystem
@@ -81,7 +84,7 @@ module Paperclip
81
84
  @errors = {}
82
85
  @dirty = false
83
86
  @interpolator = options[:interpolator]
84
- @url_generator = options[:url_generator].new(self, @options)
87
+ @url_generator = options[:url_generator].new(self)
85
88
  @source_file_options = options[:source_file_options]
86
89
  @whiny = options[:whiny]
87
90
 
@@ -95,7 +98,8 @@ module Paperclip
95
98
  # attachment:
96
99
  # new_user.avatar = old_user.avatar
97
100
  def assign(uploaded_file)
98
- @file = Paperclip.io_adapters.for(uploaded_file)
101
+ @file = Paperclip.io_adapters.for(uploaded_file,
102
+ @options[:adapter_options])
99
103
  ensure_required_accessors!
100
104
  ensure_required_validations!
101
105
 
@@ -236,6 +240,10 @@ module Paperclip
236
240
  # the instance's errors and returns false, cancelling the save.
237
241
  def save
238
242
  flush_deletes unless @options[:keep_old_files]
243
+ process = only_process
244
+ if process.any? && !process.include?(:original)
245
+ @queued_for_write.except!(:original)
246
+ end
239
247
  flush_writes
240
248
  @dirty = false
241
249
  true
@@ -322,7 +330,7 @@ module Paperclip
322
330
  OpenSSL::HMAC.hexdigest(OpenSSL::Digest.const_get(@options[:hash_digest]).new, @options[:hash_secret], data)
323
331
  end
324
332
 
325
- # This method really shouldn't be called that often. It's expected use is
333
+ # This method really shouldn't be called that often. Its expected use is
326
334
  # in the paperclip:refresh rake task and that's it. It will regenerate all
327
335
  # thumbnails forcefully, by reobtaining the original file and going through
328
336
  # the post-process again.
@@ -347,7 +355,7 @@ module Paperclip
347
355
 
348
356
  # Returns true if a file has been assigned.
349
357
  def file?
350
- !original_filename.blank?
358
+ original_filename.present?
351
359
  end
352
360
 
353
361
  alias :present? :file?
@@ -426,7 +434,7 @@ module Paperclip
426
434
  def assign_attributes
427
435
  @queued_for_write[:original] = @file
428
436
  assign_file_information
429
- assign_fingerprint(@file.fingerprint)
437
+ assign_fingerprint { @file.fingerprint }
430
438
  assign_timestamps
431
439
  end
432
440
 
@@ -436,9 +444,9 @@ module Paperclip
436
444
  instance_write(:file_size, @file.size)
437
445
  end
438
446
 
439
- def assign_fingerprint(fingerprint)
447
+ def assign_fingerprint
440
448
  if instance_respond_to?(:fingerprint)
441
- instance_write(:fingerprint, fingerprint)
449
+ instance_write(:fingerprint, yield)
442
450
  end
443
451
  end
444
452
 
@@ -464,7 +472,7 @@ module Paperclip
464
472
 
465
473
  def reset_file_if_original_reprocessed
466
474
  instance_write(:file_size, @queued_for_write[:original].size)
467
- assign_fingerprint(@queued_for_write[:original].fingerprint)
475
+ assign_fingerprint { @queued_for_write[:original].fingerprint }
468
476
  reset_updater
469
477
  end
470
478
 
@@ -500,7 +508,7 @@ module Paperclip
500
508
 
501
509
  instance.run_paperclip_callbacks(:post_process) do
502
510
  instance.run_paperclip_callbacks(:"#{name}_post_process") do
503
- unless @options[:check_validity_before_processing] && instance.errors.any?
511
+ if !@options[:check_validity_before_processing] || !instance.errors.any?
504
512
  post_process_styles(*style_args)
505
513
  end
506
514
  end
@@ -518,15 +526,18 @@ module Paperclip
518
526
  begin
519
527
  raise RuntimeError.new("Style #{name} has no processors defined.") if style.processors.blank?
520
528
  intermediate_files = []
529
+ original = @queued_for_write[:original]
521
530
 
522
- @queued_for_write[name] = style.processors.inject(@queued_for_write[:original]) do |file, processor|
531
+ @queued_for_write[name] = style.processors.
532
+ reduce(original) do |file, processor|
523
533
  file = Paperclip.processor(processor).make(file, style.processor_options, self)
524
- intermediate_files << file
534
+ intermediate_files << file unless file == @queued_for_write[:original]
525
535
  file
526
536
  end
527
537
 
528
538
  unadapted_file = @queued_for_write[name]
529
- @queued_for_write[name] = Paperclip.io_adapters.for(@queued_for_write[name])
539
+ @queued_for_write[name] = Paperclip.io_adapters.
540
+ for(@queued_for_write[name], @options[:adapter_options])
530
541
  unadapted_file.close if unadapted_file.respond_to?(:close)
531
542
  @queued_for_write[name]
532
543
  rescue Paperclip::Errors::NotIdentifiedByImageMagickError => e
@@ -586,7 +597,7 @@ module Paperclip
586
597
 
587
598
  # You can either specifiy :restricted_characters or you can define your own
588
599
  # :filename_cleaner object. This object needs to respond to #call and takes
589
- # the filename that will be cleaned. It should return the cleaned filenme.
600
+ # the filename that will be cleaned. It should return the cleaned filename.
590
601
  def filename_cleaner
591
602
  @options[:filename_cleaner] || FilenameCleaner.new(@options[:restricted_characters])
592
603
  end
@@ -51,7 +51,8 @@ module Paperclip
51
51
  end
52
52
 
53
53
  def definitions_for(klass)
54
- klass.ancestors.each_with_object({}) do |ancestor, inherited_definitions|
54
+ parent_classes = klass.ancestors.reverse
55
+ parent_classes.each_with_object({}) do |ancestor, inherited_definitions|
55
56
  inherited_definitions.deep_merge! @attachments[ancestor]
56
57
  end
57
58
  end
@@ -7,7 +7,7 @@ module Paperclip
7
7
 
8
8
  module Defining
9
9
  def define_paperclip_callbacks(*callbacks)
10
- define_callbacks(*[callbacks, {:terminator => callback_terminator}].flatten)
10
+ define_callbacks(*[callbacks, { terminator: hasta_la_vista_baby }].flatten)
11
11
  callbacks.each do |callback|
12
12
  eval <<-end_callbacks
13
13
  def before_#{callback}(*args, &blk)
@@ -22,11 +22,13 @@ module Paperclip
22
22
 
23
23
  private
24
24
 
25
- def callback_terminator
26
- if ::ActiveSupport::VERSION::STRING >= '4.1'
27
- lambda { |target, result| result == false }
28
- else
29
- 'result == false'
25
+ def hasta_la_vista_baby
26
+ lambda do |_, result|
27
+ if result.respond_to?(:call)
28
+ result.call == false
29
+ else
30
+ result == false
31
+ end
30
32
  end
31
33
  end
32
34
  end
@@ -67,8 +67,9 @@ module Paperclip
67
67
  end
68
68
 
69
69
  def type_from_mime_magic
70
- @type_from_mime_magic ||=
71
- MimeMagic.by_magic(File.open(@filepath)).try(:type)
70
+ @type_from_mime_magic ||= File.open(@filepath) do |file|
71
+ MimeMagic.by_magic(file).try(:type)
72
+ end
72
73
  end
73
74
 
74
75
  def type_from_file_command
@@ -19,7 +19,9 @@ module Paperclip
19
19
  end
20
20
 
21
21
  # Will be thrown when ImageMagic cannot determine the uploaded file's
22
- # metadata, usually this would mean the file is not an image.
22
+ # metadata, usually this would mean the file is not an image. If you are
23
+ # consistently receiving this error on PDFs make sure that you have
24
+ # installed Ghostscript.
23
25
  class NotIdentifiedByImageMagickError < Paperclip::Error
24
26
  end
25
27
 
@@ -16,7 +16,7 @@ module Paperclip
16
16
  # On BSDs, `file` doesn't give a result code of 1 if the file doesn't exist.
17
17
  type = begin
18
18
  Paperclip.run("file", "-b --mime :file", file: @filename)
19
- rescue Cocaine::CommandLineError => e
19
+ rescue Terrapin::CommandLineError => e
20
20
  Paperclip.log("Error while determining content type: #{e}")
21
21
  SENSIBLE_DEFAULT
22
22
  end
@@ -24,9 +24,9 @@ module Paperclip
24
24
  :swallow_stderr => true
25
25
  }
26
26
  )
27
- rescue Cocaine::ExitStatusError
27
+ rescue Terrapin::ExitStatusError
28
28
  ""
29
- rescue Cocaine::CommandNotFoundError => e
29
+ rescue Terrapin::CommandNotFoundError => e
30
30
  raise_because_imagemagick_missing
31
31
  end
32
32
  end
@@ -8,7 +8,7 @@ module Paperclip
8
8
  base.extend ClassMethods
9
9
  base.send :include, Callbacks
10
10
  base.send :include, Validators
11
- base.send :include, Schema if defined? ActiveRecord
11
+ base.send :include, Schema if defined? ActiveRecord::Base
12
12
 
13
13
  locale_path = Dir.glob(File.dirname(__FILE__) + "/locales/*.{rb,yml}")
14
14
  I18n.load_path += locale_path unless I18n.load_path.include?(locale_path)
@@ -91,7 +91,13 @@ module Paperclip
91
91
  name = @name
92
92
  @klass.send(:after_save) { send(name).send(:save) }
93
93
  @klass.send(:before_destroy) { send(name).send(:queue_all_for_delete) }
94
- @klass.send(:after_commit, :on => :destroy) { send(name).send(:flush_deletes) }
94
+ if @klass.respond_to?(:after_commit)
95
+ @klass.send(:after_commit, on: :destroy) do
96
+ send(name).send(:flush_deletes)
97
+ end
98
+ else
99
+ @klass.send(:after_destroy) { send(name).send(:flush_deletes) }
100
+ end
95
101
  end
96
102
 
97
103
  def add_paperclip_callbacks