2012-09-27 101 views
25

Estoy diseñando una API RESTful utilizando Python y Flask. Como se esperaba, la API necesita recibir una solicitud de API y devolver datos si todo va bien, pero en el caso de un error, debe fallar suavemente y devolver el error adecuado. Normalmente planteo excepciones cuando se produce un error, pero en este caso necesito devolver el mensaje de error al usuario (¿bloque try-catch?).Devolver mensajes de error de API con Python y Flask

La forma en que actualmente estoy lidiando con errores es hacer que mis funciones devuelvan los datos y un error, y verificar los datos en cada nivel, finalmente devolviendo los datos o el error a la persona que llama de la función API .

El problema con esto es que puede resultar engorroso cuando hay varios niveles de llamadas a funciones, lo que requiere que mis funciones pasen datos y errores varias veces y realicen comprobaciones cada vez.

¿Hay una mejor manera de hacerlo? ¿Cuáles son algunas mejoras que podría hacer para que la propagación de errores sea más simple y elegante?

Aquí se muestra un ejemplo de la forma en que actualmente estoy volviendo errores:

def get_data() 
    data1, error = get_some_data() # function not shown 
    if data1 is None: 
     return None, "could not retrieve data1" 
    data2, error = get_some_other_data() # function not shown 
    if data2 is None: 
     return None, "could not retrieve data2" 
    return (data1, data2), None 

@app.route("/api/method", methods=['GET']) 
def method(): 
    data, error = get_data() 
    if data is None: 
     if error is None: 
      error = "unknown error" 
     return json.dumps({ "error": error }), 500 
    return json.dumps({ "data": data }), 200 
+0

¿Por qué no utilizar las excepciones? – georg

+0

Porque eso devolverá un error interno del servidor sin un mensaje adecuado en formato json. Piense en el estilo de API de Facebook. – Ryan

+0

Estoy de acuerdo con @ thg435. Me parece que un intento ... excepto que limpiaría un poco tu "método". Simplemente moverá su bloque de manejo de errores al bloque "except" y todavía puede devolver el mensaje de error. Así es como lo hago en Django con llamadas Ajax. Además, no tengo ninguna experiencia con Flask, pero si esta es una API RESTful (ish). y parece ser porque va a obtener un "GET", debe devolver un código de estado apropiado. 200 si las cosas están bien. O un 4XX o 500 (dependiendo de cuál sea el problema subyacente). –

Respuesta

21

Usted podría utilizar abort(http_code) a devolver un código http apropiada para el cliente o simplemente levantar una no-http excepción. Y use el decorador @app.errorhandler() para proporcionar un controlador personalizado para errores http y excepciones arbitrarias. También podría usar un bloque try/except ordinario donde esté listo para manejar una excepción. Python no es Ir, puede usar excepciones.

+0

Me gusta la idea de elevar no-excepción http plus @ app.errorhandler(). Voy a verlo en la documentación del Frasco y luego veré qué tan bien funciona. – Ryan

+0

Este enfoque funcionó muy bien. ¡Gracias! – Ryan

+0

+1 - 'errorhandler' y' throw'ing exceptions realmente es la respuesta correcta –

Cuestiones relacionadas