Skip to content

[BUG] Callback executes but return value has no effect #1075

Closed

Description

@zupalex

Describe your context
dash 1.7.0
dash-core-components 1.6.0
dash-html-components 1.0.2
dash-renderer 1.2.2
dash-table 4.5.1

Tried on Google Chrome and Firefox

Describe the bug

Hi, I have an issue with a callback. It executes just fine (I can see print outs from it) but the return value has no effect.

Basically I hooked a Div with a custom class (a spinner) to a button. The div is at the beginning hidden. When the button is pressed, the callback changed the style of that div to remove "visibility" attribute. That button also trigger some operations happening on the server side, and when this operation is finished, it fills a Dash table and notify a hidden Div that the operation is finished. That hidden Div is also connected to my spinner to changed the style back to add the 'visibility': "hidden" back.
The code looks like this:

@app.callback(
    [
        dash.dependencies.Output('process-button-trigger-sync', 'n_clicks'),
        dash.dependencies.Output('process-button-trigger-fetch-messages', 'n_clicks')
    ],
    [
        dash.dependencies.Input('process-button', 'n_clicks')
    ]
)
def trigger_process_button_actions(n_clicks):
    print_log(request,f"process-button has been triggered: {n_clicks}")
    if n_clicks:
        return [ 1, 1 ]
    else:
        raise PreventUpdate()

@app.callback(
    dash.dependencies.Output('process-status-icon-div', 'style'),
    [
        dash.dependencies.Input('process-button-trigger-sync', 'n_clicks'),
        dash.dependencies.Input('finished-fetching-messages', 'n_clicks'),
    ],
    [
        dash.dependencies.State('process-status-icon-div', 'style')
    ]
)
def show_loading_state(started, finished, current_style):
    print_log(request,f"Checking loading state div visibility:")
	
    ctx = dash.callback_context

    print_log(request,f"Style: {current_style}")

    if ctx.triggered:
        for evt in ctx.triggered:
            comp = evt['prop_id'].split('.')[0]
            if comp == "process-button-trigger-sync":
                if started:
                    print_log(request,"should show loading state")
                    return loading_state_div_style
                else:
                    raise PreventUpdate()
            else:
                print_log(request,"should hide loading state")
                return {**loading_state_div_style, **{'visibility': "hidden"}}

@app.callback(
    [
        dash.dependencies.Output('msg-table', 'children'),
        dash.dependencies.Output('finished-fetching-messages', 'n_clicks')
    ],
    [
        dash.dependencies.Input("process-button-trigger-fetch-messages", "n_clicks")
    ]
)
def get_messages(n_clicks):
    [... do stuffs ...]

    return [ [table_content], 1 ]

It works the first time I click on the button , but any subsequent click generate the proper table content for and triggers the callback (I can see it in the logs), but the
does't get its style changed.

The logs shows:

2020-01-09 17:50:05.174789] [10.50.46.15] process-button has been triggered: 1
[2020-01-09 17:50:05.212320] [10.50.46.15] Checking loading state div visibility:
[2020-01-09 17:50:05.212419] [10.50.46.15] Style: {'display': 'inline-block', 'padding': '0% 6% 0% 1%', 'vertical-align': 'middle', 'visibility': 'hidden'}
[2020-01-09 17:50:05.212520] [10.50.46.15] should show loading state
[2020-01-09 17:50:05.349895] [10.50.46.15] Getting messages...
[2020-01-09 17:50:06.155847] [10.50.46.15] Checking loading state div visibility:
[2020-01-09 17:50:06.155985] [10.50.46.15] Style: {'display': 'inline-block', 'padding': '0% 6% 0% 1%', 'vertical-align': 'middle'}
[2020-01-09 17:50:06.156095] [10.50.46.15] should hide loading state
[2020-01-09 17:50:23.486135] [10.50.46.15] process-button has been triggered: 2
[2020-01-09 17:50:23.533177] [10.50.46.15] Checking loading state div visibility:
[2020-01-09 17:50:23.533278] [10.50.46.15] Style: {'display': 'inline-block', 'padding': '0% 6% 0% 1%', 'vertical-align': 'middle', 'visibility': 'hidden'}
[2020-01-09 17:50:23.533379] [10.50.46.15] should show loading state
[2020-01-09 17:50:23.664761] [10.50.46.15] Getting messages...
[2020-01-09 17:50:24.436566] [10.50.46.15] Checking loading state div visibility:
[2020-01-09 17:50:24.436679] [10.50.46.15] Style: {'display': 'inline-block', 'padding': '0% 6% 0% 1%', 'vertical-align': 'middle', 'visibility': 'hidden'}
[2020-01-09 17:50:24.436779] [10.50.46.15] should hide loading state

