使用自定义错误处理程序时如何从中止命令访问错误消息

Posted

技术标签:

【中文标题】使用自定义错误处理程序时如何从中止命令访问错误消息【英文标题】:how to get access to error message from abort command when using custom error handler 【发布时间】:2014-02-13 05:12:22 【问题描述】:

使用 python 烧瓶服务器,我希望能够使用 abort 命令引发 http 错误响应,并在正文中使用自定义响应字符串和自定义消息

@app.errorhandler(400)
def custom400(error):
    response = jsonify('message': error.message)
    response.status_code = 404
    response.status = 'error.Bad Request'
    return response

abort(400,'"message":"custom error message to appear in body"')

但是 error.message 变量显示为空字符串。我似乎找不到有关如何使用自定义错误处理程序访问中止函数的第二个变量的文档

【问题讨论】:

error.description 是您要找的吗? 【参考方案1】:

flask.abort 也接受flask.Response

abort(make_response(jsonify(message="Error message"), 400))

【讨论】:

你甚至不需要使用 jsonify: abort(make_response('message': 'Error message', 400))【参考方案2】:

人们过于依赖abort()。事实上,有很多更好的方法来处理错误。

例如,你可以编写这个辅助函数:

def bad_request(message):
    response = jsonify('message': message)
    response.status_code = 400
    return response

然后从你的视图函数中你可以返回一个错误:

@app.route('/')
def index():
    if error_condition:
        return bad_request('message that appears in body')

如果错误在调用堆栈的更深处发生在无法返回响应的位置,那么您可以使用自定义异常。例如:

class BadRequestError(ValueError):
    pass

@app.errorhandler(BadRequestError)
def bad_request_handler(error):
    return bad_request(str(error))

然后在需要发出错误的函数中,您只需引发异常:

def some_function():
    if error_condition:
        raise BadRequestError('message that appears in the body')

我希望这会有所帮助。

【讨论】:

在可能的情况下直接使用return bad_request(...) 是否比raise BadRequestError(...) 更可取(更快)? 您可以在任何时候提出 abort,无需返回。 如何更好?如果不是从视图中完成(并且您需要注册错误处理程序),唯一的区别是您调用 raise BadRequestError 而不是 abort,这增加了必须注册自定义异常的复杂性。【参考方案3】:

我只是这样做:

    abort(400, description="Required parameter is missing")

【讨论】:

我认为最好的答案。 当你想返回一个 json 类型的响应时。你需要 make_response。 为了澄清 Minh 7 月 7 日的评论,在 Werkzeug>=1.0.1 中,此答案中的代码将生成正确的 JSON 响应。我什至能够传递dict 作为描述,Werkzeug 正确地生成了一个嵌套的 JSON 响应。 不幸的是,这会返回我不想要的 html。我只想打印消息。这是 curl 输出的样子:<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 3.2 Final//EN"> <title>403 Forbidden</title> <h1>Forbidden</h1> <p>Required parameter is missing</p>【参考方案4】:

如果您查看flask/__init__.py,您会看到abort 实际上是从werkzeug.exceptions 导入的。查看Aborter class,我们可以看到当使用数字代码调用时,特定的HTTPException 子类被查找并使用提供给Aborter 实例的所有参数调用。查看HTTPException,特别注意lines 85-89,我们可以看到传递给HTTPException.__init__ 的第二个参数存储在description 属性中,正如@dirn 指出的那样。

您可以通过description 属性访问消息:

@app.errorhandler(400)
def custom400(error):
    response = jsonify('message': error.description['message'])
    # etc.

abort(400, 'message': 'custom error message to appear in body')

或者只是自己传递描述:

@app.errorhandler(400)
def custom400(error):
    response = jsonify('message': error.description)
    # etc.

abort(400, 'custom error message to appear in body')

【讨论】:

这是使用自定义错误消息扩展 abort 功能的好方法。谢谢你 有没有办法对每个状态代码执行此操作,而不必为每个代码编写自定义错误处理程序?例如:abort(409, 'There was a time conflict')abort(400, 'custom error message to appear in body') 重复答案 - ***.com/a/45412576/853167

以上是关于使用自定义错误处理程序时如何从中止命令访问错误消息的主要内容,如果未能解决你的问题,请参考以下文章

如何在 NodeJS 中自定义 keycloak 错误消息

Spring MVC for Rest 服务如何在 Jackson 反序列化错误时自定义错误“消息”?

ionic 调用restful API services时全局错误处理的实现 或自定义错误处理的实现

如何使用 AJV 创建自定义错误消息?

如何使用自定义消息处理错误请求 Web api 核心?

当我从中调用非静态方法时,如何使处理程序静态以避免泄漏?