Rails图片上传安全性

时间:2015-04-27 06:31:24

标签: ruby-on-rails-4 paperclip carrierwave image-uploading dropzone.js

目前,我采用Carrierwave为用户提供图像。

但是,我几乎找不到图像安全的解决方案,即如何为上传的图像设置图像授权,只允许同一组中的某个用户查看?

在挖掘Facebook的实现后,我观察到他们将这些参数(哦,oe,__ gda_)注入图像网址

?oh=924eb34394&oe=55E07&__gda__=1436393492fc8bf91e1aec5

carrierwave 回形针是否有类似的实施?

由于

3 个答案:

答案 0 :(得分:1)

我对此工作了很多(仅限Paperclip)。

有一个解决方案没问题,但需要大量处理。

如果您只想隐藏文件,您可以散列回形针附件,请参阅:https://github.com/thoughtbot/paperclip/wiki/Hashing

如果您想在每个图片加载时授权用户,您可以这样做:

将您的文件移出公共文件夹

has_attached_file :image, 
                    styles: { large: '1500x1500>', small: '250x250>'},
                    path: ':rails_root/storage/gallery/image/:style/:filename'

使用Sendfile查看文件

def show
    send_file(object.image.path(:small), filename: object.image_file_name, type: "image/png",disposition: 'inline',x_sendfile: true)    
end

然而,我有点不愿意实现这一点,例如图片库,因为它需要GET - 动作+授权每个图像。使用x-sendfile与Apache协同工作可以更快地传送图像。

价: http://apidock.com/rails/ActionController/Streaming/send_file

答案 1 :(得分:0)

我从https://makandracards.com/makandra/734-deliver-paperclip-attachments-to-authorized-users-only找到了回形针的好方法 虽然有点过时,但本文详细介绍了保护附件访问所需的一切,以及如何保护文件本身。本文介绍了实现它的所有步骤,包括Capistrano部署!

请务必通过更改以下内容来使用更新的路线:

map.resources :notes, :member => { :attachment => :get }

为:

resources :notes, only: [] do
  member do
    get :attachment
  end
end

我也更新了以下链接:

link_to 'Download attachment', [:attachment, @note]

为:

link_to 'Download Attachment', attachment_note_path( @note.id )

另请参阅Paperclip changing URL/Path以配置网址。

答案 2 :(得分:0)

默认情况下,Carrierwave会在/public中存储上传内容,其中所有内容都只是作为静态内容提供。如果您需要控制对此上传的访问权限,我首先要配置不同的存储路径

class TestUploader < CarrierWave::Uploader::Base
  def store_dir
    Rails.root.join('uploads', relative_path).to_s
  end

  def serving_path # Use this method to get the serving path of the upload
    File.join '/uploads', relative_path
  end

  private

  def relative_path
    File.join model.class.model_name.plural, model.id.to_s
  end
end

由于CarrierWave依靠公共资产服务来提供上传服务,因此您必须实施自己的文件服务方法。这是如何使用Rails

执行此操作的愚蠢示例
class Test < ApplicationRecord
  mount_uploader :file, TestUploader
end

Rails.application.routes.draw do
  get '/uploads/:model/:id', to: 'uploads#get'
end

class UploadsController < ApplicationController
  def get
    # ... autorization logic
    model = params.fetch(:model).singularize.camelcase.safe_constantize
    return head 400 unless model.present?
    send_file model.find(params.fetch(:id)).file.path
  end
end