Source code for streamlitextras.cookiemanager

import os
import time
import streamlit as st
import streamlit.components.v1 as components
from streamlitextras.logger import log
from streamlitextras.utils import repr_

absolute_path = os.path.dirname(os.path.abspath(__file__))
build_path = os.path.join(absolute_path, "frontend/build")
_component_func = components.declare_component("cookie_manager", path=build_path)


[docs]class CookieManager: """ This is a streamlit component class to manage cookies. It uses a thin component instance wrapper around the universal-cookie library. """ def __init__(self, debug: bool = False): if "cookie_manager" in st.session_state and st.session_state["cookie_manager"]: self.cookies = st.session_state["cookie_manager"].cookies.copy() else: self.cookies = {} st.session_state["cookie_manager"] = self self.debug = debug if self.debug: log.debug(f"Initialized Cookie Manager {hex(id(self))}")
[docs] def delayed_init(self): """ Used to delay initialization of streamlit objects so this class can be cached """ st.session_state["cookie_manager"] = self
[docs] def cookie_manager(self, *args, **kwargs): time.sleep(0.1) try: result = _component_func(**kwargs) except st.errors.DuplicateWidgetID: kwargs["key"] = f"""{kwargs["key"]}{time.time()}""" result = _component_func(**kwargs) time.sleep(0.1) # This ensures we get a result before streamlit redraws return result
[docs] def set( self, name, value, expires_at=None, secure=None, path=None, same_site=None, key="set", ): """ Set a cookie with name, value and options. Defaults are set in the JS component and listed below :param name: The name of the cookie :param value: The value of the cookie :param expires_at: Datetime of when the cookie expires. Default is set in the js at 1 day from browser timezone. :param secure: Secure flag, default is true. :param path: Cookie path, default is / :param same_site: Same site attribute, default is "strict" :param key: streamlit key used for the component instance :returns: True if the operation was successful, else False """ if name is None or name == "": return False expires_at = expires_at.isoformat() if expires_at else None options = { "name": name, "value": value, "expires": expires_at, "sameSite": same_site, } result = self.cookie_manager( method="set", options=options, key=key, default=False ) if result: self.cookies[name] = result return True
[docs] def get(self, name, key="get"): """ Gets a value of a cookie. NOTE: The value isn't got directly from the component instance This class fills all cookies in self.cookies everytime streamlit instances it on the page Returns empty {} dict if no result. Returns None if the operation failed. :param name: The name of the cookie to get the value of :returns Union[str, dict]: Returns the cookie value, it may be deserialized from JSON to a dict """ if not self.cookies: self.cookies = self.cookie_manager(method="getAll", key=key, default={}) if name is None or name == "": return None result = self.cookies.get(name, None) time.sleep(0.4) # Give component time to render return result
[docs] def get_all(self, key="get_all"): """ Get a dict of all the cookies in the browser, and update self.cookies :param key: streamlit key used for the component instance :returns: A dict of all the cookies """ self.cookies = self.cookie_manager(method="getAll", key=key, default={}) return self.cookies
[docs] def delete(self, name, key="delete"): """ Delete a cookie from the browser :param name: the name of the cookie to delete :param key: streamlit key used for the component instance :returns: True if the operation was successful, or else False """ if name is None or name == "": return False result = self.cookie_manager( method="delete", options={"name": name}, key=key, default=False ) if result and name in self.cookies: del self.cookies[name] return result
def __repr__(self) -> str: return repr_(self)
# @st.cache(allow_output_mutation=True, show_spinner=False)