Python Connexion:如何处理/转发HTTP错误?

时间:2019-07-03 08:56:29

标签: python python-3.x rest flask connexion

我刚开始使用Connexion和Flask,却不知道如何处理HTTP错误,例如401,是通过调用另一个API产生的。换句话说,我要实现的是简单地转发来自外部API的可能错误。

server.py

import json
import os

import connexion
import requests
from connexion import FlaskApp

def auth():
    credential: Credential = connexion.request.get_json()

    print("Credential")
    print(credential)

    AUTHENTICATION_SERVER: str = 'AUTHENTICATION_SERVER'
    AUTHENTICATION_API: str = 'AUTHENTICATION_API'

    authentication_server: str = 'http://localhost:8080'
    authentication_api = '/api/authenticate'

    if AUTHENTICATION_SERVER in os.environ:
        authentication_server = os.environ.get(AUTHENTICATION_SERVER)

    if AUTHENTICATION_API in os.environ:
        authentication_api = os.environ.get(AUTHENTICATION_API)

    authentication_url: str = authentication_server + authentication_api

    headers = {'Content-type': 'application/json'}

    response: Response = requests.post(authentication_url, data=json.dumps(credential), headers=headers)
    response.raise_for_status()
    return response.json()


def render_unauthorized(exception):
    print('Unauthorized handler fn')

    return Response(response=json.dumps({'error': 'Wrong credentials'}), status=401,
                    mimetype="application/json")


# If we're running in stand alone mode, run the application
if __name__ == '__main__':
    # Create the Connexion instance
    app: FlaskApp = connexion.FlaskApp(__name__, specification_dir='OpenAPI')

    # Add error handler
    app.add_error_handler(AuthenticationProblem, render_unauthorized)

    # Read the swagger.yml file to configure the endpoints
    app.add_api('swagger.yml')
    app.run(host='0.0.0.0', port=5000, debug=True)

凭据类

class Credential:
    def __init__(self, username: str, password: str):
        self.username = username
        self.password = password

Connexion所述,我为错误创建了该类,同时扩展了ProblemExceptionUnauthorized

AuthenticationProblem类

from connexion import ProblemException
from werkzeug.exceptions import Unauthorized


class AuthenticationProblem(ProblemException, Unauthorized):
    def __init__(self, title=None, **kwargs):
        super(Unauthorized, self).__init__(title=title, **kwargs)

最后,这是相应的 swagger.yml 文件:

openapi: 3.0.0
info:
  title: Swagger REST Article
  description: API Swagger file
  contact: {}
  version: '1.0.0'
servers:
  - url: https://{host}:{port}/api
    variables:
      host:
        default: localhost
      port:
        default: '5000'
paths:
  /auth:
    post:
      summary: Authenticate the user
      description: Authenticate the user
      operationId: server.auth
      requestBody:
        content:
          application/json:
            schema:
              $ref: '#/components/schemas/credential'
        description: The user credentials
        required: true
      responses:
        200:
          description: Authentication success
        401:
          description: Wrong Credentials
      security: [] # No Authentication Required

# Define the security scheme type (HTTP bearer)
components:
  securitySchemes:
    jwt: # arbitrary name for the security scheme
      type: http
      scheme: bearer
      bearerFormat: JWT # optional, arbitrary value for documentation purposes
      x-bearerInfoFunc: security.jwt_filter.validate
  schemas:
    credential:
      type: object
      properties:
        username:
          description: The username of the user
        password:
          description: The password of the user
      required:
        - username
        - password

当我尝试在 / auth 上通过 POST 提供错误的凭据时,会导致500 Internal Server错误,而不是401响应。 此代码有什么问题?

0 个答案:

没有答案