2017-03-24 52 views
0

我一直在試圖讓Paperclip上傳圖像到Amazon S3。儘管我首先得到了程序,但它只能在本地保存(儘管存儲方法設置爲s3),並且一旦我發現我需要重寫默認路徑,它會因寫入錯誤而崩潰。將回形針上傳到S3開發和生產

我不知道它是否重要,但我使用Devise並將profile_image添加到用戶模型中。

我試圖按照this guide從Heroku的

這裏是只有儘管似乎成爲S3設置本地寫第一個設置:

user.rb 
    class User < ApplicationRecord 
     has_attached_file :profile_image, styles: { 
     thumb: '100x100>', 
     square: '200x200#', 
     medium: '300x300>' 
     } 
     validates_attachment_content_type :profile_image, :content_type => /\Aimage\/.*\Z/ 
end 

production.rb和development.rb

config.paperlip_defaults = { 
    storage: :s3, 
    s3_credientials: { 
     bucket: ENV.fetch('S3_BUCKET_NAME'), 
     access_key_id: ENV.fetch('AWS_ACCESS_KEY_ID'), 
     secret_access_key: ENV.fetch('AWS_SECRET_ACCESS_KEY'), 
     s3_region: ENV.fetch('AWS_REGION') 
    } 
    } 
    Paperclip.options[:command_path] = '/usr/local/bin/' 

部分上傳表格 app/views/devise/registrations/edit.html.erb

<div class="form-group"> 
     <% if @user.profile_image.present? %> 
     <%= image_tag(current_user.profile_image.url(:square)) %><br /> 
     <%= link_to 'Remove profile image', remove_profile_image_path, method: :put, data: { confirm: 'Are you sure?' }, type: 'button' %> 
     <% else %> 
     <%= f.label :profile_image %> 
     <%= f.file_field :profile_image %> 
     <% end %> 
    </div> 

使用此設置,Paperclip可以工作,但它只能在本地保存圖像(在開發和部署Heroku時都是如此)。

接着,我試圖通過添加這迫使顯示URL來形式AWS到

配置/初始化/ paperclip.rb

Paperclip::Attachment.default_options[:url] = ':s3_domain_url' 
Paperclip::Attachment.default_options[:path] = '/:class/:attachment/:id_partition/:style/:filename' 

和這確實迫使圖像路徑來從那裏(當我刷新已經附加圖像的用戶的頁面時,由於沒有上傳圖像,所以它被破壞了)。不過,在我刪除這張圖片後,我無法再上傳。每次我試圖上傳我得到這個錯誤:

Errno::EACCES in Devise::RegistrationsController#update 

Permission denied @ dir_s_mkdir - /users/profile_images 

在試圖解決這個問題,我添加(從Heroku的教程)

Paperclip::Attachment.default_options[:s3_host_name] = 's3-us-east-1.amazonaws.com' 

額外的初始化,沒有工作,我嘗試加入一行到production.rb和development.rb沒有成功(我嘗試添加既默認哈希和證書哈希)

s3_domain_url: 's3-us-east-1.amazonaws.com' 

我明白,錯誤是本地寫錯誤,但我的SP (除了我如何做這項工作):

爲什麼回形針忽略存儲值的默認值並保存在本地(在第一種情況下)? 爲什麼它試圖寫入我的本地磁盤(在第二種情況下),而不是上傳到S3?

更新 的Gemfile

source 'https://rubygems.org' 

ruby '2.3.3' 

gem 'rails',     '~> 5.0.0', '>= 5.0.0.1' 
gem 'puma',     '~> 3.0' 
gem 'sass-rails',    '~> 5.0' 
gem 'uglifier',    '>= 1.3.0' 
gem 'coffee-rails',   '~> 4.2' 
gem 'jquery-rails' 
gem 'turbolinks',    '~> 5' 
gem 'jbuilder',    '~> 2.5' 
gem 'bcrypt',     '~> 3.1.7' 
gem 'devise' 
gem 'font-awesome-rails' 
gem 'bourbon',     '5.0.0.beta.7' 
gem 'neat',     '2.0.0' 
gem 'autoprefixer-rails' 
gem 'font-awesome-sass',  '~> 4.7.0' 
gem 'paperclip' 
gem 'aws-sdk',     '~> 2.3' 

group :development, :test do 
    gem 'sqlite3' 
    gem 'byebug', platform: :mri 
    gem 'dotenv-rails' 
end 

