I want to update my DataFrame that feeds my graphs in realtime. In all the tutorials I have found, the DataFrame is created before creating the app layout. I want to take the input from the input component with the username_input ID and use that in the get_dataFrame function to create my initial DataFrame which will create the figure which will be used in the graph component.
app = Dash(__name__)
df = get_dataFrame(username_input)
fig = px.line(df, x='end', y="user",color="class")
app.layout = html.Div(children=[
dcc.Input(
id="username_input",
placeholder="username",
type='text'
),
dcc.Graph(
id='example-graph',
figure=fig
),
])
I don't fully understand how to structure the code so that this is possible. In essence I want a user input first and then after the user input all the dash data updates to reflect the new input. Any ideas?
Move your dataframe and figure creation into your callback, then return a new figure after the user's input comes in. Working example:
from dash import Dash, dcc, html, Input, Output, no_update
import pandas as pd
import plotly.express as px
import numpy as np
app = Dash(__name__)
def get_dataFrame(username_input):
data = np.random.rand(10) * len(username_input)
return pd.DataFrame({"end": [*range(10)], "user": data, "class": ["red"] * 10})
fig = px.line()
app.layout = html.Div(
children=[
dcc.Input(id="username_input", placeholder="username", type="text"),
dcc.Graph(id="example-graph", figure=fig),
]
)
#app.callback(
Output("example-graph", "figure"), Input("username_input", "value"),
)
def func(username_input: str):
if username_input:
df = get_dataFrame(username_input)
fig = px.line(df, x="end", y="user", color="class")
return fig
return no_update
if __name__ == "__main__":
app.run(debug=True)
Related
I'm trying to export the dynamic dash plot to html. here is my code, when I click download as html after the plot appear, I was only able to download an empty plot, it came back nothing.
What went wrong? thank you
from dash import Dash, dcc, html,Input, Output, callback,dash_table
import plotly.express as px
from base64 import b64encode
import io
app = Dash(__name__)
buffer = io.StringIO()
df=tem1 # tem1 is my own dataset
html_bytes = buffer.getvalue().encode()
encoded = b64encode(html_bytes).decode()
app.layout = html.Div([
html.H4('Test Graph'),
dcc.Graph(id="graph"),
dcc.Checklist(
id="checklist",
options=['A','B','C'],
value=['A','B','C'],
inline=True),
html.A(
html.Button("Download as HTML"),
id="download",
href="data:text/html;base64," + encoded,
download="plotly_graph.html"
)
])
#app.callback(
Output("graph", "figure"),
Input("checklist", "value"))
def update_line_chart(Programs):
mask = df.Program.isin(Programs)
fig = px.line(df[mask],
x="Month", y="Mood", color='Group',text='Module')
return fig
#app.callback(
Output('download','n_clicks'),
[Input('graph','figure')])
def download_html(n):
return n.write_html(buffer)
app.run_server(debug=False,port=8051)
I referred to this post, but it couldn't solve my problem.
Your referred code is my question and I think you should fix it as below:
Add dcc.Download
Save fig to html first
Use dcc.send_file to download html file
I don't have your df so please refer below code:
from dash import Dash, dcc, html,Input, Output, callback,dash_table
import plotly.express as px
from base64 import b64encode
import io
app = Dash(__name__)
df = px.data.gapminder()
app.layout = html.Div([
html.H4('Test Graph'),
dcc.Graph(id="graph",figure=fig),
dcc.Checklist(
id="checklist",
options=['A','B','C'],
value=['A','B','C'],
inline=True),
html.A(
html.Button("Download as HTML"),
id="download"
),
dcc.Download(id='download_1')
])
#app.callback(
Output("graph", "figure"),
Input("checklist", "value"))
def update_line_chart(Programs):
fig = px.scatter(df.query("year==2007"), x="gdpPercap", y="lifeExp",
size="pop", color="continent",
hover_name="country", log_x=True, size_max=60)
fig.write_html("plotly_graph.html")
return fig
#app.callback(
Output('download_1','data'),
Input('download','n_clicks'),prevent_initial_call=True)
def download_html(n):
return dcc.send_file("plotly_graph.html")
app.run_server(debug=False,port=8051)
Hope this help
I'm pretty new to Dash. I created two dashboards that read from two different dataframes. They work well individually. I would like to merge them in a single one, giving the possibility to the user to access them using a dropdown menu.
I would like to also add a button which (when clicked) returns a function.
Those are the two dashboards:
first one:
import pandas as pd
df1 = pd.read_csv('/df1.csv')
# Import libraries
from dash import Dash, html, dcc, Input, Output
import pandas as pd
import plotly.express as px
# Create the Dash app
app = Dash()
# Set up the app layout
options_dropdown = dcc.Dropdown(options=df1['options'].unique(),
value='wordcount')
app.layout = html.Div(children=[
html.H1(children='offensive/non offensive username activity dashboard'),
options_dropdown,
dcc.Graph(id='df1')
])
# Set up the callback function
#app.callback(
Output(component_id='df1', component_property='figure'),
Input(component_id=options_dropdown, component_property='value')
)
def update_graph(sel_option):
filtered_options = df1[df1['options'] == sel_option]
bar_fig = px.bar(filtered_options,
x= "user", y = "value",
color='user',
color_discrete_map={
'off': '#d62728',
'non_off': 'green'},
title=f' average {sel_option}',
width=500, height=500)
return bar_fig
print(df1)
# Run local server
if __name__ == '__main__':
app.run_server(debug=True)
second one:
import pandas as pd
df2 = pd.read_csv('/df2.csv')
# Import libraries
from dash import Dash, html, dcc, Input, Output
import pandas as pd
import plotly.express as px
# Create the Dash app
app = Dash()
# Set up the app layout
options_dropdown = dcc.Dropdown(options=df2['options'].unique(),
value='wordcount')
app.layout = html.Div(children=[
html.H1(children='offensive/non offensive username activity dashboard'),
options_dropdown,
dcc.Graph(id='df2')
])
# Set up the callback function
#app.callback(
Output(component_id='df2', component_property='figure'),
Input(component_id=options_dropdown, component_property='value')
)
def update_graph(sel_option):
filtered_options = df2[df2['options'] == sel_option]
line_fig = px.line(filtered_options,
x= "Week_Number", y = "value",
color='offensive',
color_discrete_map={
1: '#d62728',
0: 'green'},
title=f' average {sel_option}')
return line_fig
print(df2)
# Run local server
if __name__ == '__main__':
app.run_server(debug=True)
and this is the function I want to implement pressing a button:
sentences = []
df3 = pd.read_csv('/df3.csv')
def cool_function():
ext = rd.randint(0,len(df3.offensive))
return rd.choice(sentences).format(df3.author[ext], "", df3.text[ext])
How do I merge those three elements in a single dashboard?
I'm trying to set my Dash app to automatically pull the latest data from a .csv file used in the data frame with dcc.Interval. The error code isn't providing a detailed explanation and also doesn't always appear. I've tried this with both a button and a set 6 sec interval, but the result seems to be the same. The Dash app runs fine at first and refreshes fine a few times, then error starts occurring:
Callback error updating graph.figure
import dash
import dash_core_components as dcc
import dash_html_components as html
from dash.dependencies import Input, Output
import plotly.express as px
import plotly.graph_objects as go
import pandas as pd
app = dash.Dash(__name__)
server = app.server
df = pd.read_csv('example.csv', encoding="WINDOWS-1252")
app.layout = html.Div([
dcc.Graph(id='graph'),
dcc.Interval(
id='interval-component',
interval=1*6000,
n_intervals=0
)
])
#app.callback(
Output('graph','figure'),
[Input('interval-component', 'n_intervals')]
)
def update_df(n):
updated_df = pd.read_csv('example.csv', encoding="WINDOWS-1252")
fig = px.scatter(updated_df, x='Date', y='Deviation', height=800)
fig.update_layout(
yaxis_tickformat = '.0%',
)
fig.update_xaxes(
rangeslider_visible=True,
rangeselector=dict(
)
)
return fig
if __name__ == '__main__':
app.run_server(debug=True)
I think your issue must have something to do with your file specifically, because the following code based exactly off as you provide (with the exception of generation of random matching-df timeseries data), works perfectly updating with an interval of every 6 seconds:
import dash
import dash_core_components as dcc
import dash_html_components as html
from dash.dependencies import Input, Output
import plotly.express as px
import plotly.graph_objects as go
import pandas as pd
import numpy as np
np.random.seed(2019)
def get_random_deviation_ts_df(N=100):
rng = pd.date_range("2019-01-01", freq="D", periods=N)
df = pd.DataFrame(np.random.rand(N, 1), columns=["Deviation"], index=rng)
df["Date"] = df.index
return df
app = dash.Dash(__name__)
server = app.server
# df = pd.read_csv('example.csv', encoding="WINDOWS-1252")
app.layout = html.Div(
[
dcc.Graph(id="graph"),
dcc.Interval(
id="interval-component", interval=1 * 6000, n_intervals=0
),
]
)
#app.callback(
Output("graph", "figure"), [Input("interval-component", "n_intervals")]
)
def update_df(n):
updated_df = (
get_random_deviation_ts_df()
) # pd.read_csv('example.csv', encoding="WINDOWS-1252")
fig = px.scatter(updated_df, x="Date", y="Deviation", height=800)
fig.update_layout(yaxis_tickformat=".0%",)
fig.update_xaxes(rangeslider_visible=True, rangeselector=dict())
return fig
if __name__ == "__main__":
app.run_server(debug=True)
I recently wrote a dash program
it is refreshing number of records and refreshes or redraws the fig
the problem is when I do filter over 1 or multiple legends it won't show any of the points
but when you hover over invisible points it shows the data of the point
my code:
from threading import Event
import dash
from dash import dcc, Input, Output
from dash import html
from dash.dcc.Interval import Interval
import plotly.express as px
import pandas as pd
import sqlalchemy
app = dash.Dash(__name__)
# assume you have a "long-form" data frame
# see https://plotly.com/python/px-arguments/ for more options
connection = sqlalchemy.create_engine('mysql+pymysql://*:*#localhost:*')
df = pd.read_sql_table('rawdata_clean', connection)
fig = px.scatter(df, x="Size", y="Price", color="Neighbourhood_Per")
index = df.index
app.layout = html.Div(children=[
html.H1(id='Numberofrecords', children= len(index)),
dcc.Interval(id='up-Numberofrecords', interval=3000, n_intervals=0),
html.Div(children='''
Dash: A web application framework for Python.
'''),
dcc.Graph(
id='grph',
animate=True
),
dcc.Interval(id='up-graph', interval=3000, n_intervals=0)
])
#app.callback(Output('grph', 'figure'),
Input('up-graph', 'n_intervals'))
def update_graph (n):
df = pd.read_sql_table('rawdata_clean', connection)
fig = px.scatter(df, x="Size", y="Price", color="Neighbourhood_Per")
return fig
#app.callback(Output('Numberofrecords', 'children'),
Input('up-Numberofrecords', 'n_intervals'))
def up_Numberofrecords (n):
df = pd.read_sql_table('rawdata_clean', connection)
index = df.index
print('up_Numberofrecords')
return len(index)
if __name__ == '__main__':
app.run_server(debug=True, port=9876)
is there any problems with this code?
i'm new to dash and plotly :D
the problem was :
animate=True
IDK what this code does but by deleting it, it get to work
When I run the code i get the graph but the graph is not getting updated i am calling the data from my sql laptop sql management studio.
Kindly let me know what needs to be done the X axis contains date and time and Y axis contains data in numeric form which is getting updated automatically
Code:
import pandas as pd
import pyodbc
import numpy as np
server ='LAPTOP-OO3V36UA\SQLEXPRESS'
db='addy'
conn=pyodbc.connect('DRIVER={SQL Server}; SERVER=' +server + ';DATABASE=' + db +
';Trusted_connection=yes')
sql="""
SELECT * FROM Summry
"""
df=pd.read_sql(sql ,conn)
import dash
from dash.dependencies import Output, Input
import dash_core_components as dcc
import dash_html_components as html
from random import random
import plotly
app = dash.Dash(__name__)
app.layout = html.Div([
dcc.Graph(id='live-update-graph-scatter', animate=True),
dcc.Interval(
id='interval-component',
interval=1*1000
)
])
#app.callback(Output('live-update-graph-scatter', 'figure'),
[Input('interval-component', 'interval')])
def update_graph_scatter():
df=pd.read_sql(sql ,conn)
trace1=go.Scatter(
y=df['ACL'],
x = df['DateandnTime'],
mode='lines',
name='ACL'
)
layout = go.Layout(
title='Daily Monitoring'
)
return {'data': trace1, 'layout': layout}
if __name__ == '__main__':
app.run_server()
You've set your callback's input to
Input('interval-component', 'interval')
But you want
Input('interval-component', 'n_intervals')
The interval property sets how frequently n_intervals gets updated. The change in n_intervals is what can be used to trigger the callback.
Here's the documentation: https://dash.plotly.com/dash-core-components/interval