我在我的 Rails 3 示例应用程序上使用 CarrierWave。我想验证远程位置上传,因此当用户提交无效 URL(空白或非图像)时,我不会收到标准错误异常:
CarrierWave::DownloadError in ImageController#create
trying to download a file which is not served over HTTP
这是我的模型:
class Painting < ActiveRecord::Base
attr_accessible :gallery_id, :name, :image, :remote_image_url
belongs_to :gallery
mount_uploader :image, ImageUploader
validates :name, :presence => true,
:length => { :minimum => 5, :maximum => 100 }
validates :image, :presence => true
end
这是我的 Controller :
class PaintingsController < ApplicationController
def new
@painting = Painting.new(:gallery_id => params[:gallery_id])
end
def create
@painting = Painting.new(params[:painting])
if @painting.save
flash[:notice] = "Successfully created painting."
redirect_to @painting.gallery
else
render :action => 'new'
end
end
def edit
@painting = Painting.find(params[:id])
end
def update
@painting = Painting.find(params[:id])
if @painting.update_attributes(params[:painting])
flash[:notice] = "Successfully updated painting."
redirect_to @painting.gallery
else
render :action => 'edit'
end
end
def destroy
@painting = Painting.find(params[:id])
@painting.destroy
flash[:notice] = "Successfully destroyed painting."
redirect_to @painting.gallery
end
end
我不太确定如何解决这个问题,所以任何见解都会很棒。
最佳答案
我遇到了同样的问题。不幸的是,这看起来像是 CarrierWave 的设计缺陷……它不允许正确验证远程 url。 CarrierWave 将在设置属性后立即尝试下载资源,如果 url 无效、无法访问或资源不具有预期类型,则会抛出异常。 DownloadError 或 IntegrityErrors 总是在任何验证发生之前抛出。
因此我找不到使用其他验证器的好的解决方法。我的解决方案最终看起来像这样:
valid = false
begin
par = params[:image].except(:remote_upload_url)
@image = Image.new(par)
# this may fail:
@image.remote_upload_url = params[:image][:remote_upload_url]
valid = true
rescue CarrierWave::DownloadError
@image.errors.add(:remote_upload_url, "This url doesn't appear to be valid")
rescue CarrierWave::IntegrityError
@image.errors.add(:remote_upload_url, "This url does not appear to point to a valid image")
end
# validate and save if no exceptions were thrown above
if valid && @image.save
redirect_to(images_configure_path)
else
render :action => 'new'
end
基本上,我将构造函数包装在救援 block 中,并最初设置除远程 url 之外的所有参数。当我设置它时,可能会发生异常,我通过在模型中手动设置错误来处理。请注意,在此场景中不执行其他验证。这是一个黑客,但对我有用。
我希望这可以在未来的版本中解决,方法是将资源下载延迟到模型验证阶段或之后。
关于ruby-on-rails - 我该怎么办 :remote location validation with CarrierWave?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/6012677/