Skip to content

Commit

Permalink
Browse files Browse the repository at this point in the history
broken build, start down renaming storage_name_file to storage_name, …
…add external config file option
  • Loading branch information
osheroff committed Jan 14, 2011
1 parent 422f41e commit 116b1e0
Show file tree
Hide file tree
Showing 4 changed files with 68 additions and 36 deletions.
2 changes: 1 addition & 1 deletion lib/attachment_fu.rb
@@ -1,5 +1,5 @@
require 'tempfile'
require 'activerecord'
require 'active_record'

Tempfile.class_eval do
# overwrite so tempfiles use the extension of the basename. important for rmagick and image science
Expand Down
52 changes: 41 additions & 11 deletions lib/technoweenie/attachment_fu.rb
Expand Up @@ -141,7 +141,7 @@ def has_attachment(options = {})
storage_klass.included_in_base(self)

# support syntax-sugar of "a = Attachment.new ; a.s3.authenticated_s3_url" for accessing store-specific stuff
self.class_eval "def #{attachment_options[:store_name]}_file; get_storage_delegator(:#{attachment_options[:store_name]}); end"
self.class_eval "def #{attachment_options[:store_name]}; get_storage_delegator(:#{attachment_options[:store_name]}); end"

case attachment_options[:processor]
when :none, nil
Expand Down Expand Up @@ -170,6 +170,26 @@ def has_attachment(options = {})
end unless parent_options[:processor] # Don't let child override processor
end

# helper method for has_attachment, for if you want to set up stuff from a yaml file
def setup_attachment_fu(extra_opts = {}, config_filename = nil)
config_file ||= RAILS_ROOT + "/config/attachments.yml"
raise "No attachment_fu configuration found, tried #{config_file}" unless File.exist?(config_file)

att_opts = YAML.load(ERB.new(File.read(config_file)).result)[Rails.env]
raise "No attachment_fu configuration found for environment #{Rails.env}" unless att_opts

arr = att_opts[self.name.tableize] || att_opts[:default]

raise "No attachment_fu configuration found for table #{self.name.tableize}" unless arr
arr = [arr] if arr.is_a?(Hash) # both flavors!
arr.each do |val|
options = val.symbolize_keys.merge(extra_opts)
puts options.inspect
has_attachment options
end
end


def load_related_exception?(e) #:nodoc: implementation specific
case
when e.kind_of?(LoadError), e.kind_of?(MissingSourceFile), $!.class.name == "CompilationError"
Expand All @@ -183,6 +203,7 @@ def load_related_exception?(e) #:nodoc: implementation specific
private :load_related_exception?
end


module ClassMethods
delegate :content_types, :to => Technoweenie::AttachmentFu

Expand Down Expand Up @@ -251,8 +272,10 @@ def after_attachment_saved(&block)
def before_thumbnail_saved(&block)
write_inheritable_array(:before_thumbnail_saved, [block])
end

end


# Get the thumbnail class, which is the current attachment class by default.
# Configure this with the :thumbnail_class option.
def thumbnail_class
Expand All @@ -262,19 +285,21 @@ def thumbnail_class

# Copies the given file path to a new tempfile, returning the closed tempfile.
def copy_to_temp_file(file, temp_base_name)
returning Tempfile.new(temp_base_name, Technoweenie::AttachmentFu.tempfile_path) do |tmp|
tmp = Tempfile.new(temp_base_name, Technoweenie::AttachmentFu.tempfile_path) do |tmp|
tmp.close
FileUtils.cp file, tmp.path
end
tmp
end

# Writes the given data to a new tempfile, returning the closed tempfile.
def write_to_temp_file(data, temp_base_name)
returning Tempfile.new(temp_base_name, Technoweenie::AttachmentFu.tempfile_path) do |tmp|
tmp = Tempfile.new(temp_base_name, Technoweenie::AttachmentFu.tempfile_path) do |tmp|
tmp.binmode
tmp.write data
tmp.close
end
tmp
end
end

