Streamlit session_state doesn't work across sessions

My UI has two simple buttons button1 and button2, button1 has a while loop based on a session variable. But when I click button2 (which changes the value of this session variable) the while loop of button1 fails with key error which shouldn’t be the case.
Streamlit version 1.22.0

import streamlit as st

button1 = st.button(“start”)
button2 = st.button(“stop”)
if button2:
    st.session_state[‘run’] = False
if button1:
    counter = 0
    st.session_state[‘run’] = True
    while st.session_state[‘run’]:
        st.write(counter)
        counter += 1

Expected behavior :
Pressing button2 should stop the while loop of button1

Actual behavior: :
On pressing the button2, the while loop of button1 fails with
raise KeyError(key)
KeyError: ‘run’

Can you reformat your post so we can see the correct indentation? Also, can you specify which version of Streamlit you are using?

I have somewhat isolated the issue.
I’m printing st.session_state at the start of code and again at the end of code.

When the application initializes -
/some run_once code runs and puts objects in st.session_state/
start of code - {}
end of code = {run_once = False, cortex object - cortex object as 23X765XCX5768889}

When I press button1 -
/the while loop will be running so we won’t get end of code st.session_state just now/
start of code = {run_once = False, cortex object - cortex object as 23X765XCX5768889}

When I press button2 -
end of code = {} - this is the issue, it becomes empty for some reason.
start of code - {run_once = False, cortex object - cortex object as 23X765XCX5768889}
end of code - {run_once = False, rec = False, cortex object - cortex object as 23X765XCX5768889}

Between executions the session_state seems to loose it’s value which is a bug I think

Can you try running on Streamlit 1.19 or changing fastRerun in your config file per this issue:

I still have the same error with Streamlit 1.19 (I have python 3.10 which I can’t change due to other requirements).
Also tried changing the runner.fastReruns to False but it didn’t help.
Any help/workarounds would be greatly appreciated.

There is another possibly related issue here: Infinite loop after breaking · Issue #6494 · streamlit/streamlit · GitHub

For me, if I use Streamlit 1.19 and add a time.sleep(1) into the while loop to slow it down, it works fine.

import streamlit as st
import time

button1 = st.button('start')
button2 = st.button('stop')
if button2:
    st.session_state['run'] = False
if button1:
    counter = 0
    st.session_state['run'] = True
    while st.session_state['run']:
        st.write(counter)
        counter += 1
        time.sleep(1)

Also, I’d like to point out that the st.session_state['run'] value isn’t really doing anything as is. You can dispense with it entirely and simply put

if button1:
    counter = 0
    while True:
        st.write(counter)
        counter += 1
        time.sleep(1)

Your while loop is never going to get interrupted directly from a change in session state like that; just clicking a button (either button) is going to stop your loop and rerun the whole page (aside from the bugs mentioned).

Ah, got it. It’s finally working. In Streamlit 1.19 it doesn’t work if I put print() inside the while loop. Instead using st.write() does the trick.
And thank you for that clarity on while loop situation. I tried using while(True) and it’s working. Appreciate the quick resolution.

Yeah, I have that documented in the second GitHub issue that Streamlit seems to need some kind of call to itself within a loop for it to break correctly. Feel free to comment or vote on those issues so the devs know you have come across them as well. :slight_smile:

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