【问题标题】:Using Flask-SQLAlchemy Event API to broadcast to Flask-SocketIO?使用 Flask-SQLAlchemy 事件 API 广播到 Flask-SocketIO?
【发布时间】:2014-07-23 00:42:48
【问题描述】:

我是一个新手,使用 Flask 作为 API 后端,使用 AngularJS 作为前端,开发一个简单的多用户游戏(想想 Minesweeper)。我按照教程构建了 Angular/Flask 应用程序,并使用 Flask-Restless 编写了一个 RESTful API。

现在我想在数据库中的游戏数据发生更改时将事件推送到所有客户端(因为它是通过 POST 到一个 Restless 端点)。我正在考虑使用 SqlAlchemy event.listen API 调用 Flask-SocketIO emit function 将数据广播给客户端。这是完成我想要做的事情的合适方法吗?这种方法有缺点吗?

【问题讨论】:

  • 方法很好;你试过什么?有什么失败吗?

标签: python angularjs flask socket.io flask-sqlalchemy


【解决方案1】:

如果您的所有计算都在同一个过程中完成,@CESCO 的回复效果很好。你也可以使用这种语法(see full source code here):

@sa.models_committed.connect_via(app)
def on_models_committed(sender, changes):
    for obj, change in changes:
        print 'SQLALCHEMY - %s %s' % (change, obj)

如果您有兴趣订阅数据库的所有更新,请继续阅读...




但是,如果您的数据库正在从另一个进程更新,这将不起作用。

models_committed 仅适用于提交来源的同一进程(它不是数据库级别的通知,它是提交到数据库后的 sqlalchemy)

https://github.com/mitsuhiko/flask-sqlalchemy/issues/369#issuecomment-170272020

我写了a little demo app,展示了如何使用 Redis、ZeroMQ 或 socketIO_client 中的任何一个来与您的服务器进行实时更新通信。这可能对尝试处理外部数据库访问的其他人有所帮助。

另外,您可以考虑订阅 postgres 事件: https://blog.andyet.com/2015/04/06/postgres-pubsub-with-json/

【讨论】:

    【解决方案2】:

    这就是您想要的代码的准系统版本。我会从那里开始测试。您必须弄清楚更改的含义,以便将正确的 SqlAlchemy 事件附加到您正在执行的更改类型。

    插入监听事件后的用户数据库

    from sqlalchemy import event   
    from app import socketio
    
    def after_insert_listener(mapper, connection, target):
        socketio.emit('namespace response',{'data': data[0]},
                      namespace='/namespace')
        print(target.id_user)
    
    event.listen(User, 'after_insert', after_insert_listener)
    

    SocketIO

    【讨论】: