处理Flask API

时间:2017-04-03 09:13:43

标签: python flask

我正在使用Flask为我们的解决方案编写一个简单的内部REST API,通过get调用(包括身份验证)提供JSON对象。我们有多个后端来从中获取数据。根据我的理解,这些应该连接到一个用@app.before_request修饰的函数,并分配给g全局,以便在请求的特定路径中使用。这不是我以前的模式。

以下是我正在做的事情的一个玩具示例:

@app.before_request
def before_request():
    g.some_conn_a = create_connection('a')
    g.some_conn_b = create_connection('b')
    g.some_client = create_client()


@app.route('/get_some_data')
@requires_auth
def get_some_data():
    # Fetch something from all connections in g
    payload = ... # Construct payload using above connections
    return jsonify(payload)


@app.route('/get_some_other_data')
@requires_auth
def get_some_other_data():
    # Fetch something from maybe just g.some_conn_b
    payload = ... # Construct payload using g.some_conn_b
    return jsonify(payload)

如果用户请求仅驻留在这些连接/客户端中的一个或两个中的数据,这对我来说似乎很浪费,例如在get_some_other_data路由示例中。

我只是考虑在路由功能中建立连接/客户端,或者懒惰地加载它。什么是"正确"办法?我希望不要制作一个新的模块,这对我正在做的事情来说似乎极端。

1 个答案:

答案 0 :(得分:1)

重新the Flask docs Database Connections example 您可以修改 get_db()以接受每个多个连接的参数。

def get_db(conn):
    """Open specificied connection if none yet for the current app context. """
    if conn == 'some_conn_a':
        if not hasattr(g, 'some_conn_a'):
            g.some_conn_a = create_connection('a')
        db = g.some_conn_a
    elif conn == 'some_conn_b':
        if not hasattr(g, 'some_conn_b'):
            g.some_conn_b = create_connection('b')
        db = g.some_conn_b 
    elif conn == 'some_client':
        if not hasattr(g, 'some_client'):
            g.some_client = create_client()
        db = g.some_client
    else:
        raise Exception("Unknown connection: %s" % conn)

    return db

@app.teardown_appcontext
def close_db(error):
    """Closes the db connections. """
    if hasattr(g, 'some_conn_a'):
        g.some_conn_a.close()
    if hasattr(g, 'some_conn_b'):
        g.some_conn_b.close()
    if hasattr(g, 'some_client'):
        g.some_client.close()

然后您可以根据需要查询每个连接:

@app.route('/get_some_data')
def get_some_data():
    data_a = get_db('some_conn_a').query().something()
    data_b = get_db('some_conn_b').query().something()
    data_c = get_db('some_client').query().something()
    payload = {'a': data_a, 'b': data_b, 'c': data_c}
    return jsonify(payload)

对于延迟加载数据库连接, get_db()模式优先于 before_request 模式。 Flask 0.11及更高版本的文档示例更大程度地利用了 get_db()模式。