如何使用 json 渲染 @photo.errors(在 Rails 4 中使用 dropzone.js)
how do I render @photo.errors with json (using dropzone.js in Rails 4)
Heroku 控制台:
Started POST "/photos"
Processing by PhotosController#create as JSON
Parameters: {"utf8"=>"✓", "authenticity_token"=>"D5pc72xeJ6J/g==", "photo"=>{"title"=>"fffffffffffffffffffffffffffffffffffffffffffffffffffff", "tag_list"=>[""], "picture"=>#, @original_filename="size.jpg", @content_type="image/jpeg", @headers="Content-Disposition: form-data; name=\"photo[picture]\"; filename=\"size.jpg\"\r\nContent-Type: image/jpeg\r\n">}, "null"=>"", "commit"=>"Upload"}
Completed 500 Internal Server Error in 941ms (ActiveRecord: 13.9ms)
ArgumentError ('#, @messages={:title=>["is too long (maximum is 30 characters)"]}>' is not an ActiveModel-compatible object. It must implement :to_partial_path.):
app/controllers/photos_controller.rb:40:in `block (2 levels) in create'
PhotosController
def create
@photo = current_user.photos.build(photo_params)
respond_to do |format|
if @photo.save
format.html { redirect_to @photo, notice: 'Item was successfully created.' }
format.json { render json: @photo }
else
format.html { render 'new'}
**rb:40** (format.json { render @photo.errors, status: :unprocessable_entity }
end
end
end
dropzonephotos.js
$(document).ready(function() {
var dropzone;
Dropzone.autoDiscover = false;
dropzone = new Dropzone('#dropform', {
maxFiles: 2,
maxFilesize: 3,
paramName: 'photo[picture]',
headers: {
"X-CSRF-Token": $('meta[name="csrf-token"]').attr('content')
},
addRemoveLinks: true,
clickable: '.dz-default.dz-message',
previewsContainer: '.dz-default.dz-message',
thumbnailWidth: 200,
thumbnailHeight: 200,
parallelUploads: 100,
autoProcessQueue: false,
uploadMultiple: false
});
$('#item-submit').click(function(e) {
e.preventDefault();
e.stopPropagation();
if (dropzone.getQueuedFiles().length > 0) {
return dropzone.processQueue();
}
else {
return $('#dropform').submit();
}
});
return dropzone.on('success', function(file, responseText) {
return window.location.href = '/photos/' + responseText.id;
});
return dropzone.on('error', function(file, errorMessage, xhr) {
console.log('error');
});
});
验证失败时,视图中未呈现任何错误。拖放区缩略图上只有一个 "X",悬停时有一条消息 "Internal Server Error"。缩略图仍显示在视图中,尽管它实际上已被删除。如果我再次点击提交,表单将被处理为html,因为dropzone/nojson中没有照片可以提交。
所以我决定不用担心表单内的 Rails Active Record Validation Errors 这样做,这甚至可能是不可能的,因为表单是由 json 提交的,并且Rails helpers 可能没有设置为那样工作,我决定通过将错误附加到视图中,在 dropzone.on('error', function(file, errorMessage)
中使用 .js 文件本身手动完成。
Heroku 控制台:
Started POST "/photos"
Processing by PhotosController#create as JSON
Parameters: {"utf8"=>"✓", "authenticity_token"=>"D5pc72xeJ6J/g==", "photo"=>{"title"=>"fffffffffffffffffffffffffffffffffffffffffffffffffffff", "tag_list"=>[""], "picture"=>#, @original_filename="size.jpg", @content_type="image/jpeg", @headers="Content-Disposition: form-data; name=\"photo[picture]\"; filename=\"size.jpg\"\r\nContent-Type: image/jpeg\r\n">}, "null"=>"", "commit"=>"Upload"}
Completed 500 Internal Server Error in 941ms (ActiveRecord: 13.9ms)
ArgumentError ('#, @messages={:title=>["is too long (maximum is 30 characters)"]}>' is not an ActiveModel-compatible object. It must implement :to_partial_path.):
app/controllers/photos_controller.rb:40:in `block (2 levels) in create'
PhotosController
def create
@photo = current_user.photos.build(photo_params)
respond_to do |format|
if @photo.save
format.html { redirect_to @photo, notice: 'Item was successfully created.' }
format.json { render json: @photo }
else
format.html { render 'new'}
**rb:40** (format.json { render @photo.errors, status: :unprocessable_entity }
end
end
end
dropzonephotos.js
$(document).ready(function() {
var dropzone;
Dropzone.autoDiscover = false;
dropzone = new Dropzone('#dropform', {
maxFiles: 2,
maxFilesize: 3,
paramName: 'photo[picture]',
headers: {
"X-CSRF-Token": $('meta[name="csrf-token"]').attr('content')
},
addRemoveLinks: true,
clickable: '.dz-default.dz-message',
previewsContainer: '.dz-default.dz-message',
thumbnailWidth: 200,
thumbnailHeight: 200,
parallelUploads: 100,
autoProcessQueue: false,
uploadMultiple: false
});
$('#item-submit').click(function(e) {
e.preventDefault();
e.stopPropagation();
if (dropzone.getQueuedFiles().length > 0) {
return dropzone.processQueue();
}
else {
return $('#dropform').submit();
}
});
return dropzone.on('success', function(file, responseText) {
return window.location.href = '/photos/' + responseText.id;
});
return dropzone.on('error', function(file, errorMessage, xhr) {
console.log('error');
});
});
验证失败时,视图中未呈现任何错误。拖放区缩略图上只有一个 "X",悬停时有一条消息 "Internal Server Error"。缩略图仍显示在视图中,尽管它实际上已被删除。如果我再次点击提交,表单将被处理为html,因为dropzone/nojson中没有照片可以提交。
所以我决定不用担心表单内的 Rails Active Record Validation Errors 这样做,这甚至可能是不可能的,因为表单是由 json 提交的,并且Rails helpers 可能没有设置为那样工作,我决定通过将错误附加到视图中,在 dropzone.on('error', function(file, errorMessage)
中使用 .js 文件本身手动完成。