Expand Down Expand Up @@ -313,7 +338,7 @@ def thumbnail_name_for(thumbnail = nil)
# Creates or updates the thumbnail for the current attachment.
def create_or_update_thumbnail(temp_file, file_name_suffix, *size)
thumbnailable? || raise(ThumbnailError.new("Can't create a thumbnail if the content type is not an image or there is no parent_id column"))
returning find_or_initialize_thumbnail(file_name_suffix) do |thumb|
thumb = find_or_initialize_thumbnail(file_name_suffix) do |thumb|
thumb.temp_paths.unshift temp_file
thumb.send(:'attributes=', {
:content_type => content_type,
Expand All @@ -324,6 +349,7 @@ def create_or_update_thumbnail(temp_file, file_name_suffix, *size)
callback_with_args :before_thumbnail_saved, thumb
thumb.save!
end
thumb
end

# Sets the content type.
Expand Down Expand Up @@ -473,18 +499,22 @@ def random_tempfile_filename

def sanitize_filename(filename)
return unless filename
returning filename.strip do |name|
# NOTE: File.basename doesn't work right with Windows paths on Unix
# get only the filename, not the whole path
name.gsub! /^.*(\\|\/)/, ''

# Finally, replace all non alphanumeric, underscore or periods with underscore
name.gsub! /[^A-Za-z0-9\.\-]/, '_'
end
name = filename.strip

# NOTE: File.basename doesn't work right with Windows paths on Unix
# get only the filename, not the whole path
name.gsub! /^.*(\\|\/)/, ''

# Finally, replace all non alphanumeric, underscore or periods with underscore
name.gsub! /[^A-Za-z0-9\.\-]/, '_'

name
end

# before_validation callback.
def set_size_from_temp_path
#puts "hello. here I be. #{temp_path} and \"#{File.size(temp_path)}\""
self.size = File.size(temp_path) if save_attachment?
end

Expand Down
26 changes: 13 additions & 13 deletions test/backends/remote/cloudfiles_test.rb
Expand Up @@ -5,7 +5,7 @@ class CloudfilesTest < ActiveSupport::TestCase
def self.test_CloudFiles?
true unless ENV["TEST_CLOUDFILES"] == "false"
end

if test_CloudFiles? && File.exist?(File.join(File.dirname(__FILE__), '../../rackspace_cloudfiles.yml'))
include BaseAttachmentTests
attachment_model CloudFilesAttachment
Expand All @@ -17,32 +17,32 @@ def test_should_create_correct_container_name(klass = CloudFilesAttachment)
end

test_against_subclass :test_should_create_correct_container_name, CloudFilesAttachment

def test_should_create_default_path_prefix(klass = CloudFilesAttachment)
attachment_model klass
attachment = upload_file :filename => '/files/rails.png'
assert_equal File.join(attachment_model.table_name, attachment.attachment_path_id), attachment.base_path
end

test_against_subclass :test_should_create_default_path_prefix, CloudFilesAttachment

def test_should_create_custom_path_prefix(klass = CloudFilesWithPathPrefixAttachment)
attachment_model klass
attachment = upload_file :filename => '/files/rails.png'
assert_equal File.join('some/custom/path/prefix', attachment.attachment_path_id), attachment.base_path
end

test_against_subclass :test_should_create_custom_path_prefix, CloudFilesWithPathPrefixAttachment


def test_should_create_valid_url(klass = CloudFilesAttachment)
attachment_model klass
attachment = upload_file :filename => '/files/rails.png'
assert_match(%r!http://cdn.cloudfiles.mosso.com/(.*?)/cloud_files_attachments/1/rails.png!, attachment.cloudfiles_url)
end

test_against_subclass :test_should_create_valid_url, CloudFilesAttachment

def test_should_save_attachment(klass = CloudFilesAttachment)
attachment_model klass
assert_created do
Expand All @@ -55,7 +55,7 @@ def test_should_save_attachment(klass = CloudFilesAttachment)
end

test_against_subclass :test_should_save_attachment, CloudFilesAttachment

def test_should_delete_attachment_from_cloud_files_when_attachment_record_destroyed(klass = CloudFilesAttachment)
attachment_model klass
attachment = upload_file :filename => '/files/rails.png'
Expand All @@ -74,19 +74,19 @@ def test_should_delete_attachment_from_cloud_files_when_attachment_record_destro
end

test_against_subclass :test_should_delete_attachment_from_cloud_files_when_attachment_record_destroyed, CloudFilesAttachment



protected
def http_response_for(url)
url = URI.parse(url)
Net::HTTP.start(url.host, url.port) {|http| http.request_head(url.path) }
end

def s3_protocol
Technoweenie::AttachmentFu::Backends::S3Backend.protocol
end

def s3_hostname
Technoweenie::AttachmentFu::Backends::S3Backend.hostname
end
Expand Down
24 changes: 13 additions & 11 deletions test/fixtures/attachment.rb
Expand Up @@ -48,11 +48,11 @@ class FileAttachmentWithStringId < ActiveRecord::Base
set_table_name 'file_attachments_with_string_id'
has_attachment :path_prefix => 'vendor/plugins/attachment_fu/test/files', :processor => :rmagick
validates_as_attachment

before_validation :auto_generate_id
before_save :auto_generate_id
@@last_id = 0

private
def auto_generate_id
@@last_id += 1
Expand All @@ -64,11 +64,11 @@ class FileAttachmentWithUuid < ActiveRecord::Base
set_table_name 'file_attachments_with_string_id'
has_attachment :path_prefix => 'vendor/plugins/attachment_fu/test/files', :processor => :rmagick, :uuid_primary_key => true
validates_as_attachment

before_validation :auto_generate_id
before_save :auto_generate_id
@@last_id = 0

private
def auto_generate_id
@@last_id += 1
Expand Down Expand Up @@ -110,7 +110,7 @@ class OrphanAttachment < ActiveRecord::Base
class MinimalAttachment < ActiveRecord::Base
has_attachment :path_prefix => 'vendor/plugins/attachment_fu/test/files', :processor => :rmagick
validates_as_attachment

def filename
"#{id}.file"
end
Expand Down Expand Up @@ -190,7 +190,7 @@ class MiniMagickAttachment < ActiveRecord::Base
class ImageThumbnailCrop < MiniMagickAttachment
has_attachment :path_prefix => 'vendor/plugins/attachment_fu/test/files',
:thumbnails => { :square => "50x50c", :vertical => "30x60c", :horizontal => "60x30c"}

# TODO this is a bad duplication, this method is in the MiniMagick Processor
def self.calculate_offset(image_width,image_height,image_aspect,thumb_width,thumb_height,thumb_aspect)
# only crop if image is not smaller in both dimensions
Expand All @@ -204,7 +204,7 @@ def self.calculate_offset(image_width,image_height,image_aspect,thumb_width,thum
command = "#{thumb_width}x#{image_height}+#{offset}+0"

# normal thumbnail generation
# calculate height and offset y, width is fixed
# calculate height and offset y, width is fixed
elsif (image_aspect <= thumb_aspect or image_width < thumb_width) and image_height > thumb_height
height = image_width / thumb_aspect
offset = (image_height / 2) - (height / 2)
Expand Down Expand Up @@ -238,27 +238,29 @@ class S3Attachment < ActiveRecord::Base
has_attachment :storage => :s3, :processor => :rmagick, :s3_config_path => File.join(File.dirname(__FILE__), '../amazon_s3.yml')
validates_as_attachment
end

class S3WithPathPrefixAttachment < S3Attachment
has_attachment :storage => :s3, :path_prefix => 'some/custom/path/prefix', :processor => :rmagick
validates_as_attachment
end
rescue
ENV["TEST_S3"] = "false"
puts "S3 error: #{$!}"
end

begin
class CloudFilesAttachment < ActiveRecord::Base
has_attachment :storage => :cloud_files, :processor => :rmagick, :cloudfiles_config_path => File.join(File.dirname(__FILE__), '../rackspace_cloudfiles.yml')
validates_as_attachment
end


class CloudFilesWithPathPrefixAttachment < CloudFilesAttachment
has_attachment :storage => :cloud_files, :path_prefix => 'some/custom/path/prefix', :processor => :rmagick
validates_as_attachment
end
rescue
ENV["TEST_CLOUDFILES"] = "false"
puts "CloudFiles error: #{$!}"
end

0 comments on commit 116b1e0

Please sign in to comment.