Plotly Dash刷新重新加载的全局数据

8

假设我有一个dash应用程序,我希望在页面重新加载时刷新全局数据。 我使用一个函数作为布局,如此处所述。 但是,我不确定应该在何处定义df,以便我可以在回调函数中使用它(例如,在我想根据某些输入对df进行子集化并将其传递给布局表的情况下)。 我下面的代码在页面刷新时重新加载数据,但回调无法访问df

我对dash非常陌生,所以可能会提出一些愚蠢的问题,请事先谅解。

def serve_layout():
    df = # Fetch data from DB
    
    return # Layout

app.layout = serve_layout

@app.callback()
def my_func:
    # Here I want to reference df

数据库查询开销大吗(即需要很长时间)?您是否有多个回调引用数据框或仅有一个? - emher
该查询可能代价高昂,并且将有多个回调引用数据。基本上,我希望能够根据需要重新提供全局数据集。但是一旦加载了数据,应用程序中的所有内容都将基于它。 - CHRD
1个回答

9
最常见的在回调之间共享数据的方法是将数据保存在 dash_core_components.Store 对象中。
def serve_layout():
    df = # Fetch data from DB
    store = Store(id="mystore", data=df.to_json())  # The store must be added to the layout
    return # Layout 

您可以将该存储库作为State参数添加到需要访问数据的回调函数中。
@app.callback(..., [State("mystore", "data")])
def my_func(..., data):
    df = pd.read_json(data)

这种方法的主要缺点是每次调用回调时客户端和服务器之间都会交换数据。如果数据帧很小,那么这并不重要,但如果它很大,数据交换(以及序列化/反序列化为JSON)可能会导致严重的性能问题。可以通过在服务器端手动缓存数据帧(如documentation中所示)或使用dash-extensions提供的增强组件来避免这种情况。以下是后者的一个小例子。
import dash_core_components as dcc
import dash_html_components as html
import numpy as np
import pandas as pd

from dash_extensions.enrich import Dash, ServersideOutput, Output, Input, Trigger

app = Dash()
app.layout = html.Div([dcc.Store(id="store"),  # this is the store that holds the data
                       html.Div(id="onload"),  # this div is used to trigger the query_df function on page load
                       html.Div(id="log")])


@app.callback(ServersideOutput("store", "data"), Trigger("onload", "children"))
def query_df():
    return pd.DataFrame(data=np.random.rand(int(10)), columns=["rnd"])  # some random example data


@app.callback(Output("log", "children"), Input("store", "data"))
def print_df(df):
    return df.to_json()  # do something with the data


if __name__ == '__main__':
    app.run_server()

使用dash-extensions==0.0.27rc1进行测试。免责声明:我是dash-extensions的作者。


谢谢你的回答。如果数据框很大,是更好选择使用服务器端缓存还是将数据存储在浏览器中的隐藏div中? - CHRD
1
将数据存储在隐藏的 div 中,与使用 Store 对象具有类似的性能。如果您的数据框架很大,则应使用服务器端缓存。 - emher
也许有点跑题,但你提供的文档中提到“请注意,文件系统缓存在像Heroku这样具有临时文件系统的系统上无法工作。”。你知道这是否适用于GCP应用引擎吗? - CHRD
1
我已经很长时间没有使用 GCP 应用引擎了,但是当您部署到可扩展的、无状态的云环境时,通常需要使用另一种存储类型而不是文件系统。不过这有些偏离主题了(并且与 Dash 无关),所以我认为讨论应该在另一个问题中继续。 - emher

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接