-
Notifications
You must be signed in to change notification settings - Fork 0
/
Copy pathuser_settings.py
231 lines (192 loc) · 8.88 KB
/
user_settings.py
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
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
import time
import datetime as dt
import streamlit as st
import gspread
from google.oauth2.service_account import Credentials
from werkzeug.security import generate_password_hash, check_password_hash
from streamlit_cookies_controller import CookieController
import json
cookie_controller = CookieController()
if "auth_status" in cookie_controller.getAll():
for k, v in cookie_controller.get("auth_status").items():
st.session_state[k] = v
scope = ["https://spreadsheets.google.com/feeds", "https://www.googleapis.com/auth/drive"]
creds = Credentials.from_service_account_info(st.secrets["gcp_service_account"], scopes=scope)
client = gspread.authorize(creds)
sheet = client.open_by_url(st.secrets["connections"]["gsheets"]["spreadsheet"]).sheet1
# Utility functions
def get_user_data(username):
"""Fetch user data from Google Sheets by username."""
users = sheet.get_all_records()
for user in users:
if user['username'] == username:
return user
return None
def register_user(username, email, name, password):
"""Register a new user in Google Sheets."""
if get_user_data(username):
st.warning("User already exists.")
else:
password_hash = generate_password_hash(password)
new_user_data = {
"username": username,
"email": email,
"name": name,
"password_hash": password_hash,
"settings": json.dumps(
{"game_tag_id": "", "is_discounted_index": 0, "selected_days_g": None,
"scheduled_time_g": "12:00", "user_id": "", "game_tag": "",
"selected_days_w": None, "scheduled_time_w": "12:00"}),
}
sheet.append_row(list(new_user_data.values()))
def apply_settings(username):
try:
# Loading data from Google Sheet
users = sheet.get_all_records()
# Looking for user by name
for i, user in enumerate(users, start=2): # Start with second row for data
if user["username"] == username:
user_settings = json.loads(user["settings"])
# Updating values in `st.session_state`
for key, value in user_settings.items():
# Time processing
if key in ("scheduled_time_g", "scheduled_time_w"):
st.session_state[key] = dt.datetime.strptime(value,
"%H:%M:%S").time() # dt.datetime.fromisoformat(value).time()
else:
st.session_state[key] = value
st.success("User settings applied successfully!")
except:
st.error("Can't apply user settings.")
def save_user_settings(username):
# DEFAULT = {"game_tag_id": "", "is_discounted_index": 0, "selected_days_g": None, "scheduled_time_g": "12:00",
# "user_id": "", "game_tag": "", "selected_days_w": None, "scheduled_time_w": "12:00"}
DEFAULT = {"game_tag_id": "", "is_discounted_index": 0, "user_id": "", "game_tag": "",}
settings_voc = {}
def custom_encoder(obj):
if isinstance(obj, (dt.datetime, dt.time)):
return obj.isoformat() # Преобразуем время в строку
raise TypeError(f"Type {type(obj)} is not JSON!!! serializable")
# Преобразуем st.session_state в JSON-строку
for key in DEFAULT.keys():
settings_voc[key] = st.session_state[key]
st_state_json = json.dumps(settings_voc, default=custom_encoder, indent=2)
try:
# Loading data from Google Sheet
users = sheet.get_all_records()
# Looking for user by name
for i, user in enumerate(users, start=2): # Start with second row for data
if user["username"] == username:
# Updating cell with user settings
sheet.update_cell(i, sheet.find("settings").col, st_state_json)
st.success("User settings saved successfully!")
except:
st.error("Can't save user settings.")
def load_user_settings(username):
try:
# Loading data from Google Sheet
users = sheet.get_all_records()
# Looking for user by name
for i, user in enumerate(users, start=2): # Start with second row for data
if user["username"] == username:
return json.loads(user["settings"])
except:
st.error("Can't load user settings.")
# Functions for import
# Func to save any user value except options
def save_user_cred(username, settings, settings_type):
"""Save user settings in Google Sheets."""
users = sheet.get_all_records()
for i, user in enumerate(users, start=2):
if user["username"] == username:
sheet.update_cell(i, sheet.find(settings_type).col, str(settings))
break
if "is_authenticated" not in st.session_state:
st.session_state["is_authenticated"] = False
if "game_tag_id" not in st.session_state:
st.session_state.game_tag_id = ""
if "is_discounted" not in st.session_state:
st.session_state.is_discounted = "yes"
if "is_discounted_index" not in st.session_state:
st.session_state.is_discounted_index = 0
if "selected_days_cron_g" not in st.session_state:
st.session_state.selected_days_cron_g = []
if "selected_days_g" not in st.session_state:
st.session_state.selected_days_g = []
if "scheduled_time_g" not in st.session_state:
st.session_state.scheduled_time_g = dt.time(12, 0)
if "user_id" not in st.session_state:
st.session_state.user_id = ""
if "game_tag" not in st.session_state:
st.session_state.game_tag = ""
if "selected_days_cron_g" not in st.session_state:
st.session_state.selected_days_cron_g = []
if "selected_days_w" not in st.session_state:
st.session_state.selected_days_w = []
if "scheduled_time_w" not in st.session_state:
st.session_state.scheduled_time_w = dt.time(12, 0)
# Initialize session state
if 'running' not in st.session_state:
st.session_state.running = False
# Streamlit UI
if st.session_state["is_authenticated"]:
st.write(f"Welcome, {st.session_state["username"]}!")
# Display settings
settings_voc = load_user_settings(st.session_state["username"])
if settings_voc:
st.write("Your discount settings:", settings_voc)
else:
st.warning("No settings stored.")
# Form to reset password
with st.form("Password change form"):
new_password = st.text_input("New password", type="password")
new_password_confirmation = st.text_input("New password confirmation", type="password")
if st.form_submit_button("Change password") and new_password == new_password_confirmation:
save_user_cred(st.session_state["username"],
generate_password_hash(new_password), "password_hash")
st.success("Password successfully saved.")
if st.button("Log out"):
st.session_state.clear()
cookie_controller.remove("auth_status")
st.rerun()
else:
with st.form("login_form", clear_on_submit=True):
st.write("Login Form")
username = st.text_input("Username")
password = st.text_input("Password", type="password")
submit = st.form_submit_button("Log in")
# Login check
if submit:
if username and password:
user = get_user_data(username)
if user:
# login_user(username, password)
if user and check_password_hash(user["password_hash"], password):
st.session_state.username = username
st.session_state.is_authenticated = True
apply_settings(username)
cookie_controller.set("auth_status", {"username": st.session_state.username,
"is_authenticated": st.session_state.is_authenticated})
else:
time.sleep(3)
st.error("Wrong username or password.")
st.session_state.is_authenticated = False
st.rerun()
else:
st.error("No user found.")
else:
st.error("You need to enter credentials")
with st.form("registration_form", clear_on_submit=True):
username = st.text_input("Username")
email = st.text_input("Email")
password = st.text_input("Password", type="password")
confirm_password = st.text_input("Confirm Password", type="password")
# Кнопка отправки внутри формы
submitted = st.form_submit_button("Submit")
# Логика при отправке формы
if submitted:
if password == confirm_password:
register_user(username, email, username, password)
st.success("Registration successfull")
else:
st.error("Passwords do not match.")