我正在用ruby在Rails上编写一个API,我发现我的方法非常重复。这就是我几乎所有方法的样子。它们都遵循相似的结构。我只是抓住了我的一种方法,并将其放在这里:
def create
if current_user
@object = Object.new(object_params)
if @object.save
render json: {
status: "SUCCESS",
message: "object saved"
}, status: :ok
else
render json: {
status: "ERROR",
message: "Could not save object"
}, status: :unprocessable_entity
end
else
render json: {
status: "UNAUTHORIZED"
}, status: :unauthorized
end
end
当然,不是我的所有方法都可以创建和保存对象。但是它们都遵循类似的模式。首先,我检查current_user
是否不为零。如果是,我将呈现JSON响应:
if current_user
# do something
else
render json: {
status: "UNAUTHORIZED"
}
如果找到当前用户,并且无论该方法必须运行成功,那么我将呈现另一个JSON响应:
if everything_went_well
render json: {
status: "SUCCESS",
message: "Everything went ok!"
}
else
render json: {
status: "ERROR",
message: "There was a problem!"
}
end
我很确定有一种抽象这种功能的方法。我在网上查找了一些有用的提示,但这些提示对项目的其他部分(例如模型和视图)有所帮助。但是,我在网上看到的大多数技巧都不太适合我控制器中的代码。
答案 0 :(得分:2)
您可以为此使用before_filter
。请注意,当before_action
已经呈现视图时,该动作本身将不再被调用。
before_action :check_permission
def create
@object = Object.new(object_params)
if @object.save
render json: {
status: "SUCCESS",
message: "object saved"
}, status: :ok
else
render json: {
status: "ERROR",
message: "Could not save object"
}, status: :unprocessable_entity
end
end
private
def check_permission
return if current_user
render json: {
status: "UNAUTHORIZED"
}, status: :unauthorized
end
答案 1 :(得分:0)
如果所有控制器看起来都是这样,那么您可以拥有一个基本控制器,并使所有其他控制器都从该控制器继承。这将使您的代码为DRY。
因此,您的基本控制器将如下所示:
class API::BaseController < ApplicationController
protected
def check_permission
return if current_user
render json: {
status: "UNAUTHORIZED"
}, status: :unauthorized
end
def render_success
render json: {
status: "SUCCESS",
message: "object saved"
}, status: :ok
end
def render_error
render json: {
status: "ERROR",
message: "Could not save object"
}, status: :unprocessable_entity
end
end
然后在您的一个控制器中:
class API::OtherController < API::BaseController
before_filter :check_permission
def create
@object = Object.new(object_params)
if @object.save
render_success
else
render_error
end
end
end
您也可以将before_filter
部分移到基本控制器上,但是灵活性较差。在当前设置下,您只能针对某些操作(例如before_filter :check_permission, only: [:create]
)使用该过滤器。
但是如果将before_filter
移至基本控制器,则会失去灵活性。