Update app.py
Browse files
app.py
CHANGED
@@ -8,61 +8,121 @@ import plotly.express as px
|
|
8 |
import time
|
9 |
from datetime import datetime, timedelta
|
10 |
import random
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
11 |
|
12 |
# Custom CSS for styling
|
13 |
st.markdown("""
|
14 |
<style>
|
|
|
|
|
15 |
.stApp {
|
16 |
-
background: #
|
|
|
17 |
}
|
18 |
.header {
|
19 |
-
font-size:
|
20 |
font-weight: bold;
|
21 |
-
color: #
|
22 |
text-align: center;
|
23 |
-
margin-bottom:
|
|
|
24 |
}
|
25 |
.subheader {
|
26 |
-
font-size:
|
27 |
font-weight: bold;
|
28 |
-
color: #
|
29 |
text-align: center;
|
30 |
-
margin-bottom:
|
31 |
}
|
32 |
.section {
|
33 |
background: white;
|
34 |
-
padding:
|
35 |
-
border-radius:
|
36 |
-
box-shadow: 0px
|
37 |
-
margin-bottom:
|
38 |
}
|
39 |
.footer {
|
40 |
text-align: center;
|
41 |
font-size: 14px;
|
42 |
-
color: #
|
43 |
-
margin-top:
|
|
|
|
|
44 |
}
|
45 |
.stProgress > div > div > div > div {
|
46 |
-
background-image: linear-gradient(to right, #
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
47 |
}
|
48 |
@keyframes gradient {
|
49 |
0% {background-position: 0% 50%;}
|
50 |
50% {background-position: 100% 50%;}
|
51 |
100% {background-position: 0% 50%;}
|
52 |
}
|
53 |
-
.
|
54 |
-
background:
|
55 |
-
|
56 |
-
|
57 |
-
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
58 |
border-radius: 5px;
|
59 |
-
margin-bottom: 10px;
|
60 |
}
|
61 |
</style>
|
62 |
""", unsafe_allow_html=True)
|
63 |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
64 |
# Function to call the Together AI model
|
65 |
-
def call_ai_model(
|
66 |
url = "https://api.together.xyz/v1/chat/completions"
|
67 |
payload = {
|
68 |
"model": "NousResearch/Nous-Hermes-2-Yi-34B",
|
@@ -71,7 +131,7 @@ def call_ai_model(all_message):
|
|
71 |
"top_k": 50,
|
72 |
"repetition_penalty": 1,
|
73 |
"n": 1,
|
74 |
-
"messages": [{"role": "user", "content":
|
75 |
"stream_tokens": True,
|
76 |
}
|
77 |
|
@@ -85,228 +145,378 @@ def call_ai_model(all_message):
|
|
85 |
"Authorization": f"Bearer {TOGETHER_API_KEY}",
|
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 |
-
# Function to get AI explanation for graphs
|
112 |
-
def get_ai_explanation(graph_type, data):
|
113 |
-
explanation_prompt = f"Provide a short, clear explanation of the following {graph_type} graph data: {data}"
|
114 |
-
response = call_ai_model(explanation_prompt)
|
115 |
-
explanation = process_ai_response(response)
|
116 |
-
return explanation
|
117 |
-
|
118 |
-
# Function to generate simulated trust scores
|
119 |
-
def generate_trust_scores(technologies, issues):
|
120 |
-
trust_scores = {}
|
121 |
-
for tech in technologies:
|
122 |
-
trust_scores[tech] = {}
|
123 |
-
for issue in issues:
|
124 |
-
trust_scores[tech][issue] = random.uniform(0, 1)
|
125 |
-
return trust_scores
|
126 |
|
127 |
-
# Function to generate simulated
|
128 |
-
def
|
129 |
-
|
130 |
-
kinship_aspects = ["Family Communication", "Intergenerational Relationships", "Cultural Traditions"]
|
131 |
-
for tech in technologies:
|
132 |
-
impact_scores[tech] = {}
|
133 |
-
for aspect in kinship_aspects:
|
134 |
-
impact_scores[tech][aspect] = random.uniform(-1, 1)
|
135 |
-
return impact_scores
|
136 |
|
137 |
-
# Function to
|
138 |
-
def
|
139 |
-
|
140 |
-
|
141 |
-
|
142 |
-
|
143 |
-
|
144 |
-
|
|
|
145 |
|
146 |
-
# Function to
|
147 |
-
def
|
148 |
-
|
149 |
-
|
150 |
-
|
151 |
-
|
152 |
-
|
153 |
-
|
154 |
-
return impact_data
|
155 |
|
156 |
# Streamlit app layout
|
157 |
-
st.markdown('<div class="header">Digital
|
158 |
-
st.markdown('<div class="subheader">
|
159 |
-
|
160 |
-
# Input section
|
161 |
-
with st.container():
|
162 |
-
st.markdown('<div class="section">', unsafe_allow_html=True)
|
163 |
-
st.subheader("Digital Technology Impacts")
|
164 |
-
digital_technologies = st.multiselect("Select digital technologies:", ["Big Data Analytics", "Biometric Authentication", "Blockchain", "E-commerce", "Social Media Platforms"])
|
165 |
-
issues = st.multiselect("Select issues of concern:", ["Trust", "Mistrust", "Data Privacy", "Fraud", "Social Classification"])
|
166 |
-
|
167 |
-
st.subheader("Kenya-Specific Inputs")
|
168 |
-
regions = st.multiselect("Select regions in Kenya:", ["Nairobi", "Coast", "Nyanza", "Rift valley", "Eastern", "North Eastern"])
|
169 |
-
gender_focus = st.multiselect("Select gender focus:", ["Male", "Female", "Non-binary"])
|
170 |
-
st.markdown('</div>', unsafe_allow_html=True)
|
171 |
|
172 |
-
#
|
173 |
-
|
174 |
-
|
175 |
-
f"Analyze the impact of digital technologies on kinship and gender dynamics in Kenya. "
|
176 |
-
f"Digital technologies: {', '.join(digital_technologies)}. "
|
177 |
-
f"Issues of concern: {', '.join(issues)}. "
|
178 |
-
f"Regions: {', '.join(regions)}. Gender focus: {', '.join(gender_focus)}. "
|
179 |
-
f"Provide a detailed analysis of how these technologies impact family ties, trust, and gender roles. "
|
180 |
-
f"Include specific impacts for each digital technology and issue. "
|
181 |
-
f"Organize the information in tables with the following columns: Digital Technology, Impact on Kinship, Impact on Gender Dynamics, Trust Issues. "
|
182 |
-
f"Be as accurate and specific to Kenya as possible in your analysis. Make the response short and precise. Do not give anything like a conclusion after generating"
|
183 |
-
)
|
184 |
-
|
185 |
-
try:
|
186 |
-
stages = [
|
187 |
-
"Analyzing digital technologies...",
|
188 |
-
"Running simulations...",
|
189 |
-
"Processing data...",
|
190 |
-
"Assessing impacts...",
|
191 |
-
"Calculating predictions...",
|
192 |
-
"Compiling results...",
|
193 |
-
"Finalizing analysis...",
|
194 |
-
"Preparing output..."
|
195 |
-
]
|
196 |
-
|
197 |
-
progress_bar = st.progress(0)
|
198 |
-
status_text = st.empty()
|
199 |
-
|
200 |
-
for i, stage in enumerate(stages):
|
201 |
-
status_text.markdown(f'<div class="animated-div">{stage}</div>', unsafe_allow_html=True)
|
202 |
-
progress_bar.progress((i + 1) / len(stages))
|
203 |
-
time.sleep(1)
|
204 |
-
|
205 |
-
response = call_ai_model(all_message)
|
206 |
-
analysis_text = process_ai_response(response)
|
207 |
|
208 |
-
|
209 |
-
|
210 |
-
|
211 |
st.markdown('<div class="section">', unsafe_allow_html=True)
|
212 |
-
st.subheader("
|
213 |
-
st.
|
|
|
|
|
|
|
|
|
|
|
214 |
st.markdown('</div>', unsafe_allow_html=True)
|
|
|
|
|
215 |
|
216 |
-
|
217 |
-
|
218 |
-
|
219 |
-
|
220 |
-
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
221 |
|
222 |
-
|
223 |
-
|
224 |
-
|
225 |
-
fig_trust = go.Figure()
|
226 |
-
for tech in digital_technologies:
|
227 |
-
fig_trust.add_trace(go.Bar(
|
228 |
-
x=list(trust_scores[tech].keys()),
|
229 |
-
y=list(trust_scores[tech].values()),
|
230 |
-
name=tech
|
231 |
-
))
|
232 |
-
fig_trust.update_layout(barmode='group', title="Trust Scores by Technology and Issue")
|
233 |
-
st.plotly_chart(fig_trust)
|
234 |
-
trust_explanation = get_ai_explanation("Trust and Fraud Metrics", trust_scores)
|
235 |
-
st.markdown(f"**AI Explanation:** {trust_explanation}")
|
236 |
-
st.markdown('</div>', unsafe_allow_html=True)
|
237 |
|
238 |
-
|
239 |
-
|
240 |
-
|
241 |
-
|
242 |
-
|
243 |
-
|
244 |
-
|
245 |
-
|
246 |
-
|
247 |
-
|
248 |
-
|
249 |
-
|
250 |
-
|
251 |
-
|
252 |
-
|
253 |
-
st.
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
254 |
|
255 |
-
|
256 |
-
|
257 |
-
|
258 |
-
|
259 |
-
|
260 |
-
|
261 |
-
|
262 |
-
|
263 |
-
|
264 |
-
|
265 |
-
|
266 |
-
|
267 |
-
|
268 |
-
|
269 |
-
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
270 |
|
271 |
-
|
272 |
-
|
273 |
-
|
274 |
-
|
275 |
-
|
276 |
-
|
277 |
-
|
278 |
-
|
279 |
-
|
280 |
-
|
281 |
-
|
282 |
-
|
283 |
-
|
284 |
-
|
285 |
-
|
286 |
-
|
287 |
-
|
288 |
-
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
289 |
|
290 |
-
|
291 |
-
|
292 |
-
|
293 |
-
|
294 |
-
|
295 |
-
|
296 |
-
|
297 |
-
|
298 |
-
|
299 |
-
|
300 |
-
|
301 |
-
|
302 |
-
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
303 |
|
304 |
-
|
305 |
-
|
306 |
-
|
307 |
-
|
308 |
-
|
309 |
-
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
310 |
|
311 |
# Footer
|
312 |
-
st.markdown('<div class="footer"
|
|
|
|
|
|
|
|
|
|
|
|
8 |
import time
|
9 |
from datetime import datetime, timedelta
|
10 |
import random
|
11 |
+
import nltk
|
12 |
+
from nltk.corpus import stopwords
|
13 |
+
from wordcloud import WordCloud
|
14 |
+
import matplotlib.pyplot as plt
|
15 |
+
from streamlit_lottie import st_lottie
|
16 |
+
import base64
|
17 |
+
from PIL import Image
|
18 |
+
import io
|
19 |
+
|
20 |
+
# Download NLTK data
|
21 |
+
nltk.download('stopwords', quiet=True)
|
22 |
+
nltk.download('punkt', quiet=True)
|
23 |
+
|
24 |
+
# Set page config
|
25 |
+
st.set_page_config(page_title="DSEAP", page_icon="📊", layout="wide")
|
26 |
|
27 |
# Custom CSS for styling
|
28 |
st.markdown("""
|
29 |
<style>
|
30 |
+
@import url('https://fonts.googleapis.com/css2?family=Roboto:wght@300;400;700&display=swap');
|
31 |
+
|
32 |
.stApp {
|
33 |
+
background: #f0f2f6;
|
34 |
+
font-family: 'Roboto', sans-serif;
|
35 |
}
|
36 |
.header {
|
37 |
+
font-size: 42px;
|
38 |
font-weight: bold;
|
39 |
+
color: #1e3799;
|
40 |
text-align: center;
|
41 |
+
margin-bottom: 30px;
|
42 |
+
text-shadow: 2px 2px 4px rgba(0,0,0,0.1);
|
43 |
}
|
44 |
.subheader {
|
45 |
+
font-size: 28px;
|
46 |
font-weight: bold;
|
47 |
+
color: #3c6382;
|
48 |
text-align: center;
|
49 |
+
margin-bottom: 25px;
|
50 |
}
|
51 |
.section {
|
52 |
background: white;
|
53 |
+
padding: 25px;
|
54 |
+
border-radius: 15px;
|
55 |
+
box-shadow: 0px 8px 16px rgba(0, 0, 0, 0.1);
|
56 |
+
margin-bottom: 30px;
|
57 |
}
|
58 |
.footer {
|
59 |
text-align: center;
|
60 |
font-size: 14px;
|
61 |
+
color: #555;
|
62 |
+
margin-top: 30px;
|
63 |
+
padding: 10px;
|
64 |
+
border-top: 1px solid #ddd;
|
65 |
}
|
66 |
.stProgress > div > div > div > div {
|
67 |
+
background-image: linear-gradient(to right, #4a69bd, #6a89cc);
|
68 |
+
}
|
69 |
+
.stButton>button {
|
70 |
+
background-color: #4a69bd;
|
71 |
+
color: white;
|
72 |
+
font-weight: bold;
|
73 |
+
border-radius: 5px;
|
74 |
+
padding: 10px 20px;
|
75 |
+
transition: all 0.3s ease;
|
76 |
+
}
|
77 |
+
.stButton>button:hover {
|
78 |
+
background-color: #1e3799;
|
79 |
+
box-shadow: 0px 4px 8px rgba(0, 0, 0, 0.2);
|
80 |
+
}
|
81 |
+
.animated-div {
|
82 |
+
background: linear-gradient(-45deg, #4a69bd, #6a89cc, #54a0ff, #5f27cd);
|
83 |
+
background-size: 400% 400%;
|
84 |
+
animation: gradient 15s ease infinite;
|
85 |
+
padding: 15px;
|
86 |
+
border-radius: 10px;
|
87 |
+
margin-bottom: 15px;
|
88 |
+
color: white;
|
89 |
+
font-weight: bold;
|
90 |
}
|
91 |
@keyframes gradient {
|
92 |
0% {background-position: 0% 50%;}
|
93 |
50% {background-position: 100% 50%;}
|
94 |
100% {background-position: 0% 50%;}
|
95 |
}
|
96 |
+
.info-box {
|
97 |
+
background-color: #e3f2fd;
|
98 |
+
border-left: 5px solid #2196f3;
|
99 |
+
padding: 15px;
|
100 |
+
margin-bottom: 20px;
|
101 |
+
border-radius: 5px;
|
102 |
+
}
|
103 |
+
.warning-box {
|
104 |
+
background-color: #fff3e0;
|
105 |
+
border-left: 5px solid #ff9800;
|
106 |
+
padding: 15px;
|
107 |
+
margin-bottom: 20px;
|
108 |
border-radius: 5px;
|
|
|
109 |
}
|
110 |
</style>
|
111 |
""", unsafe_allow_html=True)
|
112 |
|
113 |
+
# Function to load Lottie animations
|
114 |
+
def load_lottieurl(url: str):
|
115 |
+
r = requests.get(url)
|
116 |
+
if r.status_code != 200:
|
117 |
+
return None
|
118 |
+
return r.json()
|
119 |
+
|
120 |
+
# Load Lottie animations
|
121 |
+
lottie_analytics = load_lottieurl("https://assets5.lottiefiles.com/packages/lf20_qp1q7mct.json")
|
122 |
+
lottie_skills = load_lottieurl("https://assets5.lottiefiles.com/private_files/lf30_wqypnpu5.json")
|
123 |
+
|
124 |
# Function to call the Together AI model
|
125 |
+
def call_ai_model(prompt):
|
126 |
url = "https://api.together.xyz/v1/chat/completions"
|
127 |
payload = {
|
128 |
"model": "NousResearch/Nous-Hermes-2-Yi-34B",
|
|
|
131 |
"top_k": 50,
|
132 |
"repetition_penalty": 1,
|
133 |
"n": 1,
|
134 |
+
"messages": [{"role": "user", "content": prompt}],
|
135 |
"stream_tokens": True,
|
136 |
}
|
137 |
|
|
|
145 |
"Authorization": f"Bearer {TOGETHER_API_KEY}",
|
146 |
}
|
147 |
|
148 |
+
try:
|
149 |
+
response = requests.post(url, json=payload, headers=headers, stream=True)
|
150 |
+
response.raise_for_status()
|
151 |
+
|
152 |
+
full_response = ""
|
153 |
+
for line in response.iter_lines():
|
154 |
+
if line:
|
155 |
+
line_content = line.decode('utf-8')
|
156 |
+
if line_content.startswith("data: "):
|
157 |
+
line_content = line_content[6:]
|
158 |
+
try:
|
159 |
+
json_data = json.loads(line_content)
|
160 |
+
if "choices" in json_data:
|
161 |
+
delta = json_data["choices"][0]["delta"]
|
162 |
+
if "content" in delta:
|
163 |
+
full_response += delta["content"]
|
164 |
+
except json.JSONDecodeError:
|
165 |
+
continue
|
166 |
+
|
167 |
+
return full_response.strip()
|
168 |
+
except requests.exceptions.RequestException as e:
|
169 |
+
st.error(f"API call failed: {e}")
|
170 |
+
return "An error occurred while fetching AI insights."
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
171 |
|
172 |
+
# Function to generate simulated data
|
173 |
+
def generate_simulated_data(categories, count=5):
|
174 |
+
return {cat: [random.randint(1, 100) for _ in range(count)] for cat in categories}
|
|
|
|
|
|
|
|
|
|
|
|
|
175 |
|
176 |
+
# Function to create word cloud
|
177 |
+
def create_word_cloud(text):
|
178 |
+
stopwords = set(stopwords.words('english'))
|
179 |
+
wordcloud = WordCloud(width=800, height=400, background_color='white', stopwords=stopwords).generate(text)
|
180 |
+
|
181 |
+
fig, ax = plt.subplots(figsize=(10, 5))
|
182 |
+
ax.imshow(wordcloud, interpolation='bilinear')
|
183 |
+
ax.axis('off')
|
184 |
+
return fig
|
185 |
|
186 |
+
# Function to create a downloadable Excel report
|
187 |
+
def create_excel_report(data):
|
188 |
+
output = io.BytesIO()
|
189 |
+
with pd.ExcelWriter(output, engine='xlsxwriter') as writer:
|
190 |
+
for sheet_name, df in data.items():
|
191 |
+
df.to_excel(writer, sheet_name=sheet_name, index=False)
|
192 |
+
output.seek(0)
|
193 |
+
return output
|
|
|
194 |
|
195 |
# Streamlit app layout
|
196 |
+
st.markdown('<div class="header">Digital Skills and Employment Analytics Platform (DSEAP)</div>', unsafe_allow_html=True)
|
197 |
+
st.markdown('<div class="subheader">Empowering Youth Through Data-Driven Insights</div>', unsafe_allow_html=True)
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
198 |
|
199 |
+
# Sidebar for navigation
|
200 |
+
st.sidebar.title("Navigation")
|
201 |
+
page = st.sidebar.radio("Go to", ["Home", "Skills Analysis", "Program Evaluation", "Barrier Identification", "Recommendations", "Reports"])
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
202 |
|
203 |
+
if page == "Home":
|
204 |
+
col1, col2 = st.columns([2, 1])
|
205 |
+
with col1:
|
206 |
st.markdown('<div class="section">', unsafe_allow_html=True)
|
207 |
+
st.subheader("Welcome to DSEAP")
|
208 |
+
st.write("""
|
209 |
+
The Digital Skills and Employment Analytics Platform (DSEAP) is an AI-driven tool designed to enhance
|
210 |
+
the evaluation and improvement of digital empowerment programs in Kenya. Our platform provides comprehensive
|
211 |
+
insights into the demand for digital skills, the effectiveness of existing programs, and the barriers faced
|
212 |
+
by youth in accessing digital opportunities.
|
213 |
+
""")
|
214 |
st.markdown('</div>', unsafe_allow_html=True)
|
215 |
+
with col2:
|
216 |
+
st_lottie(lottie_analytics, height=300, key="analytics")
|
217 |
|
218 |
+
st.markdown('<div class="section">', unsafe_allow_html=True)
|
219 |
+
st.subheader("Key Features")
|
220 |
+
col1, col2, col3 = st.columns(3)
|
221 |
+
with col1:
|
222 |
+
st.markdown("### 📊 Skills Demand Analysis")
|
223 |
+
st.write("Analyze job market trends and identify in-demand digital skills.")
|
224 |
+
with col2:
|
225 |
+
st.markdown("### 📈 Program Effectiveness")
|
226 |
+
st.write("Evaluate the impact of digital empowerment programs on youth employment.")
|
227 |
+
with col3:
|
228 |
+
st.markdown("### 🚧 Barrier Identification")
|
229 |
+
st.write("Identify and address obstacles to digital skill acquisition and employment.")
|
230 |
+
st.markdown('</div>', unsafe_allow_html=True)
|
231 |
|
232 |
+
st.markdown('<div class="info-box">', unsafe_allow_html=True)
|
233 |
+
st.info("📌 **Tip:** Use the sidebar to navigate through different sections of the platform.")
|
234 |
+
st.markdown('</div>', unsafe_allow_html=True)
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
235 |
|
236 |
+
elif page == "Skills Analysis":
|
237 |
+
st.markdown('<div class="section">', unsafe_allow_html=True)
|
238 |
+
st.subheader("Digital Skills Demand Analysis")
|
239 |
+
|
240 |
+
col1, col2 = st.columns([3, 1])
|
241 |
+
with col1:
|
242 |
+
skills = st.multiselect("Select skills to analyze:",
|
243 |
+
["Data Analysis", "Web Development", "Digital Marketing", "Cybersecurity", "Cloud Computing", "AI/Machine Learning", "Mobile App Development", "UI/UX Design"])
|
244 |
+
regions = st.multiselect("Select regions:",
|
245 |
+
["Nairobi", "Mombasa", "Kisumu", "Nakuru", "Eldoret", "Thika", "Malindi", "Kitale"])
|
246 |
+
time_period = st.selectbox("Select time period:", ["Last 3 months", "Last 6 months", "Last year"])
|
247 |
+
with col2:
|
248 |
+
st_lottie(lottie_skills, height=200, key="skills")
|
249 |
+
|
250 |
+
if st.button("Analyze Skills Demand"):
|
251 |
+
with st.spinner("Analyzing skills demand..."):
|
252 |
+
# Simulated data generation
|
253 |
+
demand_data = generate_simulated_data(skills)
|
254 |
+
|
255 |
+
# Plotting
|
256 |
+
fig = go.Figure()
|
257 |
+
for skill in skills:
|
258 |
+
fig.add_trace(go.Bar(x=regions, y=demand_data[skill], name=skill))
|
259 |
+
fig.update_layout(title="Digital Skills Demand by Region", barmode='group')
|
260 |
+
st.plotly_chart(fig)
|
261 |
+
|
262 |
+
# AI Insights
|
263 |
+
ai_prompt = f"Analyze the demand for {', '.join(skills)} in {', '.join(regions)} over the {time_period}. Provide insights on trends, gaps, and recommendations for skill development."
|
264 |
+
ai_insights = call_ai_model(ai_prompt)
|
265 |
+
st.markdown("### AI Insights")
|
266 |
+
st.write(ai_insights)
|
267 |
+
|
268 |
+
# Word Cloud
|
269 |
+
word_cloud_text = " ".join(skills + regions + ai_insights.split())
|
270 |
+
st.markdown("### Skills Demand Word Cloud")
|
271 |
+
st.pyplot(create_word_cloud(word_cloud_text))
|
272 |
+
|
273 |
+
# Skills growth projection
|
274 |
+
st.markdown("### Skills Growth Projection")
|
275 |
+
growth_data = {skill: [random.uniform(0, 15) for _ in range(5)] for skill in skills}
|
276 |
+
years = [datetime.now().year + i for i in range(5)]
|
277 |
+
fig = go.Figure()
|
278 |
+
for skill, growth in growth_data.items():
|
279 |
+
fig.add_trace(go.Scatter(x=years, y=growth, mode='lines+markers', name=skill))
|
280 |
+
fig.update_layout(title="Projected Skills Growth (Next 5 Years)", xaxis_title="Year", yaxis_title="Growth Rate (%)")
|
281 |
+
st.plotly_chart(fig)
|
282 |
+
|
283 |
+
st.markdown('</div>', unsafe_allow_html=True)
|
284 |
|
285 |
+
elif page == "Program Evaluation":
|
286 |
+
st.markdown('<div class="section">', unsafe_allow_html=True)
|
287 |
+
st.subheader("Digital Empowerment Program Evaluation")
|
288 |
+
|
289 |
+
programs = st.multiselect("Select programs to evaluate:",
|
290 |
+
["Ajira Digital", "DigiTruck", "eMobilis", "KamiLimu", "Andela", "iHub", "NaiLab", "iBizAfrica"])
|
291 |
+
metrics = st.multiselect("Select evaluation metrics:",
|
292 |
+
["Employment Rate", "Income Increase", "Skill Proficiency", "Program Completion Rate", "Job Satisfaction", "Career Advancement"])
|
293 |
+
|
294 |
+
if st.button("Evaluate Programs"):
|
295 |
+
with st.spinner("Evaluating programs..."):
|
296 |
+
# Simulated data generation
|
297 |
+
evaluation_data = generate_simulated_data(programs)
|
298 |
+
|
299 |
+
# Plotting
|
300 |
+
fig = px.line(x=range(len(next(iter(evaluation_data.values())))), y=evaluation_data.values(),
|
301 |
+
labels={'x': 'Time (months)', 'y': 'Performance'}, title="Program Performance Over Time")
|
302 |
+
fig.update_layout(legend_title_text='Programs')
|
303 |
+
st.plotly_chart(fig)
|
304 |
+
|
305 |
+
# AI Insights
|
306 |
+
ai_prompt = f"Evaluate the effectiveness of {', '.join(programs)} based on {', '.join(metrics)}. Provide a detailed analysis of each program's performance, strengths, weaknesses, and recommendations for improvement."
|
307 |
+
ai_insights = call_ai_model(ai_prompt)
|
308 |
+
st.markdown("### AI-Powered Evaluation Insights")
|
309 |
+
st.write(ai_insights)
|
310 |
+
|
311 |
+
# Impact Visualization
|
312 |
+
impact_data = {prog: random.uniform(0, 1) for prog in programs}
|
313 |
+
fig = px.pie(values=impact_data.values(), names=impact_data.keys(), title="Program Impact Distribution")
|
314 |
+
st.plotly_chart(fig)
|
315 |
+
|
316 |
+
# Comparative Analysis
|
317 |
+
st.markdown("### Comparative Analysis")
|
318 |
+
comp_data = pd.DataFrame({metric: [random.uniform(0, 100) for _ in programs] for metric in metrics}, index=programs)
|
319 |
+
fig = px.imshow(comp_data, text_auto=True, aspect="auto", title="Program Performance Heatmap")
|
320 |
+
st.plotly_chart(fig)
|
321 |
+
|
322 |
+
st.markdown('</div>', unsafe_allow_html=True)
|
323 |
|
324 |
+
elif page == "Barrier Identification":
|
325 |
+
st.markdown('<div class="section">', unsafe_allow_html=True)
|
326 |
+
st.subheader("Digital Skills Acquisition Barriers")
|
327 |
+
|
328 |
+
barrier_categories = ["Access to Technology", "Digital Literacy", "Financial Constraints", "Cultural Factors", "Education System", "Gender Disparity", "Infrastructure", "Language Barriers"]
|
329 |
+
selected_barriers = st.multiselect("Select barrier categories to analyze:", barrier_categories)
|
330 |
+
|
331 |
+
if st.button("Identify Barriers"):
|
332 |
+
with st.spinner("Analyzing barriers..."):
|
333 |
+
# Simulated data generation
|
334 |
+
barrier_data = generate_simulated_data(selected_barriers)
|
335 |
+
|
336 |
+
# Plotting
|
337 |
+
fig = go.Figure(data=[go.Radar(
|
338 |
+
r=[max(barrier_data[cat]) for cat in selected_barriers],
|
339 |
+
theta=fig = go.Figure(data=[go.Radar(
|
340 |
+
r=[max(barrier_data[cat]) for cat in selected_barriers],
|
341 |
+
theta=selected_barriers,
|
342 |
+
fill='toself'
|
343 |
+
)])
|
344 |
+
fig.update_layout(title="Barrier Intensity Analysis")
|
345 |
+
st.plotly_chart(fig)
|
346 |
+
|
347 |
+
# AI Insights
|
348 |
+
ai_prompt = f"Analyze the barriers to digital skills acquisition in Kenya, focusing on {', '.join(selected_barriers)}. Provide a comprehensive breakdown of each barrier, its impact, and potential solutions."
|
349 |
+
ai_insights = call_ai_model(ai_prompt)
|
350 |
+
st.markdown("### AI-Generated Barrier Analysis")
|
351 |
+
st.write(ai_insights)
|
352 |
+
|
353 |
+
# Recommendations
|
354 |
+
st.markdown("### Recommended Interventions")
|
355 |
+
interventions = {
|
356 |
+
"Access to Technology": "Implement mobile learning programs and community technology centers",
|
357 |
+
"Digital Literacy": "Integrate digital skills into primary and secondary education curricula",
|
358 |
+
"Financial Constraints": "Provide scholarships and low-interest loans for digital skills training",
|
359 |
+
"Cultural Factors": "Develop culturally sensitive training materials and awareness campaigns",
|
360 |
+
"Education System": "Partner with local schools for early digital education integration",
|
361 |
+
"Gender Disparity": "Create women-focused digital skills programs and mentorship opportunities",
|
362 |
+
"Infrastructure": "Invest in rural broadband expansion and solar-powered internet kiosks",
|
363 |
+
"Language Barriers": "Develop multilingual digital learning resources and interfaces"
|
364 |
+
}
|
365 |
+
for barrier in selected_barriers:
|
366 |
+
st.write(f"- **{barrier}:** {interventions.get(barrier, 'Customized intervention based on specific barrier characteristics')}")
|
367 |
+
|
368 |
+
# Barrier Impact Over Time
|
369 |
+
st.markdown("### Projected Barrier Impact Over Time")
|
370 |
+
years = [datetime.now().year + i for i in range(5)]
|
371 |
+
impact_data = {barrier: [random.uniform(0, 100) for _ in range(5)] for barrier in selected_barriers}
|
372 |
+
fig = go.Figure()
|
373 |
+
for barrier, impact in impact_data.items():
|
374 |
+
fig.add_trace(go.Scatter(x=years, y=impact, mode='lines+markers', name=barrier))
|
375 |
+
fig.update_layout(title="Projected Barrier Impact (Next 5 Years)", xaxis_title="Year", yaxis_title="Impact Score")
|
376 |
+
st.plotly_chart(fig)
|
377 |
+
|
378 |
+
st.markdown('</div>', unsafe_allow_html=True)
|
379 |
|
380 |
+
elif page == "Recommendations":
|
381 |
+
st.markdown('<div class="section">', unsafe_allow_html=True)
|
382 |
+
st.subheader("Personalized Recommendations")
|
383 |
+
|
384 |
+
# User profile input
|
385 |
+
st.write("Enter your profile information to receive personalized recommendations:")
|
386 |
+
age = st.slider("Age", 15, 35, 25)
|
387 |
+
education = st.selectbox("Highest Education Level", ["High School", "Diploma", "Bachelor's", "Master's", "PhD"])
|
388 |
+
current_skills = st.multiselect("Current Digital Skills",
|
389 |
+
["Basic Computer Use", "Office Software", "Web Browsing", "Social Media",
|
390 |
+
"Programming", "Data Analysis", "Graphic Design", "Digital Marketing"])
|
391 |
+
career_goal = st.text_input("Career Goal")
|
392 |
+
location = st.selectbox("Current Location", ["Nairobi", "Mombasa", "Kisumu", "Nakuru", "Eldoret", "Other"])
|
393 |
+
|
394 |
+
if st.button("Get Recommendations"):
|
395 |
+
with st.spinner("Generating personalized recommendations..."):
|
396 |
+
# AI-generated recommendations
|
397 |
+
ai_prompt = f"""Generate personalized digital skills recommendations for a {age}-year-old with {education} education,
|
398 |
+
skills in {', '.join(current_skills)}, located in {location}, aiming for a career in {career_goal}.
|
399 |
+
Provide a detailed learning path, skill priorities, job market insights, and potential challenges to overcome."""
|
400 |
+
recommendations = call_ai_model(ai_prompt)
|
401 |
+
|
402 |
+
st.markdown("### Your Personalized Digital Skills Roadmap")
|
403 |
+
st.write(recommendations)
|
404 |
+
|
405 |
+
# Simulated skill gap analysis
|
406 |
+
st.markdown("### Skill Gap Analysis")
|
407 |
+
all_skills = ["Data Analysis", "Web Development", "Digital Marketing", "Cybersecurity", "Cloud Computing",
|
408 |
+
"AI/Machine Learning", "Mobile App Development", "UI/UX Design"]
|
409 |
+
skill_gaps = [skill for skill in all_skills if skill not in current_skills]
|
410 |
+
gap_scores = [random.randint(1, 100) for _ in skill_gaps]
|
411 |
+
fig = go.Figure(go.Bar(
|
412 |
+
x=skill_gaps,
|
413 |
+
y=gap_scores,
|
414 |
+
marker_color=['#1e3799', '#4a69bd', '#6a89cc', '#54a0ff', '#48dbfb']
|
415 |
+
))
|
416 |
+
fig.update_layout(title="Skill Gap Analysis", xaxis_title="Skills", yaxis_title="Proficiency Gap")
|
417 |
+
st.plotly_chart(fig)
|
418 |
+
|
419 |
+
# Job market alignment
|
420 |
+
st.markdown("### Job Market Alignment")
|
421 |
+
job_matches = ["Data Analyst", "Digital Marketing Specialist", "Front-end Developer", "UX Researcher", "Cybersecurity Analyst"]
|
422 |
+
match_scores = [random.uniform(0.5, 1) for _ in job_matches]
|
423 |
+
fig = px.bar(x=job_matches, y=match_scores, labels={'x': 'Job Titles', 'y': 'Match Score'}, title="Top Job Matches")
|
424 |
+
st.plotly_chart(fig)
|
425 |
+
|
426 |
+
# Learning resources
|
427 |
+
st.markdown("### Recommended Learning Resources")
|
428 |
+
resources = [
|
429 |
+
{"name": "Coursera", "type": "Online Courses", "link": "https://www.coursera.org/"},
|
430 |
+
{"name": "edX", "type": "Online Courses", "link": "https://www.edx.org/"},
|
431 |
+
{"name": "Udacity", "type": "Nanodegree Programs", "link": "https://www.udacity.com/"},
|
432 |
+
{"name": "FreeCodeCamp", "type": "Coding Tutorials", "link": "https://www.freecodecamp.org/"},
|
433 |
+
{"name": "Codecademy", "type": "Interactive Coding Lessons", "link": "https://www.codecademy.com/"}
|
434 |
+
]
|
435 |
+
for resource in resources:
|
436 |
+
st.write(f"- [{resource['name']}]({resource['link']}) - {resource['type']}")
|
437 |
+
|
438 |
+
st.markdown('</div>', unsafe_allow_html=True)
|
439 |
|
440 |
+
elif page == "Reports":
|
441 |
+
st.markdown('<div class="section">', unsafe_allow_html=True)
|
442 |
+
st.subheader("Generate Custom Reports")
|
443 |
+
|
444 |
+
report_type = st.selectbox("Select Report Type", ["Skills Demand", "Program Effectiveness", "Barrier Analysis"])
|
445 |
+
date_range = st.date_input("Select Date Range", [datetime.now() - timedelta(days=30), datetime.now()])
|
446 |
+
|
447 |
+
if st.button("Generate Report"):
|
448 |
+
with st.spinner("Generating report..."):
|
449 |
+
# Simulated report generation
|
450 |
+
if report_type == "Skills Demand":
|
451 |
+
skills = ["Data Analysis", "Web Development", "Digital Marketing", "Cybersecurity", "Cloud Computing"]
|
452 |
+
demand_data = pd.DataFrame({
|
453 |
+
"Skill": skills,
|
454 |
+
"Demand Score": [random.randint(50, 100) for _ in skills],
|
455 |
+
"Growth Rate": [random.uniform(0.5, 15) for _ in skills]
|
456 |
+
})
|
457 |
+
|
458 |
+
st.markdown("### Skills Demand Report")
|
459 |
+
st.dataframe(demand_data)
|
460 |
+
|
461 |
+
fig = px.scatter(demand_data, x="Demand Score", y="Growth Rate", size="Demand Score",
|
462 |
+
color="Skill", hover_name="Skill", size_max=60)
|
463 |
+
fig.update_layout(title="Skills Demand vs Growth Rate")
|
464 |
+
st.plotly_chart(fig)
|
465 |
+
|
466 |
+
elif report_type == "Program Effectiveness":
|
467 |
+
programs = ["Ajira Digital", "DigiTruck", "eMobilis", "KamiLimu", "Andela"]
|
468 |
+
metrics = ["Employment Rate", "Income Increase", "Skill Proficiency", "Program Completion Rate"]
|
469 |
+
effectiveness_data = pd.DataFrame({
|
470 |
+
metric: [random.uniform(60, 95) for _ in programs] for metric in metrics
|
471 |
+
}, index=programs)
|
472 |
+
|
473 |
+
st.markdown("### Program Effectiveness Report")
|
474 |
+
st.dataframe(effectiveness_data)
|
475 |
+
|
476 |
+
fig = px.imshow(effectiveness_data, text_auto=True, aspect="auto",
|
477 |
+
title="Program Effectiveness Heatmap")
|
478 |
+
st.plotly_chart(fig)
|
479 |
+
|
480 |
+
elif report_type == "Barrier Analysis":
|
481 |
+
barriers = ["Access to Technology", "Digital Literacy", "Financial Constraints", "Cultural Factors"]
|
482 |
+
impact_data = pd.DataFrame({
|
483 |
+
"Barrier": barriers,
|
484 |
+
"Impact Score": [random.uniform(3, 9) for _ in barriers],
|
485 |
+
"Affected Population (%)": [random.uniform(10, 50) for _ in barriers]
|
486 |
+
})
|
487 |
+
|
488 |
+
st.markdown("### Barrier Analysis Report")
|
489 |
+
st.dataframe(impact_data)
|
490 |
+
|
491 |
+
fig = px.bar(impact_data, x="Barrier", y="Impact Score", color="Affected Population (%)",
|
492 |
+
title="Barrier Impact Analysis")
|
493 |
+
st.plotly_chart(fig)
|
494 |
+
|
495 |
+
# Generate Excel report
|
496 |
+
excel_data = {
|
497 |
+
"Report": pd.DataFrame({"Report Type": [report_type], "Date Range": [f"{date_range[0]} to {date_range[1]}"]})
|
498 |
+
}
|
499 |
+
if report_type == "Skills Demand":
|
500 |
+
excel_data["Skills Demand"] = demand_data
|
501 |
+
elif report_type == "Program Effectiveness":
|
502 |
+
excel_data["Program Effectiveness"] = effectiveness_data
|
503 |
+
elif report_type == "Barrier Analysis":
|
504 |
+
excel_data["Barrier Analysis"] = impact_data
|
505 |
+
|
506 |
+
excel_report = create_excel_report(excel_data)
|
507 |
+
st.download_button(
|
508 |
+
label="Download Excel Report",
|
509 |
+
data=excel_report,
|
510 |
+
file_name=f"DSEAP_{report_type}_Report_{date_range[0]}_{date_range[1]}.xlsx",
|
511 |
+
mime="application/vnd.openxmlformats-officedocument.spreadsheetml.sheet"
|
512 |
+
)
|
513 |
+
|
514 |
+
st.markdown('</div>', unsafe_allow_html=True)
|
515 |
|
516 |
# Footer
|
517 |
+
st.markdown('<div class="footer">© 2024 Digital Skills and Employment Analytics Platform (DSEAP) | Developed by Your Team</div>', unsafe_allow_html=True)
|
518 |
+
|
519 |
+
# Add a warning about simulated data
|
520 |
+
st.markdown('<div class="warning-box">', unsafe_allow_html=True)
|
521 |
+
st.warning("**Note:** This is a prototype version Developed by Teresa Abuya, COD SIST")
|
522 |
+
st.markdown('</div>', unsafe_allow_html=True)
|