2017-10-09 1 views
0

L'application en question utilise connexion, qui enveloppe le flacon, pour prendre soin du serveur Web. L'API est spécifiée avec swagger. Existe-t-il un moyen facile et direct d'obtenir quelque part dans le code où les réponses http sont formulées à partir du serveur Web?Consigner toutes les réponses http avec un code d'erreur> = 400

Si possible, je voudrais éviter d'écrire 200 errorhandlers, ou les 10 plus populaires et croisant mes doigts.

api.py

import connexion 
app = connexion.App(__name__, 
       specification_dir='../swagger/', 
       swagger_ui=False, 
       validator_map={ 
        'body': connexion.decorators.validation.RequestBodyValidator 
       }) 
app.add_api('swagger.yml', strict_validation=True) 

# If I had to use app.error_handler decorators to implement the special 
# treatment of http responses with error codes, I would put it here 

swagger.yml

swagger: '2.0' 
info: 
    title: My Minimal Working Example 
consumes: 

    - application/json 
produces: 
    - application/json 

basePath: /api/v1 
paths: 
    '/do_something': 
    post: 
     tags: 
     - MyTag 
     operationId: entrypoint.do_something 
     summary: Do something on request 
     parameters: 
     - name: data 
      in: body 
      schema: 
      $ref: '#/definitions/data' 
     responses: 
     '200': 
      description: Success! 
      schema: 
      $ref: '#/definitions/Response' 
     '400': 
      description: Error! 
      schema: 
      $ref: '#/definitions/Response' 
     '403': 
      description: Not Authorized 
      schema: 
      $ref: '#/definitions/Response'  
# a lot more stuff and "definitions" 
+1

Si vous n'écrivez pas de code directement et que vous utilisez simplement Swagger, vous êtes limité à ce que Swagger peut faire. Sinon, il existe des moyens de sous-classer Flask et de surcharger sa gestion des erreurs. Ne sachant pas Swagger ou Connexion, je ne sais pas si cela serait possible dans votre cas. Avez-vous le contrôle sur la classe Flask ou l'instance d'application? – davidism

+0

Je suis en train d'écrire du code directement et j'ai le contrôle sur l'instance de l'application – Arne

+0

Veuillez [edit] inclure un [mcve] démontrant cela. – davidism

Répondre

1

I résolu le problème en dérivant l'objet Flask, comme suggéré davidism. La version courte est la suivante:

app.py

import logging.config 
import yaml 

logging.config.dictConfig(yaml.load(open('logging.conf', 'r'))) 
logger = logging.getLogger("mainLogger") 


class LoggingFlask(Flask): 
    def make_response(self, rv): 
     rv = super(LoggingFlask, self).make_response(rv) 
     if int(rv.status_code) >= 300: 
      logger.warn("Request failed with error code %s." % rv.status_code) 
     return rv 


app = LoggingFlask(__name__) 

session.log

./app.py 
[2017-10-10 11:38:19,564 - werkzeug - INFO]: * Running on http://127.0.0.1:5000/ (Press CTRL+C to quit) 
[2017-10-10 11:38:19,566 - werkzeug - INFO]: * Restarting with stat 
[2017-10-10 11:38:19,690 - werkzeug - WARNING]: * Debugger is active! 
[2017-10-10 11:38:19,691 - werkzeug - INFO]: * Debugger PIN: 211-310-838 

# issues a good request 
[2017-10-10 11:38:25,179 - werkzeug - INFO]: 127.0.0.1 - - [10/Oct/2017 11:38:25] "GET /todo/api/v1.0/tasks HTTP/1.1" 200 - 

# issued a bad request 
[2017-10-10 11:38:28,646 - mainLogger - WARNING]: Request failed with error code 404. 
[2017-10-10 11:38:28,646 - mainLogger - WARNING]: Request failed with error code 404. 
[2017-10-10 11:38:28,647 - werkzeug - INFO]: 127.0.0.1 - - [10/Oct/2017 11:38:28] "GET /todo/api/v1.0/task HTTP/1.1" 404 - 

Si quelqu'un sait comment accéder à la demande qui a déclenché la réponse actuelle, ne hésitez pas pour laisser un commentaire afin que je puisse l'inclure dans cette réponse.