Commit 49b833a4 by Jon Yurek

Refactor shared behavior into AbstractAdapter superclass

parent 67281668
module Paperclip module Paperclip
class AbstractAdapter class AbstractAdapter
def original_filename
@original_filename
end
def content_type
@content_type
end
def size
@size
end
def fingerprint
@fingerprint ||= Digest::MD5.file(path).to_s
end
def nil?
false
end
def read(length = nil, buffer = nil)
@tempfile.read(length, buffer)
end
# We don't use this directly, but aws/sdk does.
def rewind
@tempfile.rewind
end
def eof?
@tempfile.eof?
end
def path
@tempfile.path
end
private private
def destination def destination
...@@ -22,8 +60,9 @@ module Paperclip ...@@ -22,8 +60,9 @@ module Paperclip
def type_from_file_command def type_from_file_command
# On BSDs, `file` doesn't give a result code of 1 if the file doesn't exist. # On BSDs, `file` doesn't give a result code of 1 if the file doesn't exist.
type = (self.original_filename.match(/\.(\w+)$/)[1] rescue "octet-stream").downcase type = (File.extname(self.path.to_s)).downcase
mime_type = (Paperclip.run("file", "-b --mime :file", :file => self.path).split(/[:;\s]+/)[0] rescue "application/x-#{type}") type = "octet-stream" if type.empty?
mime_type = Paperclip.run("file", "-b --mime :file", :file => self.path).split(/[:;\s]+/)[0]
mime_type = "application/x-#{type}" if mime_type.match(/\(.*?\)/) mime_type = "application/x-#{type}" if mime_type.match(/\(.*?\)/)
mime_type mime_type
end end
......
...@@ -11,43 +11,6 @@ module Paperclip ...@@ -11,43 +11,6 @@ module Paperclip
cache_current_values cache_current_values
end end
def original_filename
@original_filename
end
def content_type
@content_type
end
def size
@size
end
def nil?
false
end
def fingerprint
@fingerprint ||= Digest::MD5.file(path).to_s
end
def read(length = nil, buffer = nil)
@tempfile.read(length, buffer)
end
# We don't use this directly, but aws/sdk does.
def rewind
@tempfile.rewind
end
def eof?
@tempfile.eof?
end
def path
@tempfile.path
end
private private
def cache_current_values def cache_current_values
......
...@@ -2,18 +2,20 @@ module Paperclip ...@@ -2,18 +2,20 @@ module Paperclip
class FileAdapter < AbstractAdapter class FileAdapter < AbstractAdapter
def initialize(target) def initialize(target)
@target = target @target = target
@tempfile = copy_to_tempfile(@target) cache_current_values
end end
def original_filename private
if @target.respond_to?(:original_filename)
@target.original_filename def cache_current_values
else @original_filename = @target.original_filename if @target.respond_to?(:original_filename)
File.basename(@target.path) @original_filename ||= File.basename(@target.path)
end @tempfile = copy_to_tempfile(@target)
@content_type = calculate_content_type
@size = File.size(@target)
end end
def content_type def calculate_content_type
types = MIME::Types.type_for(original_filename) types = MIME::Types.type_for(original_filename)
if types.length == 0 if types.length == 0
type_from_file_command type_from_file_command
...@@ -23,35 +25,6 @@ module Paperclip ...@@ -23,35 +25,6 @@ module Paperclip
best_content_type_option(types) best_content_type_option(types)
end end
end end
def fingerprint
@fingerprint ||= Digest::MD5.file(path).to_s
end
def size
File.size(@tempfile)
end
def nil?
@target.nil?
end
def read(length = nil, buffer = nil)
@tempfile.read(length, buffer)
end
# We don't use this directly, but aws/sdk does.
def rewind
@tempfile.rewind
end
def eof?
@tempfile.eof?
end
def path
@tempfile.path
end
end end
end end
......
...@@ -2,55 +2,23 @@ module Paperclip ...@@ -2,55 +2,23 @@ module Paperclip
class StringioAdapter < AbstractAdapter class StringioAdapter < AbstractAdapter
def initialize(target) def initialize(target)
@target = target @target = target
cache_current_values
@tempfile = copy_to_tempfile(@target) @tempfile = copy_to_tempfile(@target)
end end
attr_writer :original_filename, :content_type private
def original_filename def cache_current_values
@original_filename ||= @target.original_filename if @target.respond_to?(:original_filename) @original_filename = @target.original_filename if @target.respond_to?(:original_filename)
@original_filename ||= "stringio.txt" @original_filename ||= "stringio.txt"
@original_filename.strip @original_filename = @original_filename.strip
end
def content_type @content_type = @target.content_type if @target.respond_to?(:content_type)
@content_type ||= @target.content_type if @target.respond_to?(:content_type)
@content_type ||= "text/plain" @content_type ||= "text/plain"
@content_type
end
def size
@target.size
end
def fingerprint
if (@cached_fingerprint.nil?)
rewind # start reading from the beginning
@cached_fingerprint = Digest::MD5.hexdigest(read)
rewind # for later read()
end
@cached_fingerprint
end
def read(length = nil, buffer = nil) @size = @target.size
@tempfile.read(length, buffer)
end end
# We don't use this directly, but aws/sdk does.
def rewind
@tempfile.rewind
end
def eof?
@tempfile.eof?
end
def path
@tempfile.path
end
private
def copy_to_tempfile(src) def copy_to_tempfile(src)
while data = src.read(16*1024) while data = src.read(16*1024)
destination.write(data) destination.write(data)
......
...@@ -2,6 +2,7 @@ module Paperclip ...@@ -2,6 +2,7 @@ module Paperclip
class UploadedFileAdapter < AbstractAdapter class UploadedFileAdapter < AbstractAdapter
def initialize(target) def initialize(target)
@target = target @target = target
cache_current_values
if @target.respond_to?(:tempfile) if @target.respond_to?(:tempfile)
@tempfile = copy_to_tempfile(@target.tempfile) @tempfile = copy_to_tempfile(@target.tempfile)
...@@ -10,41 +11,12 @@ module Paperclip ...@@ -10,41 +11,12 @@ module Paperclip
end end
end end
def original_filename private
@target.original_filename
end
def content_type
@target.content_type
end
def fingerprint
@fingerprint ||= Digest::MD5.file(path).to_s
end
def size
File.size(path)
end
def nil?
false
end
def read(length = nil, buffer = nil)
@tempfile.read(length, buffer)
end
# We don't use this directly, but aws/sdk does.
def rewind
@tempfile.rewind
end
def eof?
@tempfile.eof?
end
def path def cache_current_values
@tempfile.path @original_filename = @target.original_filename
@content_type = @target.content_type
@size = File.size(@target.path)
end end
end end
end end
......
...@@ -68,5 +68,9 @@ module Paperclip ...@@ -68,5 +68,9 @@ module Paperclip
end end
end end
def copy_to_local_file(style, local_dest_path)
FileUtils.cp(path(style), local_dest_path)
end
end end
end end
...@@ -63,6 +63,7 @@ class FileAdapterTest < Test::Unit::TestCase ...@@ -63,6 +63,7 @@ class FileAdapterTest < Test::Unit::TestCase
context "file with multiple possible x-types but no official type" do context "file with multiple possible x-types but no official type" do
setup do setup do
MIME::Types.stubs(:type_for).returns([MIME::Type.new('image/x-mp4'), MIME::Type.new('image/x-video')]) MIME::Types.stubs(:type_for).returns([MIME::Type.new('image/x-mp4'), MIME::Type.new('image/x-video')])
@subject = Paperclip.io_adapters.for(@file)
end end
should "return the first" do should "return the first" do
...@@ -74,6 +75,7 @@ class FileAdapterTest < Test::Unit::TestCase ...@@ -74,6 +75,7 @@ class FileAdapterTest < Test::Unit::TestCase
setup do setup do
MIME::Types.stubs(:type_for).returns([]) MIME::Types.stubs(:type_for).returns([])
Paperclip.stubs(:run).returns("application/vnd.ms-office\n") Paperclip.stubs(:run).returns("application/vnd.ms-office\n")
@subject = Paperclip.io_adapters.for(@file)
end end
should "return content type without newline character" do should "return content type without newline character" do
......
...@@ -12,20 +12,10 @@ class StringioFileProxyTest < Test::Unit::TestCase ...@@ -12,20 +12,10 @@ class StringioFileProxyTest < Test::Unit::TestCase
assert_equal "stringio.txt", @subject.original_filename assert_equal "stringio.txt", @subject.original_filename
end end
should "allow us to set a name" do
@subject.original_filename = "data.txt"
assert_equal "data.txt", @subject.original_filename
end
should "return a content type" do should "return a content type" do
assert_equal "text/plain", @subject.content_type assert_equal "text/plain", @subject.content_type
end end
should "allow us to set a content type" do
@subject.content_type = "image/jpg"
assert_equal "image/jpg", @subject.content_type
end
should "return the size of the data" do should "return the size of the data" do
assert_equal 6, @subject.size assert_equal 6, @subject.size
end end
......
...@@ -12,7 +12,8 @@ class UploadedFileAdapterTest < Test::Unit::TestCase ...@@ -12,7 +12,8 @@ class UploadedFileAdapterTest < Test::Unit::TestCase
:original_filename => "5k.png", :original_filename => "5k.png",
:content_type => "image/png", :content_type => "image/png",
:head => "", :head => "",
:tempfile => tempfile :tempfile => tempfile,
:path => tempfile.path
) )
@subject = Paperclip.io_adapters.for(@file) @subject = Paperclip.io_adapters.for(@file)
end end
......
...@@ -276,8 +276,13 @@ class S3Test < Test::Unit::TestCase ...@@ -276,8 +276,13 @@ class S3Test < Test::Unit::TestCase
'secret_access_key' => "54321" 'secret_access_key' => "54321"
} }
file = Paperclip.io_adapters.for(StringIO.new(".")) stringio = StringIO.new(".")
file.original_filename = "question?mark.png" class << stringio
def original_filename
"question?mark.png"
end
end
file = Paperclip.io_adapters.for(stringio)
@dummy = Dummy.new @dummy = Dummy.new
@dummy.avatar = file @dummy.avatar = file
@dummy.save @dummy.save
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment