ginipick commited on
Commit
c9f9775
ยท
verified ยท
1 Parent(s): 9bb8db0

Update app.py

Browse files
Files changed (1) hide show
  1. app.py +111 -104
app.py CHANGED
@@ -31,7 +31,7 @@ def create_trend_chart(space_id, daily_ranks_df):
31
  xaxis_title="Date",
32
  yaxis_title="Rank",
33
  yaxis=dict(
34
- range=[100, 1],
35
  tickmode='linear',
36
  tick0=1,
37
  dtick=10
@@ -54,55 +54,111 @@ def create_trend_chart(space_id, daily_ranks_df):
54
 
55
  return fig
56
  except Exception as e:
57
- print(f"Error creating chart: {e}")
 
58
  return None
59
 
60
- def get_total_scores(daily_ranks_df):
 
 
 
 
 
61
  try:
62
- # ์ตœ์‹  ๋‚ ์งœ ์ฐพ๊ธฐ
63
- latest_date = daily_ranks_df['date'].max()
64
- print(f"Latest date: {latest_date}")
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
65
 
66
- # ์ตœ์‹  ๋‚ ์งœ์˜ Top 100 ๋ฐ์ดํ„ฐ ๊ฐ€์ ธ์˜ค๊ธฐ
67
- latest_top_100 = daily_ranks_df[
 
 
 
 
68
  (daily_ranks_df['date'] == latest_date) &
69
  (daily_ranks_df['rank'] <= 100)
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
70
  ].copy()
71
- print(f"Number of entries in top 100: {len(latest_top_100)}")
72
 
73
- # ID ๋นˆ๋„์ˆ˜ ํ™•์ธ
74
- id_counts = latest_top_100['id'].value_counts()
 
75
  multiple_ids = id_counts[id_counts >= 2].index
76
- print(f"IDs with multiple entries: {len(multiple_ids)}")
77
 
78
- # ์ค‘๋ณต ๋“ฑ๋ก๋œ ID๋“ค์˜ ๋ฐ์ดํ„ฐ๋งŒ ํ•„ํ„ฐ๋ง
79
- multiple_entries = latest_top_100[latest_top_100['id'].isin(multiple_ids)].copy()
 
80
 
81
- # ID๋ณ„๋กœ ์Šค์ฝ”์–ด ํ•ฉ์‚ฐ ๋ฐ ๋“ฑ์žฅ ํšŸ์ˆ˜ ๊ณ„์‚ฐ
82
- summary = pd.DataFrame({
83
- 'total_score': multiple_entries.groupby('id')['trendingScore'].sum(),
84
- 'count': multiple_entries.groupby('id')['id'].count()
85
- }).sort_values('total_score', ascending=True)
86
 
87
- print("Summary of multiple entries:")
88
- print(summary)
 
 
 
 
89
 
90
- return summary
 
91
 
 
92
  except Exception as e:
93
- print(f"Error in get_total_scores: {e}")
94
  traceback.print_exc()
95
  return pd.DataFrame()
96
 
97
- def create_score_chart(total_scores):
98
  """
99
- - total_scores๊ฐ€ ๋น„์—ˆ์„ ๊ฒฝ์šฐ 'No multiple entries found'๋ผ๋Š” ์ œ๋ชฉ์˜
100
- ๊ฐ„๋‹จํ•œ placeholder ์ฐจํŠธ๋ฅผ ๋ฐ˜ํ™˜ํ•˜์—ฌ, ์˜ค๋ฅธ์ชฝ ์ƒ๋‹จ ์˜์—ญ์ด ๋น„์–ด ์žˆ์ง€ ์•Š๋„๋ก ํ•จ.
101
- - ์ƒ์œ„ 10๊ฐœ๋งŒ ํ‘œ์‹œ (total_score ๊ธฐ์ค€ ๋‚ด๋ฆผ์ฐจ์ˆœ).
102
  """
103
  try:
104
- if total_scores.empty:
105
- # ์ค‘๋ณต๋œ ID ์ž์ฒด๊ฐ€ ์ „ํ˜€ ์—†๋Š” ๊ฒฝ์šฐ
106
  placeholder_df = pd.DataFrame({"id": ["No multiple entries"], "total_score": [0]})
107
  fig = px.bar(
108
  placeholder_df,
@@ -121,40 +177,17 @@ def create_score_chart(total_scores):
121
  )
122
  return fig
123
 
124
- # total_score ๊ธฐ์ค€์œผ๋กœ ๋‚ด๋ฆผ์ฐจ์ˆœ ์ •๋ ฌ ํ›„ ์ƒ์œ„ 10๊ฐœ๋งŒ ์ฐจํŠธ์— ํ‘œ์‹œ
125
- df = total_scores.reset_index().sort_values('total_score', ascending=False).head(10)
126
 
127
- if df.empty:
128
- # ์ค‘๋ณต๋œ ID๋Š” ์กด์žฌํ•˜์ง€๋งŒ ์Šค์ฝ”์–ด๊ฐ€ 0์ด๊ฑฐ๋‚˜ ๋“ฑ๋“ฑ, ์˜๋„์น˜ ์•Š๊ฒŒ ๋น„์—ˆ์„ ๊ฒฝ์šฐ ๋Œ€๋น„
129
- placeholder_df = pd.DataFrame({"id": ["No multiple entries"], "total_score": [0]})
130
- fig = px.bar(
131
- placeholder_df,
132
- x="total_score",
133
- y="id",
134
- orientation='h'
135
- )
136
- fig.update_layout(
137
- title="No multiple entries found in Top 100",
138
- xaxis_title="Total Trending Score",
139
- yaxis_title="Space ID",
140
- plot_bgcolor='white',
141
- paper_bgcolor='white',
142
- showlegend=False,
143
- margin=dict(l=200, r=20, t=40, b=40),
144
- )
145
- return fig
146
-
147
  fig = px.bar(
148
  df,
149
  y='id',
150
  x='total_score',
151
  orientation='h',
152
- title=f"Top 10 Spaces with Multiple Entries in Top 100",
153
  height=400,
154
- text=[
155
- f"Score: {score:.1f}\nEntries: {count}"
156
- for score, count in zip(df['total_score'], df['count'])
157
- ]
158
  )
159
 
160
  fig.update_layout(
@@ -182,6 +215,10 @@ def create_score_chart(total_scores):
182
  return None
183
 
184
  def update_display(selection):
 
 
 
 
185
  global daily_ranks_df
186
 
187
  if not selection:
@@ -219,58 +256,25 @@ def update_display(selection):
219
  print(f"Error in update_display: {e}")
220
  return None, gr.HTML(value=f"<div style='color: red;'>Error processing data: {str(e)}</div>")
221
 
222
- def load_and_process_data():
223
- try:
224
- url = "https://huggingface.co/datasets/cfahlgren1/hub-stats/resolve/main/spaces.parquet"
225
- response = requests.get(url)
226
- df = pd.read_parquet(BytesIO(response.content))
227
-
228
- thirty_days_ago = datetime.now() - timedelta(days=30)
229
- df['createdAt'] = pd.to_datetime(df['createdAt'])
230
- df = df[df['createdAt'] >= thirty_days_ago].copy()
231
-
232
- dates = pd.date_range(start=thirty_days_ago, end=datetime.now(), freq='D')
233
- daily_ranks = []
234
-
235
- for date in dates:
236
- date_data = df[df['createdAt'].dt.date <= date.date()].copy()
237
- date_data = date_data.sort_values(['trendingScore', 'id'], ascending=[False, True])
238
- date_data['rank'] = range(1, len(date_data) + 1)
239
- date_data['date'] = date.date()
240
- daily_ranks.append(
241
- date_data[['id', 'date', 'rank', 'trendingScore', 'createdAt']]
242
- )
243
-
244
- daily_ranks_df = pd.concat(daily_ranks, ignore_index=True)
245
-
246
- latest_date = daily_ranks_df['date'].max()
247
- top_100_spaces = daily_ranks_df[
248
- (daily_ranks_df['date'] == latest_date) &
249
- (daily_ranks_df['rank'] <= 100)
250
- ].sort_values('rank').copy()
251
-
252
- return daily_ranks_df, top_100_spaces
253
- except Exception as e:
254
- print(f"Error loading data: {e}")
255
- traceback.print_exc()
256
- return pd.DataFrame(), pd.DataFrame()
257
 
258
  # ๋ฐ์ดํ„ฐ ๋กœ๋“œ
259
  print("Loading initial data...")
260
  daily_ranks_df, top_100_spaces = load_and_process_data()
261
  print("Data loaded successfully!")
262
 
263
- # ์ด ์Šค์ฝ”์–ด ๋ถ„์„
264
- print("Analyzing total scores...")
265
- total_scores = get_total_scores(daily_ranks_df)
266
- score_chart = create_score_chart(total_scores) # <- ์—ฌ๊ธฐ์„œ ์ฐจํŠธ ์ƒ์„ฑ
267
 
268
  # Gradio ์ธํ„ฐํŽ˜์ด์Šค ์ƒ์„ฑ
269
  with gr.Blocks(theme=gr.themes.Soft()) as demo:
270
  gr.Markdown("""
271
  # HF Space Ranking Tracker
272
 
273
- Track, analyze, and discover trending AI applications in the Hugging Face ecosystem. Our service continuously monitors and ranks all Spaces over a 30-day period, providing detailed analytics and daily ranking changes for the top 100 performers.
 
 
274
  """)
275
 
276
  with gr.Tabs():
@@ -284,26 +288,27 @@ with gr.Blocks(theme=gr.themes.Soft()) as demo:
284
  )
285
  # ์˜ค๋ฅธ์ชฝ(Score Chart)
286
  with gr.Column(scale=3):
287
- # ์ด๋ฏธ ์ƒ์„ฑํ•œ score_chart๋ฅผ ๊ธฐ๋ณธ๊ฐ’์œผ๋กœ ๋„ฃ์–ด์คŒ
288
  score_plot = gr.Plot(
289
  value=score_chart,
290
- label="Multiple Entries Analysis (Top 10)",
291
  container=True
292
  )
293
 
 
294
  with gr.Row():
295
  info_box = gr.HTML(
296
  value="<div style='text-align: center; padding: 20px; color: #666;'>Select a space to view details</div>"
297
  )
298
 
299
- # ๋ผ๋””์˜ค ๋ฒ„ํŠผ์„ ๋จผ์ € ์ •์˜
300
  space_selection = gr.Radio(
301
  choices=[row['id'] for _, row in top_100_spaces.iterrows()],
302
  value=None,
303
  visible=False
304
  )
305
 
306
- # HTML์—์„œ JavaScript ์ด๋ฒคํŠธ๋ฅผ ์ง์ ‘ ์ฒ˜๋ฆฌ
307
  html_content = """
308
  <div style='display: flex; flex-wrap: wrap; gap: 16px; justify-content: center;'>
309
  """ + "".join([
@@ -391,12 +396,15 @@ with gr.Blocks(theme=gr.themes.Soft()) as demo:
391
  - Make data-driven decisions about your AI projects
392
  - Stay ahead of the curve in AI application development
393
 
394
- Our dashboard provides a comprehensive view of the Hugging Face Spaces ecosystem, helping developers, researchers, and enthusiasts track and understand the dynamics of popular AI applications. Whether you're monitoring your own Space's performance or discovering new trending applications, HF Space Ranking Tracker offers the insights you need.
 
 
395
 
396
- Experience the pulse of the AI community through our daily updated rankings and discover what's making waves in the world of practical AI applications.
 
397
  """)
398
 
399
- # ๋ผ๋””์˜ค ๋ฒ„ํŠผ ๋ณ€๊ฒฝ ์ด๋ฒคํŠธ ์—ฐ๊ฒฐ
400
  space_selection.change(
401
  fn=update_display,
402
  inputs=[space_selection],
@@ -406,4 +414,3 @@ with gr.Blocks(theme=gr.themes.Soft()) as demo:
406
 
407
  if __name__ == "__main__":
408
  demo.launch(share=True)
409
-
 
31
  xaxis_title="Date",
32
  yaxis_title="Rank",
33
  yaxis=dict(
34
+ range=[100, 1], # ๋žญํ‚น์ด 1์ด ์ตœ๊ณ ์ด๋ฏ€๋กœ y์ถ•์„ ๋’ค์ง‘์–ด์„œ ํ‘œ์‹œ
35
  tickmode='linear',
36
  tick0=1,
37
  dtick=10
 
54
 
55
  return fig
56
  except Exception as e:
57
+ print(f"Error creating trend chart: {e}")
58
+ traceback.print_exc()
59
  return None
60
 
61
+ def load_and_process_data():
62
+ """
63
+ 1) spaces.parquet๋ฅผ ๋‹ค์šด๋กœ๋“œํ•˜์—ฌ DataFrame์œผ๋กœ ๋ณ€ํ™˜
64
+ 2) ์ตœ๊ทผ 30์ผ์น˜ ๋ฐ์ดํ„ฐ๋งŒ ํ•„ํ„ฐ๋ง
65
+ 3) ๋งค ์ผ์ž๋ณ„๋กœ trendingScore ๋‚ด๋ฆผ์ฐจ์ˆœ์œผ๋กœ rank๋ฅผ ๋งค๊ธด ๋’ค, ๋ˆ„์ 
66
+ """
67
  try:
68
+ url = "https://huggingface.co/datasets/cfahlgren1/hub-stats/resolve/main/spaces.parquet"
69
+ response = requests.get(url)
70
+ df = pd.read_parquet(BytesIO(response.content))
71
+
72
+ # ์ตœ๊ทผ 30์ผ ๊ธฐ์ค€์œผ๋กœ ํ•„ํ„ฐ๋ง
73
+ thirty_days_ago = datetime.now() - timedelta(days=30)
74
+ df['createdAt'] = pd.to_datetime(df['createdAt'])
75
+ df = df[df['createdAt'] >= thirty_days_ago].copy()
76
+
77
+ # 30์ผ ๋™์•ˆ์˜ ๋ชจ๋“  ๋‚ ์งœ์— ๋Œ€ํ•ด
78
+ dates = pd.date_range(start=thirty_days_ago, end=datetime.now(), freq='D')
79
+ daily_ranks = []
80
+
81
+ for date in dates:
82
+ # date ๋‚ ์งœ๊นŒ์ง€ ์ƒ์„ฑ๋œ ์ŠคํŽ˜์ด์Šค๋งŒ ํ•„ํ„ฐ๋ง
83
+ date_data = df[df['createdAt'].dt.date <= date.date()].copy()
84
+ # trendingScore ๋†’์€ ์ˆœ, id ์˜ค๋ฆ„์ฐจ์ˆœ์œผ๋กœ ์ •๋ ฌ ํ›„ rank ๋ถ€์—ฌ
85
+ date_data = date_data.sort_values(['trendingScore', 'id'], ascending=[False, True])
86
+ date_data['rank'] = range(1, len(date_data) + 1)
87
+ date_data['date'] = date.date()
88
+
89
+ daily_ranks.append(
90
+ date_data[['id', 'date', 'rank', 'trendingScore', 'createdAt']]
91
+ )
92
 
93
+ # ํ•˜๋ฃจํ•˜๋ฃจ ์Œ“์ธ rank ๊ธฐ๋ก์„ ๋ชจ๋‘ ํ•ฉ์นจ
94
+ daily_ranks_df = pd.concat(daily_ranks, ignore_index=True)
95
+
96
+ # ์ตœ์‹  ๋‚ ์งœ์˜ Top100๋งŒ ๋ณ„๋„๋กœ ์ถ”์ถœ
97
+ latest_date = daily_ranks_df['date'].max()
98
+ top_100_spaces = daily_ranks_df[
99
  (daily_ranks_df['date'] == latest_date) &
100
  (daily_ranks_df['rank'] <= 100)
101
+ ].sort_values('rank').copy()
102
+
103
+ return daily_ranks_df, top_100_spaces
104
+ except Exception as e:
105
+ print(f"Error loading data: {e}")
106
+ traceback.print_exc()
107
+ return pd.DataFrame(), pd.DataFrame()
108
+
109
+ def get_top20_multiple_ids(daily_ranks_df):
110
+ """
111
+ '์ตœ์‹  ๋‚ ์งœ์˜ Top100'์—์„œ, ๋™์ผํ•œ id๊ฐ€ 2๊ฐœ ์ด์ƒ ๋“ฑ์žฅํ•˜๋Š” ๊ฒฝ์šฐ
112
+ ํ•ด๋‹น ์Šค์ฝ”์–ด๋ฅผ ํ•ฉ์‚ฐํ•˜์—ฌ, ํ•ฉ๊ณ„๊ฐ€ ๋†’์€ ์ˆœ์œผ๋กœ top 20๊นŒ์ง€๋งŒ ๋ฆฌํ„ดํ•˜๋Š” ํ•จ์ˆ˜
113
+ """
114
+ if daily_ranks_df.empty:
115
+ return pd.DataFrame()
116
+
117
+ try:
118
+ # ์ตœ์‹  ๋‚ ์งœ ํŒŒ์•…
119
+ latest_date = daily_ranks_df['date'].max()
120
+
121
+ # ์ตœ์‹  ๋‚ ์งœ์˜ Top100๋งŒ ํ•„ํ„ฐ๋ง
122
+ latest_top100 = daily_ranks_df[
123
+ (daily_ranks_df['date'] == latest_date) & (daily_ranks_df['rank'] <= 100)
124
  ].copy()
 
125
 
126
+ # id๋ณ„ ๋“ฑ์žฅ ํšŸ์ˆ˜ (Top100 ๋‚ด)
127
+ id_counts = latest_top100['id'].value_counts()
128
+ # 2๊ฐœ ์ด์ƒ ๋“ฑ์žฅํ•˜๋Š” id๋งŒ ์ถ”์ถœ
129
  multiple_ids = id_counts[id_counts >= 2].index
 
130
 
131
+ if len(multiple_ids) == 0:
132
+ # ์ค‘๋ณต id๊ฐ€ ์•„์˜ˆ ์—†๋Š” ๊ฒฝ์šฐ
133
+ return pd.DataFrame()
134
 
135
+ # ์ค‘๋ณต๋œ id์— ํ•ด๋‹นํ•˜๋Š” ํ–‰๋งŒ ๋ชจ์œผ๊ธฐ
136
+ multiple_entries = latest_top100[latest_top100['id'].isin(multiple_ids)].copy()
 
 
 
137
 
138
+ # id๋ณ„๋กœ score ํ•ฉ์‚ฐ
139
+ df_sum = (multiple_entries
140
+ .groupby('id')['trendingScore']
141
+ .sum()
142
+ .reset_index()
143
+ .rename(columns={'trendingScore': 'total_score'}))
144
 
145
+ # ํ•ฉ์‚ฐ๋œ total_score ์ˆœ์œผ๋กœ ๋‚ด๋ฆผ์ฐจ์ˆœ ์ •๋ ฌ ํ›„ ์ƒ์œ„ 20
146
+ df_sum = df_sum.sort_values(by='total_score', ascending=False).head(20)
147
 
148
+ return df_sum
149
  except Exception as e:
150
+ print(f"Error in get_top20_multiple_ids: {e}")
151
  traceback.print_exc()
152
  return pd.DataFrame()
153
 
154
+ def create_score_chart(multiple_ids_df):
155
  """
156
+ ์œ„์—์„œ ๋งŒ๋“  df_sum (id + total_score) ๋ฅผ ๊ฐ€์ง€๊ณ ,
157
+ id๋ณ„ total_score ๋ง‰๋Œ€ ์ฐจํŠธ๋ฅผ ์ƒ์„ฑ. ์ƒ์œ„ 20๊ฐœ๋งŒ ํ‘œ์‹œ.
 
158
  """
159
  try:
160
+ if multiple_ids_df.empty:
161
+ # ์ค‘๋ณต๋œ id ์ž์ฒด๊ฐ€ ํ•˜๋‚˜๋„ ์—†๋Š” ๊ฒฝ์šฐ(๋˜๋Š” ์ง‘๊ณ„๊ฒฐ๊ณผ ์—†์Œ)
162
  placeholder_df = pd.DataFrame({"id": ["No multiple entries"], "total_score": [0]})
163
  fig = px.bar(
164
  placeholder_df,
 
177
  )
178
  return fig
179
 
180
+ # ์—ฌ๊ธฐ์„œ multiple_ids_df์—๋Š” ์ด๋ฏธ ์ƒ์œ„ 20๊ฐœ๋งŒ ์žˆ๋Š” ์ƒํƒœ
181
+ df = multiple_ids_df.copy()
182
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
183
  fig = px.bar(
184
  df,
185
  y='id',
186
  x='total_score',
187
  orientation='h',
188
+ title=f"Top 20 IDs with Multiple Entries in Top 100",
189
  height=400,
190
+ text=[f"Score: {score:.2f}" for score in df['total_score']]
 
 
 
191
  )
192
 
193
  fig.update_layout(
 
215
  return None
216
 
217
  def update_display(selection):
218
+ """
219
+ ์‚ฌ์šฉ์ž๊ฐ€ ์™ผ์ชฝ/HTML ์นด๋“œ์—์„œ ํŠน์ • id๋ฅผ ์„ ํƒํ–ˆ์„ ๋•Œ,
220
+ ๊ทธ id์— ๋Œ€ํ•œ ์ผ๊ฐ„ Trend Chart + ์ƒ์„ธ ์ •๋ณด๋ฅผ ๋ฐ˜ํ™˜
221
+ """
222
  global daily_ranks_df
223
 
224
  if not selection:
 
256
  print(f"Error in update_display: {e}")
257
  return None, gr.HTML(value=f"<div style='color: red;'>Error processing data: {str(e)}</div>")
258
 
259
+ ########## ๋ฉ”์ธ ์‹คํ–‰ ##########
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
260
 
261
  # ๋ฐ์ดํ„ฐ ๋กœ๋“œ
262
  print("Loading initial data...")
263
  daily_ranks_df, top_100_spaces = load_and_process_data()
264
  print("Data loaded successfully!")
265
 
266
+ # '์ตœ์‹  ๋‚ ์งœ์˜ Top100' ์ค‘๋ณต ID ์ง‘๊ณ„ -> ์ƒ์œ„ 20
267
+ multiple_ids_df = get_top20_multiple_ids(daily_ranks_df)
268
+ score_chart = create_score_chart(multiple_ids_df)
 
269
 
270
  # Gradio ์ธํ„ฐํŽ˜์ด์Šค ์ƒ์„ฑ
271
  with gr.Blocks(theme=gr.themes.Soft()) as demo:
272
  gr.Markdown("""
273
  # HF Space Ranking Tracker
274
 
275
+ Track, analyze, and discover trending AI applications in the Hugging Face ecosystem.
276
+ Our service continuously monitors and ranks all Spaces over a 30-day period,
277
+ providing detailed analytics and daily ranking changes for the top 100 performers.
278
  """)
279
 
280
  with gr.Tabs():
 
288
  )
289
  # ์˜ค๋ฅธ์ชฝ(Score Chart)
290
  with gr.Column(scale=3):
291
+ # multiple_ids_df ๊ธฐ๋ฐ˜ ์ฐจํŠธ
292
  score_plot = gr.Plot(
293
  value=score_chart,
294
+ label="Multiple-Entry IDs (Top 20)",
295
  container=True
296
  )
297
 
298
+ # Space ์ƒ์„ธ ์ •๋ณด
299
  with gr.Row():
300
  info_box = gr.HTML(
301
  value="<div style='text-align: center; padding: 20px; color: #666;'>Select a space to view details</div>"
302
  )
303
 
304
+ # ๋ผ๋””์˜ค ๋ฒ„ํŠผ(๊ฐ€๋ ค๋†“๊ณ  HTML ๋ฒ„ํŠผ -> JS -> ๋ผ๋””์˜ค change ์ด๋ฒคํŠธ ํŠธ๋ฆฌ๊ฑฐ)
305
  space_selection = gr.Radio(
306
  choices=[row['id'] for _, row in top_100_spaces.iterrows()],
307
  value=None,
308
  visible=False
309
  )
310
 
311
+ # Top100 ๋ฆฌ์ŠคํŠธ๋ฅผ HTML ์นด๋“œ๋กœ ํ‘œ์‹œ (JS ๋กœ ํด๋ฆญ ์ด๋ฒคํŠธ -> ๋ผ๋””์˜ค ์„ ํƒ)
312
  html_content = """
313
  <div style='display: flex; flex-wrap: wrap; gap: 16px; justify-content: center;'>
314
  """ + "".join([
 
396
  - Make data-driven decisions about your AI projects
397
  - Stay ahead of the curve in AI application development
398
 
399
+ Our dashboard provides a comprehensive view of the Hugging Face Spaces ecosystem,
400
+ helping developers, researchers, and enthusiasts track and understand
401
+ the dynamics of popular AI applications.
402
 
403
+ Whether you're monitoring your own Space's performance or discovering new trending applications,
404
+ HF Space Ranking Tracker offers the insights you need.
405
  """)
406
 
407
+ # ๋ผ๋””์˜ค ๋ฒ„ํŠผ change ์ด๋ฒคํŠธ -> update_display ํ•จ์ˆ˜
408
  space_selection.change(
409
  fn=update_display,
410
  inputs=[space_selection],
 
414
 
415
  if __name__ == "__main__":
416
  demo.launch(share=True)