【问题标题】:Dash long tasks via redis queue通过 redis 队列冲刺长任务
【发布时间】:2020-08-11 00:06:41
【问题描述】:

我想在 Dash 中构建一个 Web 应用程序,该应用程序对用户输入的数据执行计算量很大的任务,并以表格格式返回结果。 在前端,我有一个 Dash 回调,它根据 Dash 组件的输入更新 Dash 组件,例如:

from rq import Queue
from worker import conn
import time

# redis connection to execute tasks in the background
q = Queue(connection=conn,job_timeout='3m')
@app.callback(
    [Output('table-columns', 'columns'),
     Output('table-columns', 'data'),],
    [Input('upload', 'contents'),
     Input('launch-expensive-job-button', 'n_clicks')],
     )

def expensive_task(contents, n_clicks_launch):
    df = q.enqueue(expensive_function, contents).result
    while df is None:
        time.sleep(2)
    return [{"name": i, "id": i} for i in df.columns], df.to_dict("rows")

我正在使用 Redis 队列在后台运行任务。一旦结果在 df 变量中更新(Redis 约定在处理期间结果为 None),我就会将其返回给客户端。问题是我的部署平台不允许前端作业运行太久。因此,即使我将作业发送到后端,我也必须找到一种方法让 Dash 应用程序监听变量 df 的任何更新。

我确信解决方案在某个地方可以访问,但我太新手了,无法找到它。很高兴有人指出我可以找到的一些文档。

【问题讨论】:

    标签: heroku redis gunicorn plotly-dash


    【解决方案1】:

    我认为您正在寻找Interval 组件(文档here)。它定期触发客户端更新,例如每秒一次。回调将类似于,

    ...
    Interval(id='trigger', interval=1000)  # must be in the app layout
    ...
    
    @app.callback(Output(...), [Input('trigger', 'n_intervals')])
    def poll_update(n_intervals):
        # check status of redis here and update the output accordingly 
    

    【讨论】:

    • 感谢您的回答,Interval 组件绝对是要走的路。继续前进,您能否建议一种方法让Interval 组件的回调监听来自 df 变量的更新,而不是使变量成为全局变量?我目前仍然有义务在本地存储 df,因为它是一个相当大的数据集,所以如果我能够将它直接传输到回调,那就太好了。非常感谢!
    猜你喜欢
    • 2018-12-20
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2017-09-30
    • 1970-01-01
    • 2011-03-27
    • 2012-10-20
    • 1970-01-01
    相关资源
    最近更新 更多