Must Make Filter Selection Twice in Multiselect when Setting Default Values with sesesion_state

Summary

When I assign the current selection in a multiselect object to a session_state variable that I feed back into the same multiselect object, it requires me to select a filter twice before it registers (although the first selection works without needing to select twice). A visual of the behavior is below.

Screen Recording 2023-07-10 at 3.44.08 PM

Steps to reproduce

Code snippet:

import streamlit as st
import pandas as pd

df = pd.DataFrame({'text' : ['text1', 'text2', 'text3']*5})

if 'fils' not in st.session_state:
    st.session_state.fils = None

if st.session_state.fils:
    default_value = st.session_state.fils
else:
    default_value = list(df['text'].unique())
user_cat_input1 = st.multiselect(
            f"Values for text",
            df['text'].unique(),
            default=default_value,
        )
st.session_state.fils = user_cat_input1
df2 = df[df['text'].isin(user_cat_input1)]

st.dataframe(df2)

Expected behavior:
Only need to click once for each filtered item and have the new set of filtered items populate the default of the multiselect.

Actual behavior:
Must click each filter selection twice.

Debug info

  • Streamlit version: 1.22
  • Python version: 3.9.13
  • PyEnv
  • OS version: 13.4.1
  • Browser version: Chrome and Firefox

Additional information

I am attempting the have the selections remembered and then put into the default selection because I want the user to interact with the filtered data on other pages and be able to return to the filter page and see the previously selected filters. A visual of this process is below.

I am open to better ways of achieving the same outcome of having the filters remembered when returning to the filter page.

Screen Recording 2023-07-10 at 4.20.19 PM

I found this post, which helped me solve this problem. I changed the app to be:

import streamlit as st
import pandas as pd

st.elements.utils._shown_default_value_warning=True

df = pd.DataFrame({'text' : ['text1', 'text2', 'text3']*3})
if 'key1' in st.session_state:
    st.session_state.key1 = st.session_state.key1

if 'fils' not in st.session_state:
    st.session_state.fils = list(df['text'].unique())

st.session_state.fils = st.multiselect(
            f"Values for text",
            df['text'].unique(),
            default=st.session_state.fils,
            key='key1'
        )

df2 = df[df['text'].isin(st.session_state.fils)]

st.dataframe(df2)

The st.elements.utils._shown_default_value_warning=True line is needed to prevent the warning that the solution to the problem caused. If there is a better way of achieving the same outcome of having the defaults dynamically set so that one can navigate to another page and return to the page where the data was filtered and see the latest filters that were applied before navigating away, I would be open to it.

1 Like

This topic was automatically closed 2 days after the last reply. New replies are no longer allowed.