我正在构建一个JSON API,到目前为止,我还没有找到关于如何在使用RABL模板的控制器中处理保存错误的好建议。我非常感谢有关改进代码的任何建议。
以下是我目前处理保存失败的方法:
# products_controller.rb
def create
@product = Product.new(params[:product])
unless @product.save
render json: @product.errors, status: :unprocessable_entity
end
end
这是我的RABL模板:
# product.json.rabl
object @product
attributes :name, :price
它有效,但除非@ product.save'感觉不对......以下是测试:
# products_controller_test.rb
test 'create a product' do
assert_difference 'Product.count', 1 do
post :create, product: { name: 'Apple', price: 1.25 }, format: :json
end
assert_response :success
end
test 'failing product creation' do
Product.any_instance.stubs(:save).returns(false)
assert_no_difference 'Product.count' do
post :create, product: { name: 'Apple' }, format: :json
end
assert_response 422
end
更新
感谢@KonradOleksiuk,我能够以更易读的方式重写控制器:
if @product.save
respond_with @product
else
respond_with @product, status: :unprocessable_entity
end
我还必须确保错误附加到json响应:
# product.json.rabl
object @product
attributes :name, :price
node :errors do |o|
o.errors
end
答案 0 :(得分:1)
这取决于您希望在响应中实现的格式。您始终可以在rabl模板中使用node
来内联呈现错误。宝石的合作者已经解释过:https://github.com/nesquena/rabl/issues/222#issuecomment-5413021
多亏了这一点,您可以避免使用除非声明并仅使用视图。
答案 1 :(得分:0)
def create
@product = Product.new(params[:product])
@product.save
respond_with @product
end
两种情况都适用于成功和失败的保存。 如果保存失败,则respond_with将使用@product错误呈现json,在成功的情况下,它将呈现rabl模板