adding LogTransform to app causes Duplicate callback output error
matt-sd-watson opened this issue · comments
When adding the LogTransform
as an app transformation:
transforms=[ServersideOutputTransform(backends=[backend_dir]),
LogTransform()]
Upon opening, my app now has a Duplicate callback outputs
error, despite not having the error without the transform.
The particular output in question uses a allow_duplicate=True
flag as needed.
It is probably related to the recent change in callback structure when allow_duplicate=True
flag was added. Could you post a small example demonstrating the issue?
I have the same issue. It came up as I upgraded my project dependencies from 0.1.13
to 1.0.4
. It seems that there is an undocumented breaking change in 1.0.0
? (I tried using 1.0.0
as a dependency instead of 1.0.4
but I still get the same error)
Interestingly, I just tried deploying my app with the LogTransform
added using 0.1.13
and, while it works on my localhost, I do not see any logging messages on my deploy server.
I have tried replicating the issue with a small example but I am not able to replicate it on a small example. Here is the code I used in an attempt to replicate it:
import secrets
from dash_extensions.enrich import (
DashProxy,
LogTransform,
Input,
Output,
State,
DashLogger
)
from dash import dcc, html, no_update
import flask
server = flask.Flask(__name__)
app = DashProxy(
transforms=[
LogTransform(),
],
external_stylesheets=[],
server=server,
)
app.server.secret_key = secrets.token_urlsafe(16)
app.layout = html.Div([
dcc.Input(id='text_input'),
html.Button("Click me", id="input_button"),
html.Button("Click me 2", id="input_button2"),
html.H2(id="output_region")
])
@app.callback(
Output("output_region", "children", allow_duplicate=True),
State('text_input', 'value'),
Input("input_button", "n_clicks"),
prevent_initial_call=True,
log=True,
)
def callback1(
input_text: str,
button_clicks: int,
dash_logger: DashLogger
):
if not input_text:
dash_logger.warning("Please input some text value before clicking")
return no_update
return input_text
@app.callback(
Output("output_region", "children", allow_duplicate=True),
State('text_input', 'value'),
Input("input_button2", "n_clicks"),
prevent_initial_call=True,
log=True,
)
def callback2(
input_text: str,
button_clicks: int,
dash_logger: DashLogger
):
if not input_text:
dash_logger.warning("Please input some text value before clicking")
return no_update
return input_text
# Run App
if __name__ == "__main__":
app.run(debug=True)
The app that I am running is a fairly large multi-page application. The outputs that triggered the error were not, in fact, duplicate outputs. Still, I added the allow_duplicate=True
argument but it has no effect.
The other thing that I found interesting about the callbacks that triggered the error is that they are on two of my sub-pages which are fairly deep into the application. I thought that the error would have been triggered by one of my earlier callbacks.
EDIT:
I "fixed" the issue by just removing the logging behaviour from the offending callbacks. For me, it was on two non-critical functions. To confirm, though, the duplicate callbacks were on the dash mantine components notifications, not any of my Output
objects. I used the default dmc notifications on the included DashLogger
. So, for some reason, the notification outputs on those two callback functions seemed to be creating duplicate IDs on the notification component...that is, I am assuming that how the LoggingTransform works is by adding additional Output objects to the function. Since, I do not have access to those Output objects, it seems that I am not able to add the allow_duplicate=True
on the Output objects that are actually causing the error.
Should be fixed in the 1.0.12
release. Please comment/re-open if you still see any issues.
The issue still appears to occur, I will try to develop another MRE to indicate
@emilhe, I might be mistaken but I think adding allow_duplicate=True
to Output
s in 1.0.12 didn’t help for reasons well described in this issue: plotly/dash#2486
In my particular situation, I have two callbacks that share the same Input
s but had different Output
s, which works fine. However, after adding log=True
to those callbacks, they now share the notification_provider
Output
with the same uid, which now does cause the “Duplicate callback outputs” issue.
I've been trying to make the log_id
unique inside setup_notifications_log_config()
and wasn't successful yet, but maybe that's a step in right direction?