As you can see (hopefully), The first time the button is pressed, the current style of the Div has the "hidden" attribute. When the operation is over ("Getting messages" message), the callback is triggered again, and the current style doesn't have the hidden attribute (which is expected).

The second time around, the callback is triggered properly again, but the spinner never showed. Indeed, one can see that after the operation completes, and the current style of the div is printed, it has the "hidden" attribute while it should have been removed previously.

Expected behavior

When the callback is triggered and executed, the return value should have an effect.

I hope this is clear enough. This is taken from a big piece of code so hopefully I managed to make it readable.

Activity

  1. zupalex commented on Jan 9, 2020

    @zupalex
    Author

    Using what I posted here as a minimal example, I can get it to work properly by removing the intermediate Div and and . Instead, if I use the directly as an input for both callbacks, and use children as an input for the second callback instead of , it updates just fine.

    However I would expect this to work, especially since the callback fires properly, just that the return value is not registered.

    The reason why I split it like that at the first place is that in the full code, I was using as an input for multiple callbacks (5 total), and some would not fire at all or fire randomly when the button was pressed. Using it as an input for only one callback and using several Div to propagate the callback made the appropriate callbacks fire, but then the return values are "ignored" as described in the first post.

  2. mjclawar commented on Feb 15, 2020

    @mjclawar
    Contributor

    Running into (I think) a similar issue with callbacks being ignored with Dash releases post 1.6.1. The callback does execute (and I can even see it correct in the network requests in the console), but does not have the intended effect on the layout.

    Does your example work when you use dash==1.6.1 and break when you use dash==1.7.0?

  3. mjclawar commented on Feb 15, 2020

    @mjclawar
    Contributor

    It may have something to do with this change (I would assume it's in the dash-renderer JS since it's making it to the client correctly):

    v1.6.1...v1.7.0#diff-15692ba768eeab56e95aa409ab7c19b7R370-R392

    /**
    * Determine the id of all components used as input or state in the callbacks
    * triggered by the props change.
    *
    * Wait for all components associated to these ids to be ready before initiating
    * the callbacks.
    */
    const deps = queuedObservers.map(output =>
      dependenciesRequest.content.find(
        dependency => dependency.output === output
      )
    );
    
    const ids = uniq(
      flatten(
        deps.map(dep => [
          dep.inputs.map(input => input.id),
          dep.state.map(state => state.id),
        ])
      )
    );
    
    await isAppReady(layout, paths, ids);

    Also potentially related to #1071 and #1053

  4. alexcjohnson commented on Mar 6, 2020

    @alexcjohnson
    Collaborator

    I suspect this will be fixed by #1103 (which includes tests for #1053 and #1071) but it's hard to tell for sure without a complete reproduction case. If one of you would be able to post a full app showing the bug I'd be happy to try it and include a test for it - or, you can try the 475-wildcards branch on your own, but beware if you pull that branch down you need to rebuild the renderer bundle before running the app.

  5. matsujju commented on Jan 12, 2021

    @matsujju

    Hey @alexcjohnson
    I am having similar issue but my Output is single. The result of callback is printing in console but not showing in Dashboard. I have also posted in community channel. You can look here.
    Here is the code of mine:

    import dash
    import dash_core_components as dcc
    import dash_html_components as html
    import dash_bootstrap_components as dbc
    from dash.dependencies import Input, Output, State
    from dash.exceptions import PreventUpdate
    import pandas as pd
    import numpy as np
    import joblib
    import re
    import nltk
    from bs4 import BeautifulSoup
    import unicodedata
    import spacy
    
    nlp = spacy.load("en_core_web_sm")
    
    from nltk.tokenize import word_tokenize
    from nltk.tokenize.toktok import ToktokTokenizer
    
    tokenizer = ToktokTokenizer()
    stopword_list = nltk.corpus.stopwords.words("english")
    
    import pickle
    from sklearn.feature_extraction.text import TfidfVectorizer
    
    ################################################################################
    def data_clean(text):
        text = text.lower()  # lowering of characters
        text = text.strip()  # removeing extra spaces before and after the sentence
        # text = TextBlob(text).correct() # spelling mistakes correction  (very slow) (maybe try directly on dataframe column)
        return text
    
    
    # remove accented characters (Sómě Áccěntěd těxt)
    def remove_accented_chars(text):
        text = (
            unicodedata.normalize("NFKD", text)
            .encode("ascii", "ignore")
            .decode("utf-8", "ignore")
        )
        return text
    
    
    def strip_html_tags(text):  # function for removing html tags
        soup = BeautifulSoup(text, "html.parser")
        stripped_text = soup.get_text()
        return stripped_text
    
    
    def remove_special_characters(
        text, remove_digits=False
    ):  # function for removing punctuations , before using this remove any contractions(like "I'll" --> "I will") in text data
        pattern = r"[^a-zA-z0-9\s\-\+\#]" if not remove_digits else r"[^a-zA-z\s\-\+\#]"
        text = re.sub(pattern, "", text)
        return text
    
    
    def remove_links_emojis(text):
        pattern = re.compile(
            r"http[s]?://(?:[a-zA-Z]|[0-9]|[$-_@.&+]|[!*\(\),]|(?:%[0-9a-fA-F][0-9a-fA-F]))+"
        )  # removing https:www.examples.com
        text = pattern.sub("", text)
    
        emoji = re.compile(
            "["
            "\U0001F600-\U0001FFFF"  # emoticons
            "\U0001F300-\U0001F5FF"  # symbols & pictographs
            "\U0001F680-\U0001F6FF"  # transport & map symbols
            "\U0001F1E0-\U0001F1FF"  # flags (iOS)
            "\U00002702-\U000027B0"
            "\U000024C2-\U0001F251"
            "]+",
            flags=re.UNICODE,
        )
        text = emoji.sub(r"", text)
        return text
    
    
    def contractions(text):  # contraction of text i.e remove_apostrophes
        text = re.sub("ain't", "is not", str(text))
        text = re.sub("aren't", "are not", str(text))
        text = re.sub("can't", "cannot", str(text))
        text = re.sub("can't've", "cannot have", str(text))
        text = re.sub("'cause", "because", str(text))
        text = re.sub("could've", "could have", str(text))
        text = re.sub("couldn't", "could not", str(text))
        text = re.sub("couldn't've", "could not have", str(text))
        text = re.sub("didn't", "did not", str(text))
        text = re.sub("doesn't", "does not", str(text))
        text = re.sub("don't", "do not", str(text))
        text = re.sub("hadn't", "had not", str(text))
        text = re.sub("hadn't've", "had not have", str(text))
        text = re.sub("hasn't", "has not", str(text))
        text = re.sub("haven't", "have not", str(text))
        text = re.sub("he'd", "he would", str(text))
        text = re.sub("he'd've", "he would have", str(text))
        text = re.sub("he'll", "he will", str(text))
        text = re.sub("he'll've", "he he will have", str(text))
        text = re.sub("he's", "he is", str(text))
        text = re.sub("how'd", "how did", str(text))
        text = re.sub("how'd'y", "how do you", str(text))
        text = re.sub("how'll", "how will", str(text))
        text = re.sub("how's", "how is", str(text))
        text = re.sub("I'd", "I would", str(text))
        text = re.sub("I'd've", "I would have", str(text))
        text = re.sub("I'll", "I will", str(text))
        text = re.sub("I'll've", "I will have", str(text))
        text = re.sub("I'm", "I am", str(text))
        text = re.sub("I've", "I have", str(text))
        text = re.sub("i'd", "i would", str(text))
        text = re.sub("i'd've", "i would have", str(text))
        text = re.sub("i'll", "i will", str(text))
        text = re.sub("i'll've", "i will have", str(text))
        text = re.sub("i'm", "i am", str(text))
        text = re.sub("i've", "i have", str(text))
        text = re.sub("isn't", "is not", str(text))
        text = re.sub("it'd", "it would", str(text))
        text = re.sub("it'd've", "it would have", str(text))
        text = re.sub("it'll", "it will", str(text))
        text = re.sub("it'll've", "it will have", str(text))
        text = re.sub("it's", "it is", str(text))
        text = re.sub("let's", "let us", str(text))
        text = re.sub("ma'am", "madam", str(text))
        text = re.sub("mayn't", "may not", str(text))
        text = re.sub("might've", "might have", str(text))
        text = re.sub("mightn't", "might not", str(text))
        text = re.sub("mightn't've", "might not have", str(text))
        text = re.sub("must've", "must have", str(text))
        text = re.sub("mustn't", "must not", str(text))
        text = re.sub("mustn't've", "must not have", str(text))
        text = re.sub("needn't", "need not", str(text))
        text = re.sub("needn't've", "need not have", str(text))
        text = re.sub("o'clock", "of the clock", str(text))
        text = re.sub("oughtn't", "ought not", str(text))
        text = re.sub("oughtn't've", "ought not have", str(text))
        text = re.sub("shan't", "shall not", str(text))
        text = re.sub("sha'n't", "shall not", str(text))
        text = re.sub("shan't've", "shall not have", str(text))
        text = re.sub("she'd", "she would", str(text))
        text = re.sub("she'd've", "she would have", str(text))
        text = re.sub("she'll", "she will", str(text))
        text = re.sub("she'll've", "she will have", str(text))
        text = re.sub("she's", "she is", str(text))
        text = re.sub("should've", "should have", str(text))
        text = re.sub("shouldn't", "should not", str(text))
        text = re.sub("shouldn't've", "should not have", str(text))
        text = re.sub("so've", "so have", str(text))
        text = re.sub("so's", "so as", str(text))
        text = re.sub("that'd", "that would", str(text))
        text = re.sub("that'd've", "that would have", str(text))
        text = re.sub("that's", "that is", str(text))
        text = re.sub("there'd", "there would", str(text))
        text = re.sub("there'd've", "there would have", str(text))
        text = re.sub("there's", "there is", str(text))
        text = re.sub("they'd", "they would", str(text))
        text = re.sub("they'd've", "they would have", str(text))
        text = re.sub("they'll", "they will", str(text))
        text = re.sub("they'll've", "they will have", str(text))
        text = re.sub("they're", "they are", str(text))
        text = re.sub("they've", "they have", str(text))
        text = re.sub("to've", "to have", str(text))
        text = re.sub("wasn't", "was not", str(text))
        text = re.sub("we'd", "we would", str(text))
        text = re.sub("we'd've", "we would have", str(text))
        text = re.sub("we'll", "we will", str(text))
        text = re.sub("we'll've", "we will have", str(text))
        text = re.sub("we're", "we are", str(text))
        text = re.sub("we've", "we have", str(text))
        text = re.sub("weren't", "were not", str(text))
        text = re.sub("what'll", "what will", str(text))
        text = re.sub("what'll've", "what will have", str(text))
        text = re.sub("what're", "what are", str(text))
        text = re.sub("what's", "what is", str(text))
        text = re.sub("what've", "what have", str(text))
        text = re.sub("when's", "when is", str(text))
        text = re.sub("when've", "when have", str(text))
        text = re.sub("where'd", "where did", str(text))
        text = re.sub("where's", "where is", str(text))
        text = re.sub("where've", "where have", str(text))
        text = re.sub("who'll", "who will", str(text))
        text = re.sub("who'll've", "who will have", str(text))
        text = re.sub("who's", "who is", str(text))
        text = re.sub("who've", "who have", str(text))
        text = re.sub("why's", "why is", str(text))
        text = re.sub("why've", "why have", str(text))
        text = re.sub("will've", "will have", str(text))
        text = re.sub("won't", "will not", str(text))
        text = re.sub("won't've", "will not have", str(text))
        text = re.sub("would've", "would have", str(text))
        text = re.sub("wouldn't", "would not", str(text))
        text = re.sub("wouldn't've", "would not have", str(text))
        text = re.sub("y'all", "you all", str(text))
        text = re.sub("y'all'd", "you all would", str(text))
        text = re.sub("y'all'd've", "you all would have", str(text))
        text = re.sub("y'all're", "you all are", str(text))
        text = re.sub("y'all've", "you all have", str(text))
        text = re.sub("you'd", "you would", str(text))
        text = re.sub("you'd've", "you would have", str(text))
        text = re.sub("you'll", "you will", str(text))
        text = re.sub("you'll've", "you will have", str(text))
        text = re.sub("you're", "you are", str(text))
        text = re.sub("you've", "you have", str(text))
        return text
    
    
    def lemmatize_text(text):  # function for lemmetization of text
        text = nlp(text)
        text = str(
            " ".join(
                [word.lemma_ if word.lemma_ != "-PRON-" else word.text for word in text]
            )
        )
        return text
    
    
    def remove_stopwords(text):
        tokens = tokenizer.tokenize(text)
        tokens = [token.strip() for token in tokens]
    
        filtered_tokens = [token for token in tokens if token.lower() not in stopword_list]
        filtered_text = " ".join(filtered_tokens)
        return filtered_text
    
    
    def preprocess(
        text,
        clean_data=True,
        contraction_expansion=True,
        accented_char_removal=True,
        text_lemmatization=False,
        link_emoji=True,
        strip_html_tag=True,
        special_characters=True,
        remove_digits=False,
        stop_words=False,
    ):
    
        # cleaned data (lower & strip whitespaces & spelling mistake)
        if clean_data:
            text = data_clean(text)
        # strip html
        if strip_html_tag:
            text = strip_html_tags(text)
        # accented char removal
        if accented_char_removal:
            text = remove_accented_chars(text)
    
        # exapand contraction
        if contraction_expansion:
            text = contractions(text)
        if stop_words:
            text = remove_stopwords(text)
        # lemmetization
        if text_lemmatization:
            text = lemmatize_text(text)
        # punctuations and digits
        if special_characters:
            text = remove_special_characters(text, remove_digits=remove_digits)
    
        # remove extra whitespace
        text = re.sub(" +", " ", text)
    
        return text
    
    
    classifier = joblib.load("logreg_multi_label.joblib")
    multilabel = joblib.load("multilabel_binarizer.pkl")
    
    tfidf_vocab = pickle.load(open("tfidf_file_0.8.pkl", "rb"))
    tfidf = TfidfVectorizer(
        max_features=50000,
        ngram_range=(1, 3),
        stop_words="english",
        vocabulary=tfidf_vocab.vocabulary_,
    )
    
    
    def get_tags(predicted_list, threshold, labels):
        mlb = [(i1, c1) for i1, c1 in enumerate(multilabel.classes_)]
        temp_list = sorted(
            [(i, c) for i, c in enumerate(list(predicted_list))],
            key=lambda x: x[1],
            reverse=True,
        )
        tag_list = [item1 for item1 in temp_list if item1[1] >= threshold]
        tags = [
            item[1] for item2 in tag_list[:labels] for item in mlb if item2[0] == item[0]
        ]
        return tags
    
    
    app = dash.Dash(
        __name__, title="Multi Tag Prediction", external_stylesheets=[dbc.themes.BOOTSTRAP]
    )
    server = app.server
    app.layout = html.Div(
        [
            html.H2(
                ["Multi Tag Prediction"],
                style={
                    "text-align": "left",
                    "margin-left": "4.5%",
                    "margin-right": "2%",
                    "margin-bottom": "2%",
                },
            ),
            dbc.Row(
                [
                    dbc.Col(
                        html.Div(
                            [
                                dbc.FormGroup(
                                    [
                                        dbc.Label(
                                            "Filter by Preprocessing Functions to Apply:"
                                        ),
                                        dbc.RadioItems(
                                            options=[
                                                {"label": "All", "value": "all"},
                                                {"label": "Customized", "value": "custom"},
                                            ],
                                            value="all",
                                            id="radio-button",
                                            inline=True,
                                            style={"padding": "10px"},
                                        ),
                                    ]
                                ),
                                html.Div(
                                    [
                                        dcc.Dropdown(
                                            id="drop-down",
                                            options=[
                                                {
                                                    "label": "remove_digits",
                                                    "value": "remove_digits",
                                                },
                                                {
                                                    "label": "remove_stopwords",
                                                    "value": "stop_words",
                                                },
                                                {
                                                    "label": "text_lemmatization",
                                                    "value": "text_lemmatization",
                                                },
                                            ],
                                            value=[
                                                "remove_digits",
                                                "remove_stopwords",
                                                "text_lemmatization",
                                            ],
                                            multi=True,
                                            placeholder="Select the preprocessing functions",
                                            searchable=True,
                                        )
                                    ],
                                    style={"padding": "5px", "margin-bottom": "10px",},
                                ),
                                html.Div(
                                    [
                                        html.H6(
                                            "Filter by threshold (probabilty of labels to include):"
                                        ),
                                        dcc.Slider(
                                            id="slider",
                                            min=0.1,
                                            max=0.9,
                                            step=0.1,
                                            value=0.5,
                                            marks={
                                                0.1: "0.1",
                                                0.2: "0.2",
                                                0.3: "0.3",
                                                0.4: "0.4",
                                                0.5: "0.5",
                                                0.6: "0.6",
                                                0.7: "0.7",
                                                0.8: "0.8",
                                                0.9: "0.9",
                                            },
                                            tooltip={"placement": "top"},
                                            included=False,
                                        ),
                                    ],
                                    style={"margin-bottom": "10px"},
                                ),
                                html.Div(
                                    [
                                        html.H6(
                                            "Filter by label count (how many labels to include if there are more):"
                                        ),
                                        dcc.Slider(
                                            id="slider-2",
                                            min=5,
                                            max=10,
                                            step=1,
                                            value=5,
                                            marks={
                                                5: "5",
                                                6: "6",
                                                7: "7",
                                                8: "8",
                                                9: "9",
                                                10: "10",
                                            },
                                            tooltip={"placement": "top"},
                                            included=False,
                                        ),
                                    ],
                                    style={"margin-top": "10px"},
                                ),
                            ],
                            style={
                                "width": "100%",
                                "box-shadow": "5px 5px 5px  #cacfd2",
                                "padding": "35px",
                                "background-color": "#f9f9f9",
                            },
                        ),
                        width={"size": 4, "order": "first", "offset": 0},
                    ),
                    dbc.Col(
                        html.Div(
                            [
                                dbc.Textarea(
                                    id="input_text",
                                    value="",
                                    style={
                                        "height": 300,
                                        "width": "100%",
                                        "box-shadow": "5px 5px 5px  #cacfd2",
                                        # "margin-left": "-20px",
                                        "background-color": "#f9f9f9",
                                    },
                                    maxLength=10000,
                                    placeholder="Type the text or copy-paste from somewhere else",
                                ),
                                dbc.Button(
                                    "Submit",
                                    id="submit-button",
                                    n_clicks=0,
                                    style={"margin-left": "532px", "margin-top": "15px",},
                                    outline=True,
                                    color="primary",
                                ),
                                html.Div(
                                    [
                                        dbc.Spinner(
                                            [
                                                dbc.Toast(
                                                    id="output-state",
                                                    header="Predicted Labels:",
                                                    icon="info",
                                                    is_open=True,
                                                    duration=1000000,
                                                    dismissable=False,
                                                    style={
                                                        "position": "fixed",
                                                        "height": "15%",
                                                        "width": "400%",
                                                        "margin-top": "20px",
                                                    },
                                                    children=[],
                                                )
                                            ],
                                            type="grow",
                                            color="info",
                                            fullscreen=False,
                                        ),
                                    ]
                                ),
                            ]
                        ),
                        width={"size": 6, "order": "second"},
                        # align="end",
                    ),
                ],
                justify="around",
            ),
        ],
    
    )
    
    
    @app.callback(Output("drop-down", "value"), [Input("radio-button", "value")])
    def display_status(selector):
        if selector == "all":
            return ["remove_digits", "text_lemmatization", "remove_stopwords"]
        else:
            return []
    
    
    @app.callback(
        Output("output-state", "is_open"),
        [Input("submit-button", "n_clicks")],
        [
            State("input_text", "value"),
            State("slider", "value"),
            State("drop-down", "value"),
            State("slider-2", "value"),
        ],
        prevent_initial_call=True,
    )
    def label_prediction(num_clicks, text, threshold_value, preprocess_func, label_value):
        if text is None or num_clicks is None:
            raise PreventUpdate
        else:
    
            params = ["remove_digits", "remove_stopwords", "text_lemmatization"]
            dict_params = [param in preprocess_func for param in params]
            preprocess_text = preprocess(text, *dict_params)
            transformed_text = tfidf.fit_transform([preprocess_text])
            prediction = classifier.predict_proba(transformed_text)
            # print("This is the result to show")
            result = get_tags(prediction[0], threshold_value, label_value)
            print(str(result))
            return result
    
    
    if __name__ == "__main__":
        app.run_server(debug=True)
    
    
  6. alexcjohnson commented on Jan 12, 2021

    @alexcjohnson
    Collaborator

    I continued the discussion with @matsujju on the community post. The rest of this most likely was handled by #1103 but if there's anything else along these lines please open a new issue.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Type

    No type

    Projects

    No projects

      Milestone

      No milestone

      Relationships

      None yet

      Development

      No branches or pull requests

      Issue actions