我有一个具有多个模型与全部上传到S3回形针附件的Rails应用程序。这个应用程序还具有运行往往一个大的测试套件。这样做的缺点是,一吨的文件都上传到每一个试运行我们的S3帐户,使得测试套件运行缓慢。它也减慢发展一点,需要你有为了工作在code互联网连接。
I have a rails application that has multiple models with paperclip attachments that are all uploaded to S3. This app also has a large test suite that is run quite often. The downside with this is that a ton of files are uploaded to our S3 account on every test run, making the test suite run slowly. It also slows down development a bit, and requires you to have an internet connection in order to work on the code.
有没有一种合理的方式来设置基于Rails环境回形针存储机制?理想的情况下,我们的测试和开发环境将使用本地文件系统存储和生产环境将使用S3存储
Is there a reasonable way to set the paperclip storage mechanism based on the Rails environment? Ideally, our test and development environments would use the local filesystem storage, and the production environment would use S3 storage.
我也想提取这个逻辑到某种共享的模块,因为我们有几个模式,将需要此行为。我想,以避免像这里面的每个模型的解决方案:
I'd also like to extract this logic into a shared module of some kind, since we have several models that will need this behavior. I'd like to avoid a solution like this inside of every model:
### We don't want to do this in our models...
if Rails.env.production?
has_attached_file :image, :styles => {...},
:path => "images/:uuid_partition/:uuid/:style.:extension",
:storage => :s3,
:url => ':s3_authenticated_url', # generates an expiring url
:s3_credentials => File.join(Rails.root, 'config', 's3.yml'),
:s3_permissions => 'private',
:s3_protocol => 'https'
else
has_attached_file :image, :styles => {...},
:storage => :filesystem
# Default :path and :url should be used for dev/test envs.
end
更新:的粘性部分是附件的:路径
和:网址
选项需要取决于哪个存储系统被用于不同
Update: The sticky part is that the attachment's :path
and :url
options need to differ depending on which storage system is being used.
任何意见或建议,将不胜AP preciated! : - )
Any advice or suggestions would be greatly appreciated! :-)
与它玩了一段时间后,我想出了一个模块,我想要做什么。
After playing around with it for a while, I came up with a module that does what I want.
在应用程序/模型/共享/ attachment_helper.rb
:
module Shared
module AttachmentHelper
def self.included(base)
base.extend ClassMethods
end
module ClassMethods
def has_attachment(name, options = {})
# generates a string containing the singular model name and the pluralized attachment name.
# Examples: "user_avatars" or "asset_uploads" or "message_previews"
attachment_owner = self.table_name.singularize
attachment_folder = "#{attachment_owner}_#{name.to_s.pluralize}"
# we want to create a path for the upload that looks like:
# message_previews/00/11/22/001122deadbeef/thumbnail.png
attachment_path = "#{attachment_folder}/:uuid_partition/:uuid/:style.:extension"
if Rails.env.production?
options[:path] ||= attachment_path
options[:storage] ||= :s3
options[:url] ||= ':s3_authenticated_url'
options[:s3_credentials] ||= File.join(Rails.root, 'config', 's3.yml')
options[:s3_permissions] ||= 'private'
options[:s3_protocol] ||= 'https'
else
# For local Dev/Test envs, use the default filesystem, but separate the environments
# into different folders, so you can delete test files without breaking dev files.
options[:path] ||= ":rails_root/public/system/attachments/#{Rails.env}/#{attachment_path}"
options[:url] ||= "/system/attachments/#{Rails.env}/#{attachment_path}"
end
# pass things off to paperclip.
has_attached_file name, options
end
end
end
end
(注:我在上面使用一些自定义的回形针插值,如:uuid_partition
,:UUID
和:s3_authenticated_url
你需要修改的东西根据需要为特定的应用程序)的
(Note: I'm using some custom paperclip interpolations above, like :uuid_partition
, :uuid
and :s3_authenticated_url
. You'll need to modify things as needed for your particular application)
现在,对于具有回形针附件的每一个模型,你就必须包括该共享的模块,并调用 has_attachment
方法(而不是回形针的 has_attached_file
)
Now, for every model that has paperclip attachments, you just have to include this shared module, and call the has_attachment
method (instead of paperclip's has_attached_file
)
这是例子模型文件:应用程序/模型/ user.rb
:
class User < ActiveRecord::Base
include Shared::AttachmentHelper
has_attachment :avatar, :styles => { :thumbnail => "100x100>" }
end
有了这个地方,你必须保存在以下位置的文件,根据您的环境:
With this in place, you'll have files saved to the following locations, depending on your environment:
发展:
RAILS_ROOT +公共/附件/开发/ user_avatars / AA / BB / CC / AABBCCDDEEFF / thumbnail.jpg
测试:
RAILS_ROOT +公共/附件/测试/ user_avatars / AA / BB / CC / AABBCCDDEEFF / thumbnail.jpg
制作:
https://s3.amazonaws.com/your-bucket-name/user_avatars/aa/bb/cc/aabbccddeeff/thumbnail.jpg
这确实我在寻找什么,希望它会证明是有用的给别人了。 :)
This does exactly what I'm looking for, hopefully it'll prove useful to someone else too. :)
约翰