Get path to ActiveStorage file on disk

前端 未结 4 582
[愿得一人]
[愿得一人] 2020-12-09 02:16

I need to get the path to the file on disk which is using ActiveStorage. The file is stored locally.

When I was using paperclip, I used the path<

相关标签:
4条回答
  • 2020-12-09 02:35

    I'm not sure why all the other answers use send(:url_for, key). I'm using Rails 5.2.2 and url_for is a public method, therefore, it's way better to avoid send, or simply call path_for:

    class User < ApplicationRecord
      has_one_attached :avatar
    
      def avatar_path
        ActiveStorage::Blob.service.path_for(avatar.key)
      end
    end
    

    Worth noting that in the view you can do things like this:

    <p>
      <%= image_tag url_for(@user.avatar) %>
      <br>
      <%= link_to 'View', polymorphic_url(@user.avatar) %>
      <br>
      Stored at <%= @user.image_path %>
      <br>
      <%= link_to 'Download', rails_blob_path(@user.avatar, disposition: :attachment) %>
      <br>
      <%= f.file_field :avatar %>
    </p>
    
    0 讨论(0)
  • 2020-12-09 02:35

    You can download the attachment to a local dir and then process it.

    Supposing you have in your model:

    has_one_attached :pdf_attachment
    

    You can define:

    def process_attachment      
       # Download the attached file in temp dir
       pdf_attachment_path = "#{Dir.tmpdir}/#{pdf_attachment.filename}"
       File.open(pdf_attachment_path, 'wb') do |file|
           file.write(pdf_attachment.download)
       end   
    
       # process the downloaded file
       # ...
    end
    
    0 讨论(0)
  • 2020-12-09 02:36

    Thanks to the help of @muistooshort in the comments, after looking at the Active Storage Code, this works:

    active_storage_disk_service = ActiveStorage::Service::DiskService.new(root: Rails.root.to_s + '/storage/')
    active_storage_disk_service.send(:path_for, user.avatar.blob.key)
      # => returns full path to the document stored locally on disk
    

    This solution feels a bit hacky to me. I'd love to hear of other solutions. This does work for me though.

    0 讨论(0)
  • 2020-12-09 02:42

    Just use:

    ActiveStorage::Blob.service.send(:path_for, user.avatar.key)
    

    You can do something like this on your model:

    class User < ApplicationRecord
      has_one_attached :avatar
    
      def avatar_on_disk
        ActiveStorage::Blob.service.send(:path_for, avatar.key)
      end
    end
    
    0 讨论(0)
提交回复
热议问题