Spaces:
Sleeping
Sleeping
File size: 6,193 Bytes
5a94297 0cd2128 f128fe5 5a94297 40fa5b9 d657219 0cd2128 f128fe5 40fa5b9 f128fe5 5a94297 f128fe5 40fa5b9 f128fe5 0cd2128 d657219 0cd2128 d657219 0cd2128 f128fe5 d657219 f128fe5 0cd2128 01b734e 0cd2128 01b734e 0cd2128 01b734e 6efe11e 01b734e f128fe5 01b734e f128fe5 01b734e f128fe5 01b734e f128fe5 079a08e |
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 |
import streamlit as st
# Do not load st-gsheets-connection
# from streamlit_gsheets import GSheetsConnection
import gspread
from oauth2client.service_account import ServiceAccountCredentials
import hmac
# Standard imports
import pandas as pd
# Custom and other imports
import project_config
# from utils import add_logo
from menu import menu
# Insert logo
# add_logo(project_config.MEDIA_DIR / 'gravity_logo.png')
# Initialize st.session_state.role to None
if "role" not in st.session_state:
st.session_state.role = None
# # Retrieve the role from Session State to initialize the widget
# st.session_state._role = st.session_state.role
# def set_role():
# # Callback function to save the role selection to Session State
# st.session_state.role = st.session_state._role
# From https://stackoverflow.com/questions/55961295/serviceaccountcredentials-from-json-keyfile-name-equivalent-for-remote-json
# See also https://www.slingacademy.com/article/pandas-how-to-read-and-update-google-sheet-files/
# See also https://docs.streamlit.io/develop/tutorials/databases/private-gsheet
# Note that the secrets cannot be passed in a group in HuggingFace Spaces,
# which is required for the native Streamlit implementation
def create_keyfile_dict():
variables_keys = {
# "spreadsheet": st.secrets['spreadsheet'], # spreadsheet
"type": st.secrets['type'], # type
"project_id": st.secrets['project_id'], # project_id
"private_key_id": st.secrets['private_key_id'], # private_key_id
# Have to replace \n with new lines (^l in Word) by hand
"private_key": st.secrets['private_key'], # private_key
"client_email": st.secrets['client_email'], # client_email
"client_id": st.secrets['client_id'], # client_id
"auth_uri": st.secrets['auth_uri'], # auth_uri
"token_uri": st.secrets['token_uri'], # token_uri
"auth_provider_x509_cert_url": st.secrets['auth_provider_x509_cert_url'], # auth_provider_x509_cert_url
"client_x509_cert_url": st.secrets['client_x509_cert_url'], # client_x509_cert_url
"universe_domain": st.secrets['universe_domain'] # universe_domain
}
return variables_keys
def check_password():
"""Returns `True` if the user had a correct password."""
def login_form():
"""Form with widgets to collect user information"""
# Header
col1, col2, col3 = st.columns(3)
with col2:
st.image(str(project_config.MEDIA_DIR / 'gravity_logo.svg'), width=300)
# col1, col2, col3 = st.columns(3)
# with col1:
# st.header("Log In")
with st.form("Credentials"):
st.text_input("Username", key="username")
st.text_input("Password", type="password", key="password")
st.form_submit_button("Log In", on_click=password_entered)
def password_entered():
"""Checks whether a password entered by the user is correct."""
# Define the scope
scope = [
'https://spreadsheets.google.com/feeds',
'https://www.googleapis.com/auth/drive'
]
# Add credentials to the account
creds = ServiceAccountCredentials.from_json_keyfile_dict(create_keyfile_dict(), scope)
# Authenticate and create the client
client = gspread.authorize(creds)
# Open the spreadsheet
sheet = client.open_by_url(st.secrets['spreadsheet']).worksheet("user_db")
data = sheet.get_all_records()
user_db = pd.DataFrame(data)
# # Create a connection object to Google Sheets
# conn = st.connection("gsheets", type=GSheetsConnection)
# # Read the user database
# user_db = conn.read()
# user_db.dropna(axis=0, how="all", inplace=True)
# user_db.dropna(axis=1, how="all", inplace=True)
# Check if the username is in the database
if st.session_state["username"] in user_db.username.values:
st.session_state["username_correct"] = True
# Check if the password is correct
if hmac.compare_digest(
st.session_state["password"],
user_db.loc[user_db.username == st.session_state["username"], "password"].values[0],
):
st.session_state["password_correct"] = True
# Check if the username is an admin
if st.session_state["username"] in user_db[user_db.role == "admin"].username.values:
st.session_state["role"] = "admin"
else:
st.session_state["role"] = "user"
# Retrieve and store user name and team
st.session_state["name"] = user_db.loc[user_db.username == st.session_state["username"], "name"].values[0]
st.session_state["team"] = user_db.loc[user_db.username == st.session_state["username"], "team"].values[0]
# st.session_state["profile_pic"] = user_db.loc[user_db.username == st.session_state["username"], "profile_pic"].values[0]
st.session_state["profile_pic"] = st.session_state["username"]
# Don't store the username or password
del st.session_state["password"]
# del st.session_state["username"]
else:
st.session_state["password_correct"] = False
else:
st.session_state["username_correct"] = False
st.session_state["password_correct"] = False
# Return True if the username + password is validated
if st.session_state.get("password_correct", False):
return True
# Show inputs for username + password
login_form()
if "password_correct" in st.session_state:
if not st.session_state["username_correct"]:
st.error("User not found.")
elif not st.session_state["password_correct"]:
st.error("The password you entered is incorrect.")
else:
st.error("An unexpected error occurred.")
return False
menu() # Render the dynamic menu!
if not check_password():
st.stop()
st.switch_page("pages/about.py") |