File size: 5,497 Bytes
c186757
b24d62a
c186757
 
b24d62a
c186757
 
b24d62a
c186757
 
b24d62a
1a780aa
 
 
 
 
 
 
b24d62a
 
1a780aa
 
 
 
 
 
c186757
eaae9d8
 
 
 
 
c186757
eaae9d8
c186757
eaae9d8
c186757
 
eaae9d8
86b6921
eaae9d8
 
c186757
 
eaae9d8
1a780aa
 
 
 
eaae9d8
 
1a780aa
eaae9d8
 
1a780aa
2faa222
 
 
 
 
 
1a780aa
 
2faa222
 
1a780aa
2faa222
1a780aa
 
 
 
2faa222
 
 
 
 
eaae9d8
 
 
 
1a780aa
eaae9d8
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1a780aa
 
 
 
 
 
 
 
 
 
 
 
 
 
 
c186757
1a780aa
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
c186757
1a780aa
 
 
 
 
 
c186757
eaae9d8
 
 
 
 
 
 
 
 
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
import os

import pandas as pd
import requests
import streamlit as st
from dotenv import load_dotenv

from modules.utils import set_sidebar

load_dotenv()

PANTRY_ID = os.environ.get("PANTRY_ID")
PANTRY_BASKET = os.environ.get("PANTRY_BASKET")
assert (
    PANTRY_ID is not None and PANTRY_BASKET is not None
), "Pantry ID and basket name must be set in .env file."


PAGE_TITLE = "The Leaderboard"

pd.set_option("future.no_silent_downcasting", True)


def _user_passed_level(df: pd.DataFrame, name: str, level: str) -> bool:
    return df.loc[df["Name"] == name, level].values[0] == "βœ…"


def main():
    st.set_page_config(
        page_title=PAGE_TITLE,
        page_icon="assets/effixis_logo.ico",
        layout="centered",
    )
    set_sidebar()

    st.title(PAGE_TITLE)

    st.markdown(
        """
        ### *Welcome to the Leaderboard!*
        Here you can submit your keys and see how you compare to others!
        """
    )

    # Display leaderboard
    leaderboard_url = (
        f"https://getpantry.cloud/apiv1/pantry/{PANTRY_ID}/basket/{PANTRY_BASKET}"
    )
    leaderboard_response = requests.get(leaderboard_url)
    if leaderboard_response.status_code == 200:
        leaderboard_json = leaderboard_response.json()
        print(f"Leaderboard data: {leaderboard_json}")
        leaderboard_data = (
            pd.DataFrame(leaderboard_json)
            .transpose()
            .rename(
                columns={
                    "level 0": "Level 1",
                    "level 1": "Level 2",
                    "level 2": "Level 3",
                },
            )[["Level 1", "Level 2", "Level 3"]]
            .fillna(False)
            .map(lambda x: "βœ…" if x else "❌")
            .assign(
                # Weighted sum of the levels
                Score=lambda df: df.apply(
                    lambda x: sum(
                        [int(passing == "βœ…") * (i + 1) for i, passing in enumerate(x)]
                    ),
                    axis=1,
                )
            )
            .sort_values(by="Score", ascending=False)
            .reset_index()
            .rename(columns={"index": "Name"})
        )
        st.dataframe(leaderboard_data)
    else:
        st.error("An error occurred while fetching the leaderboard.")
        st.stop()

    # Submit keys
    with st.form("leaderboard"):
        key = st.text_input("Enter your key here:")
        email = st.text_input("Enter your email here:")
        display_name = st.text_input("Enter your leaderboard display name here:")
        st.markdown(
            "*Note: Your email will not be displayed on the leaderboard, it is only used to contact you if you win!*"
        )
        submit = st.form_submit_button("Submit")

        if submit and key and email and display_name:
            if (
                display_name in leaderboard_json.keys()
                and email != leaderboard_json[display_name]["email"]
            ):
                st.error(
                    "This display name is already taken, please choose another one."
                )
            else:
                if key not in {
                    os.environ.get("LEVEL_1_KEY"),
                    os.environ.get("LEVEL_2_KEY"),
                    os.environ.get("LEVEL_3_KEY"),
                }:
                    st.error("Invalid key!")
                    st.stop()

                if display_name not in leaderboard_json.keys():
                    data = {
                        display_name: {
                            "email": email,
                            "level 0": key == os.environ.get("LEVEL_1_KEY"),
                            "level 1": key == os.environ.get("LEVEL_2_KEY"),
                            "level 2": key == os.environ.get("LEVEL_3_KEY"),
                        }
                    }
                else:
                    data = {
                        display_name: {
                            "email": email,
                            "level 0": (
                                key == os.environ.get("LEVEL_1_KEY")
                                or _user_passed_level(
                                    leaderboard_data, display_name, "Level 1"
                                )
                            ),
                            "level 1": (
                                key == os.environ.get("LEVEL_2_KEY")
                                or _user_passed_level(
                                    leaderboard_data, display_name, "Level 2"
                                )
                            ),
                            "level 2": (
                                key == os.environ.get("LEVEL_3_KEY")
                                or _user_passed_level(
                                    leaderboard_data, display_name, "Level 3"
                                )
                            ),
                        }
                    }

                try:
                    updated_data = leaderboard_json | data
                    print(f"Updated data: {updated_data}")
                    _ = requests.post(leaderboard_url, json=leaderboard_json | data)

                    st.success(
                        "You should soon be able to see your name and your scores on the leaderboard! πŸŽ‰"
                    )
                except Exception as e:
                    st.error(f"An error occurred while submitting your key: {e}")


if __name__ == "__main__":
    main()