group :development do 
    gem 'listen', '~> 3.0.5' 
    gem 'web-console' 
    gem 'spring' 
    gem 'spring-watcher-listen', '~> 2.0.0' 
    gem 'rubocop', require: false 
    gem 'haml-lint', require: false 
end 

group :test do 
    gem 'guard', '2.13.0' 
    gem 'minitest-reporters', '1.1.9' 
    gem 'coveralls', require: false 
    gem 'capybara' 
    gem 'factory_girl_rails', '~>4.0' 
end 

group :production do 
    gem 'pg', '0.18.4' 
end 

# Windows does not include zoneinfo files, so bundle the tzinfo-data gem 
gem 'tzinfo-data', platforms: [:mingw, :mswin, :x64_mingw, :jruby] 

回答

1

更改此設置在問題和使用的文檔或者是錯誤的或者沒有的方式在Heroku上更有效的Paperclip ~> 5.1 & AWS-SDK ~> 2.0

還有第二個未說明的問題,一旦這個問題在開發中工作就會變得明顯,開發上傳將覆蓋生產上傳,反之亦然。

這是使用開發環境和生產環境都可以上傳到S3的設置。

  1. 苗條下來初始化僅向共享信息

config/initializers/paperclip.rb

Paperclip::Attachment.default_options[:path] = ':class/:attachment/:id_partition/:style/:filename' 
Paperclip::Attachment.default_options[:storage] = :s3 
Paperclip::Attachment.default_options[:s3_protocol] = 'https' 
  • 定義和有效圖像和圖像大小在用戶模型
  • app/model/users.rb

    has_attached_file :profile_image, styles: { 
        thumb: '100x100>', 
        square: '200x200#', 
        medium: '300x300>' 
        } 
    validates_attachment_content_type :profile_image, :content_type => /\Aimage\/.*\Z/ 
    
  • 註冊的第二dev的圖像桶並添加必要的變量到.ENV文件
  • .ENV

    # Shared S3 variables 
    AWS_ACCESS_KEY_ID=XXXXXXXXXXXXXXXXX 
    AWS_SECRET_ACCESS_KEY=XXXXXXXXXXXXXXXXX 
    
    # Development variables 
    DEV_S3_BUCKET_NAME=your-dev-bucket-name 
    
    # Production variables 
    S3_BUCKET_NAME=your-production-bucket-name 
    
  • 將默認選項和命令路徑置於其各自的環境文件中
  • config/environments/development.rb

    Paperclip::Attachment.default_options[:s3_credentials] = { 
        :bucket => ENV['DEV_S3_BUCKET_NAME'], 
        :access_key_id => ENV['AWS_ACCESS_KEY_ID'], 
        :secret_access_key => ENV['AWS_SECRET_ACCESS_KEY'], 
        :region => 'us-east-2' 
        } 
    Paperclip::Attachment.default_options[:s3_region] = 'us-east-2' 
    Paperclip::Attachment.default_options[:s3_host_name] = 's3.us-east-2.amazonaws.com' 
    Paperclip.options[:command_path] = 'usr/local/bin' 
    

    在我來說,我硬編碼的區域和主機名,您可以提取這些,如果你想要的。我還選擇在另一個區域託管開發圖像,以便再分開一點。另請注意,我創建的第一個存儲桶(生產)不會將區域附加到地址。我不確定爲什麼S3以這種方式配置,但您可以通過上傳圖像來檢查特定的圖像路徑,然後深入到AWS控制檯的文件夾中,直到找到圖像URL。

    config/environments/production.rb

    Paperclip::Attachment.default_options[:s3_credentials] = { 
        :bucket => ENV['S3_BUCKET_NAME'], 
        :access_key_id => ENV['AWS_ACCESS_KEY_ID'], 
        :secret_access_key => ENV['AWS_SECRET_ACCESS_KEY'], 
        :region => 'us-east-1' 
        } 
    Paperclip::Attachment.default_options[:s3_region] = 'us-east-1' 
    Paperclip::Attachment.default_options[:s3_host_name] = 's3.amazonaws.com' 
    Paperclip.options[:command_path] = 'usr/local/bin' 
    
    0

    您可能需要的路徑選擇從

    PaperClip::Attachment.default_options[:path] = ":rails_root/public/system/.../the/rest/of/the/desired/path" 
    
    +0

    這確實解決了寫錯誤,但你可以發佈您的Gemfile圖片尚未在本地,而不是上傳到S3 – oneWorkingHeadphone

    +0

    救嗎? – Jeremie

    +0

    在底部添加 – oneWorkingHeadphone

    相關問題