Update app.py
Browse files
app.py
CHANGED
|
@@ -1,6 +1,6 @@
|
|
| 1 |
# -*- coding: utf-8 -*-
|
| 2 |
"""
|
| 3 |
-
AI λ΄μ€ & νκΉ
νμ΄μ€ νΈλ λ© LLM λΆμ μΉμ± (μμ ν v3.
|
| 4 |
νμΌλͺ
: app_advanced.py
|
| 5 |
|
| 6 |
μ£Όμ κΈ°λ₯:
|
|
@@ -8,7 +8,7 @@ AI λ΄μ€ & νκΉ
νμ΄μ€ νΈλ λ© LLM λΆμ μΉμ± (μμ ν v3.3)
|
|
| 8 |
2. AI Times μ€μκ° λ΄μ€ ν¬λ‘€λ§ (2κ° μΉμ
)
|
| 9 |
3. μ€μ Hugging Face Trending API μ°λ (λͺ¨λΈ/μ€νμ΄μ€ 30μ)
|
| 10 |
4. Fireworks AI (Qwen3-235B) μ€μκ° LLM λΆμ
|
| 11 |
-
- λ΄μ€
|
| 12 |
- λͺ¨λΈ μΉ΄λ μλ λΆμ (README.md)
|
| 13 |
- μ€νμ΄μ€ μ½λ μλ λΆμ (app.py)
|
| 14 |
5. ν UI (λ΄μ€/λͺ¨λΈ/μ€νμ΄μ€)
|
|
@@ -545,7 +545,7 @@ HTML_TEMPLATE = """
|
|
| 545 |
<body>
|
| 546 |
<div class="container">
|
| 547 |
<h1>π€ AI λ΄μ€ & νκΉ
νμ΄μ€ LLM λΆμ</h1>
|
| 548 |
-
<p class="subtitle"
|
| 549 |
|
| 550 |
<!-- ν΅κ³ μΉ΄λ -->
|
| 551 |
<div class="stats">
|
|
@@ -676,7 +676,7 @@ HTML_TEMPLATE = """
|
|
| 676 |
</div>
|
| 677 |
|
| 678 |
<div class="space-analysis">
|
| 679 |
-
<strong>π
|
| 680 |
{{ space.simple_explanation }}
|
| 681 |
</div>
|
| 682 |
|
|
@@ -722,12 +722,12 @@ HTML_TEMPLATE = """
|
|
| 722 |
|
| 723 |
<!-- νΈν° -->
|
| 724 |
<div class="footer">
|
| 725 |
-
<p>π€ AI λ΄μ€ LLM λΆμ μμ€ν
v3.
|
| 726 |
<p style="margin-top: 10px; font-size: 0.9em;">
|
| 727 |
πΎ SQLite DB μꡬ μ μ₯ | π AI Times μ€μκ° ν¬λ‘€λ§ | π€ Hugging Face Trending API | π§ Powered by Fireworks AI (Qwen3-235B)
|
| 728 |
</p>
|
| 729 |
<p style="margin-top: 10px; font-size: 0.85em; color: #999;">
|
| 730 |
-
λ°μ΄ν° μΆμ²: AI Times (μ€μκ° ν¬λ‘€λ§), Hugging Face | μ€μκ° λΆμ: Fireworks AI
|
| 731 |
</p>
|
| 732 |
</div>
|
| 733 |
</div>
|
|
@@ -1096,32 +1096,32 @@ class LLMAnalyzer:
|
|
| 1096 |
return None
|
| 1097 |
|
| 1098 |
def analyze_news_simple(self, title: str, content: str = "") -> Dict:
|
| 1099 |
-
"""λ΄μ€ κΈ°μ¬λ₯Ό
|
| 1100 |
|
| 1101 |
analysis_templates = {
|
| 1102 |
"μ±GPT": {
|
| 1103 |
-
"summary": "λ§μ΄ν¬λ‘μννΈ(MS)
|
| 1104 |
-
"significance": "
|
| 1105 |
"impact_level": "high",
|
| 1106 |
"impact_text": "λμ",
|
| 1107 |
-
"impact_description": "
|
| 1108 |
-
"action": "μ±GPT
|
| 1109 |
},
|
| 1110 |
"GPU": {
|
| 1111 |
-
"summary": "
|
| 1112 |
-
"significance": "
|
| 1113 |
"impact_level": "medium",
|
| 1114 |
"impact_text": "μ€κ°",
|
| 1115 |
-
"impact_description": "AI
|
| 1116 |
-
"action": "
|
| 1117 |
},
|
| 1118 |
"μλΌ": {
|
| 1119 |
-
"summary": "μ€νAI
|
| 1120 |
-
"significance": "
|
| 1121 |
"impact_level": "high",
|
| 1122 |
"impact_text": "λμ",
|
| 1123 |
-
"impact_description": "
|
| 1124 |
-
"action": "
|
| 1125 |
}
|
| 1126 |
}
|
| 1127 |
|
|
@@ -1130,18 +1130,18 @@ class LLMAnalyzer:
|
|
| 1130 |
if keyword.lower() in title.lower():
|
| 1131 |
return template
|
| 1132 |
|
| 1133 |
-
# κΈ°λ³Έ λΆμ
|
| 1134 |
return {
|
| 1135 |
-
"summary": f"'{title}'
|
| 1136 |
-
"significance": "AI
|
| 1137 |
"impact_level": "medium",
|
| 1138 |
"impact_text": "μ€κ°",
|
| 1139 |
-
"impact_description": "AI κΈ°μ μ λ°μ μ
|
| 1140 |
-
"action": "AI
|
| 1141 |
}
|
| 1142 |
|
| 1143 |
def analyze_model(self, model_name: str, task: str, downloads: int) -> str:
|
| 1144 |
-
"""νκΉ
νμ΄μ€ λͺ¨λΈ λΆμ - λͺ¨λΈ μΉ΄λλ₯Ό LLMμΌλ‘
|
| 1145 |
|
| 1146 |
# 1. λͺ¨λΈ μΉ΄λ κ°μ Έμ€κΈ°
|
| 1147 |
model_card = self.fetch_model_card(model_name)
|
|
@@ -1152,7 +1152,7 @@ class LLMAnalyzer:
|
|
| 1152 |
messages = [
|
| 1153 |
{
|
| 1154 |
"role": "system",
|
| 1155 |
-
"content": "λΉμ μ
|
| 1156 |
},
|
| 1157 |
{
|
| 1158 |
"role": "user",
|
|
@@ -1160,12 +1160,12 @@ class LLMAnalyzer:
|
|
| 1160 |
|
| 1161 |
{model_card}
|
| 1162 |
|
| 1163 |
-
μ΄ λͺ¨λΈμ
|
| 1164 |
-
1. μ΄ λͺ¨λΈμ΄ 무μμ νλμ§
|
| 1165 |
-
2. μ΄λ€
|
| 1166 |
-
3.
|
| 1167 |
|
| 1168 |
-
|
| 1169 |
}
|
| 1170 |
]
|
| 1171 |
|
|
@@ -1177,31 +1177,31 @@ class LLMAnalyzer:
|
|
| 1177 |
except Exception as e:
|
| 1178 |
print(f" β οΈ λͺ¨λΈ λΆμ LLM μ€λ₯: {e}")
|
| 1179 |
|
| 1180 |
-
# 3. Fallback: ν
νλ¦Ώ κΈ°λ° μ€λͺ
|
| 1181 |
task_explanations = {
|
| 1182 |
-
"text-generation": "
|
| 1183 |
-
"image-to-text": "
|
| 1184 |
-
"text-to-image": "
|
| 1185 |
-
"translation": "
|
| 1186 |
-
"question-answering": "
|
| 1187 |
-
"summarization": "κΈ΄
|
| 1188 |
-
"text-classification": "
|
| 1189 |
-
"token-classification": "
|
| 1190 |
-
"fill-mask": "
|
| 1191 |
}
|
| 1192 |
|
| 1193 |
-
task_desc = task_explanations.get(task, "
|
| 1194 |
|
| 1195 |
if downloads > 10000000:
|
| 1196 |
-
popularity = "
|
| 1197 |
elif downloads > 1000000:
|
| 1198 |
-
popularity = "
|
| 1199 |
elif downloads > 100000:
|
| 1200 |
-
popularity = "
|
| 1201 |
else:
|
| 1202 |
-
popularity = "
|
| 1203 |
|
| 1204 |
-
return f"μ΄ λͺ¨λΈμ {task_desc}
|
| 1205 |
|
| 1206 |
def analyze_space(self, space_name: str, space_id: str, description: str) -> Dict:
|
| 1207 |
"""νκΉ
νμ΄μ€ μ€νμ΄μ€ λΆμ - app.pyλ₯Ό LLMμΌλ‘ λΆμ"""
|
|
@@ -1215,7 +1215,7 @@ class LLMAnalyzer:
|
|
| 1215 |
messages = [
|
| 1216 |
{
|
| 1217 |
"role": "system",
|
| 1218 |
-
"content": "λΉμ μ
|
| 1219 |
},
|
| 1220 |
{
|
| 1221 |
"role": "user",
|
|
@@ -1223,12 +1223,12 @@ class LLMAnalyzer:
|
|
| 1223 |
|
| 1224 |
{app_code}
|
| 1225 |
|
| 1226 |
-
μ΄ μ±μ
|
| 1227 |
-
1. μ΄ μ±μ΄
|
| 1228 |
-
2. μ΄λ€
|
| 1229 |
-
3.
|
| 1230 |
|
| 1231 |
-
|
| 1232 |
}
|
| 1233 |
]
|
| 1234 |
|
|
@@ -1261,9 +1261,9 @@ class LLMAnalyzer:
|
|
| 1261 |
except Exception as e:
|
| 1262 |
print(f" β οΈ μ€νμ΄μ€ λΆμ LLM μ€λ₯: {e}")
|
| 1263 |
|
| 1264 |
-
# 3. Fallback: ν
νλ¦Ώ κΈ°λ° μ€λͺ
|
| 1265 |
return {
|
| 1266 |
-
"simple_explanation": f"{space_name}λ
|
| 1267 |
"tech_stack": ["Python", "Gradio", "Transformers", "PyTorch"]
|
| 1268 |
}
|
| 1269 |
|
|
@@ -1287,13 +1287,14 @@ class AdvancedAIAnalyzer:
|
|
| 1287 |
"""AI Timesμμ μ€λ λ μ§ λ΄μ€ ν¬λ‘€λ§"""
|
| 1288 |
print("π° AI Times λ΄μ€ μμ§ μ€...")
|
| 1289 |
|
|
|
|
| 1290 |
urls = [
|
| 1291 |
'https://www.aitimes.com/news/articleList.html?sc_multi_code=S2&view_type=sm',
|
| 1292 |
'https://www.aitimes.com/news/articleList.html?sc_section_code=S1N24&view_type=sm'
|
| 1293 |
]
|
| 1294 |
|
| 1295 |
all_news = []
|
| 1296 |
-
today = datetime.now().strftime('%m-%d')
|
| 1297 |
|
| 1298 |
for url_idx, url in enumerate(urls, 1):
|
| 1299 |
try:
|
|
@@ -1304,28 +1305,54 @@ class AdvancedAIAnalyzer:
|
|
| 1304 |
response.raise_for_status()
|
| 1305 |
response.encoding = 'utf-8'
|
| 1306 |
|
| 1307 |
-
|
| 1308 |
|
| 1309 |
-
#
|
| 1310 |
-
|
| 1311 |
-
|
|
|
|
| 1312 |
|
| 1313 |
articles_found = 0
|
| 1314 |
-
for
|
| 1315 |
try:
|
| 1316 |
-
|
| 1317 |
-
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 1318 |
|
| 1319 |
-
|
|
|
|
| 1320 |
continue
|
| 1321 |
|
| 1322 |
-
# λ μ§ μ°ΎκΈ°
|
| 1323 |
-
|
| 1324 |
-
|
| 1325 |
-
|
| 1326 |
-
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 1327 |
|
| 1328 |
-
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 1329 |
|
| 1330 |
# μ€λ λ μ§λ§ νν°λ§
|
| 1331 |
if today not in date_text:
|
|
@@ -1341,19 +1368,20 @@ class AdvancedAIAnalyzer:
|
|
| 1341 |
|
| 1342 |
all_news.append(news_item)
|
| 1343 |
articles_found += 1
|
|
|
|
| 1344 |
print(f" β μΆκ°: {title[:60]}... ({date_text})")
|
| 1345 |
|
| 1346 |
except Exception as e:
|
| 1347 |
continue
|
| 1348 |
|
| 1349 |
-
print(f" β {articles_found}κ° μ€λμ κΈ°μ¬
|
| 1350 |
-
time.sleep(1)
|
| 1351 |
|
| 1352 |
except Exception as e:
|
| 1353 |
print(f" β οΈ URL μμ§ μ€λ₯: {e}\n")
|
| 1354 |
continue
|
| 1355 |
|
| 1356 |
-
# μ€λ³΅ μ κ±°
|
| 1357 |
unique_news = []
|
| 1358 |
seen_urls = set()
|
| 1359 |
for news in all_news:
|
|
@@ -1363,7 +1391,7 @@ class AdvancedAIAnalyzer:
|
|
| 1363 |
|
| 1364 |
print(f"β
μ΄ {len(unique_news)}κ° μ€λ³΅ μ κ±°λ μ€λμ λ΄μ€\n")
|
| 1365 |
|
| 1366 |
-
# μ΅μ 3
|
| 1367 |
if len(unique_news) < 3:
|
| 1368 |
print("β οΈ λ΄μ€κ° λΆμ‘±νμ¬ μ΅κ·Ό μν μΆκ°\n")
|
| 1369 |
sample_news = [
|
|
@@ -1393,7 +1421,7 @@ class AdvancedAIAnalyzer:
|
|
| 1393 |
if sample['url'] not in seen_urls:
|
| 1394 |
unique_news.append(sample)
|
| 1395 |
|
| 1396 |
-
return unique_news[:20]
|
| 1397 |
|
| 1398 |
def fetch_huggingface_models(self, limit: int = 30) -> List[Dict]:
|
| 1399 |
"""νκΉ
νμ΄μ€ νΈλ λ© λͺ¨λΈ 30κ° μμ§ (μ€μ API)"""
|
|
@@ -1713,7 +1741,7 @@ def health():
|
|
| 1713 |
return jsonify({
|
| 1714 |
"status": "healthy",
|
| 1715 |
"service": "AI News LLM Analyzer",
|
| 1716 |
-
"version": "3.
|
| 1717 |
"database": {
|
| 1718 |
"connected": True,
|
| 1719 |
"news_count": news_count,
|
|
@@ -1742,14 +1770,14 @@ if __name__ == '__main__':
|
|
| 1742 |
print(f"""
|
| 1743 |
ββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ
|
| 1744 |
β β
|
| 1745 |
-
β π€ AI λ΄μ€ & νκΉ
νμ΄μ€ LLM λΆμ μΉμ± v3.
|
| 1746 |
β β
|
| 1747 |
ββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ
|
| 1748 |
|
| 1749 |
β¨ μ£Όμ κΈ°λ₯:
|
| 1750 |
β’ πΎ SQLite DB μꡬ μ€ν 리μ§
|
| 1751 |
β’ π AI Times μ€μκ° λ΄μ€ ν¬λ‘€λ§ (2κ° μΉμ
)
|
| 1752 |
-
β’ π° λ΄μ€
|
| 1753 |
β’ π€ νκΉ
νμ΄μ€ νΈλ λ© λͺ¨λΈ TOP 30 (λͺ¨λΈ μΉ΄λ λΆμ)
|
| 1754 |
β’ π νκΉ
νμ΄μ€ νΈλ λ© μ€νμ΄μ€ TOP 30 (app.py λΆμ)
|
| 1755 |
β’ π§ Fireworks AI (Qwen3-235B) μ€μκ° LLM λΆμ
|
|
|
|
| 1 |
# -*- coding: utf-8 -*-
|
| 2 |
"""
|
| 3 |
+
AI λ΄μ€ & νκΉ
νμ΄μ€ νΈλ λ© LLM λΆμ μΉμ± (μμ ν v3.2)
|
| 4 |
νμΌλͺ
: app_advanced.py
|
| 5 |
|
| 6 |
μ£Όμ κΈ°λ₯:
|
|
|
|
| 8 |
2. AI Times μ€μκ° λ΄μ€ ν¬λ‘€λ§ (2κ° μΉμ
)
|
| 9 |
3. μ€μ Hugging Face Trending API μ°λ (λͺ¨λΈ/μ€νμ΄μ€ 30μ)
|
| 10 |
4. Fireworks AI (Qwen3-235B) μ€μκ° LLM λΆμ
|
| 11 |
+
- λ΄μ€ μ΄λ±νμ μμ€ λΆμ
|
| 12 |
- λͺ¨λΈ μΉ΄λ μλ λΆμ (README.md)
|
| 13 |
- μ€νμ΄μ€ μ½λ μλ λΆμ (app.py)
|
| 14 |
5. ν UI (λ΄μ€/λͺ¨λΈ/μ€νμ΄μ€)
|
|
|
|
| 545 |
<body>
|
| 546 |
<div class="container">
|
| 547 |
<h1>π€ AI λ΄μ€ & νκΉ
νμ΄μ€ LLM λΆμ</h1>
|
| 548 |
+
<p class="subtitle">μ΄λ±νμλ μ΄ν΄νλ AI νΈλ λ λΆμ μμ€ν
π</p>
|
| 549 |
|
| 550 |
<!-- ν΅κ³ μΉ΄λ -->
|
| 551 |
<div class="stats">
|
|
|
|
| 676 |
</div>
|
| 677 |
|
| 678 |
<div class="space-analysis">
|
| 679 |
+
<strong>π μ΄λ±νμ μ€λͺ
:</strong><br>
|
| 680 |
{{ space.simple_explanation }}
|
| 681 |
</div>
|
| 682 |
|
|
|
|
| 722 |
|
| 723 |
<!-- νΈν° -->
|
| 724 |
<div class="footer">
|
| 725 |
+
<p>π€ AI λ΄μ€ LLM λΆμ μμ€ν
v3.2</p>
|
| 726 |
<p style="margin-top: 10px; font-size: 0.9em;">
|
| 727 |
πΎ SQLite DB μꡬ μ μ₯ | π AI Times μ€μκ° ν¬λ‘€λ§ | π€ Hugging Face Trending API | π§ Powered by Fireworks AI (Qwen3-235B)
|
| 728 |
</p>
|
| 729 |
<p style="margin-top: 10px; font-size: 0.85em; color: #999;">
|
| 730 |
+
λ°μ΄ν° μΆμ²: AI Times (μ€μκ° ν¬λ‘€λ§), Hugging Face | μ€μκ° λΆμ: Fireworks AI
|
| 731 |
</p>
|
| 732 |
</div>
|
| 733 |
</div>
|
|
|
|
| 1096 |
return None
|
| 1097 |
|
| 1098 |
def analyze_news_simple(self, title: str, content: str = "") -> Dict:
|
| 1099 |
+
"""λ΄μ€ κΈ°μ¬λ₯Ό μ΄λ±νμ μμ€μΌλ‘ λΆμ"""
|
| 1100 |
|
| 1101 |
analysis_templates = {
|
| 1102 |
"μ±GPT": {
|
| 1103 |
+
"summary": "λ§μ΄ν¬λ‘μννΈ(MS)λΌλ ν° νμ¬κ° μ±GPTλΌλ AIλ₯Ό λ무 λ§μ μ¬λλ€μ΄ μ¬μ©ν΄μ, μ»΄ν¨ν°λ₯Ό 보κ΄νλ ν° κ±΄λ¬Ό(λ°μ΄ν°μΌν°)μ΄ λΆμ‘±νλ€κ³ λ§νμ΄μ.",
|
| 1104 |
+
"significance": "μ±GPTκ° μ λ§ μΈκΈ°κ° λ§λ€λ λ»μ΄μμ. λ§μΉ λ무 λ§μ μΉκ΅¬λ€μ΄ ν κ²μκΈ°λ₯Ό μ°λ €κ³ νλ κ²κ³Ό λΉμ·ν΄μ.",
|
| 1105 |
"impact_level": "high",
|
| 1106 |
"impact_text": "λμ",
|
| 1107 |
+
"impact_description": "AI κΈ°μ μ΄ λΉ λ₯΄κ² λ°μ νκ³ μκ³ , λ§μ μ¬λλ€μ΄ μ¬μ©νκ³ μλ€λ μ€μν μ νΈμμ.",
|
| 1108 |
+
"action": "μ±GPT κ°μ AI λꡬλ₯Ό λ°°μ보μΈμ. μμ λ₯Ό λμλ¬λΌκ³ νκ±°λ, λͺ¨λ₯΄λ κ²μ λ¬Όμ΄λ³Ό μ μμ΄μ!"
|
| 1109 |
},
|
| 1110 |
"GPU": {
|
| 1111 |
+
"summary": "λ―Έκ΅μ΄ μλμ미리νΈ(UAE)λΌλ λλΌμ GPUλΌλ νΉλ³ν μ»΄ν¨ν° λΆνμ ν μ μκ² νλ½νμ΄μ. GPUλ AIλ₯Ό λ§λλ λ° κΌ νμν λΆνμ΄μμ.",
|
| 1112 |
+
"significance": "GPUλ AIμ λλ κ°μ κ±°μμ. μ΄κ±Έ ν μ μκ² λλ©΄ λ λ§μ λλΌμμ AIλ₯Ό λ§λ€ μ μμ΄μ.",
|
| 1113 |
"impact_level": "medium",
|
| 1114 |
"impact_text": "μ€κ°",
|
| 1115 |
+
"impact_description": "AI κΈ°μ μ΄ λ λ§μ λλΌλ‘ νΌμ§ μ μκ² λμμ΄μ.",
|
| 1116 |
+
"action": "μ»΄ν¨ν°κ° μ΄λ»κ² μλνλμ§ κ΄μ¬μ κ°μ Έλ³΄μΈμ. GPUκ° λ¬΄μμΈμ§ κ²μν΄λ³΄λ κ²λ μ’μμ!"
|
| 1117 |
},
|
| 1118 |
"μλΌ": {
|
| 1119 |
+
"summary": "μ€νAIκ° λ§λ 'μλΌ'λΌλ AI μ±μ΄ μμ² λΉ λ₯΄κ² μΈκΈ°λ₯Ό μ»μμ΄μ. 100λ§ λͺ
μ΄ λ€μ΄λ‘λνλ λ° μ±GPTλ³΄λ€ λ λΉ¨λλμ!",
|
| 1120 |
+
"significance": "μ¬λλ€μ΄ λΉλμ€λ₯Ό λ§λλ AIμ μ λ§ κ΄μ¬μ΄ λ§λ€λ λ»μ΄μμ.",
|
| 1121 |
"impact_level": "high",
|
| 1122 |
"impact_text": "λμ",
|
| 1123 |
+
"impact_description": "μμΌλ‘ λꡬλ μ½κ² λ©μ§ λΉλμ€λ₯Ό λ§λ€ μ μκ² λ κ±°μμ.",
|
| 1124 |
+
"action": "μλΌλ₯Ό μ¨λ³΄κ³ , μμν κ²μ λΉλμ€λ‘ λ§λ€μ΄λ³΄μΈμ. μ°½μλ ₯μ λ°νν μ μμ΄μ!"
|
| 1125 |
}
|
| 1126 |
}
|
| 1127 |
|
|
|
|
| 1130 |
if keyword.lower() in title.lower():
|
| 1131 |
return template
|
| 1132 |
|
| 1133 |
+
# κΈ°λ³Έ λΆμ
|
| 1134 |
return {
|
| 1135 |
+
"summary": f"'{title}'λΌλ AI κ΄λ ¨ λ΄μ€κ° λμμ΄μ. AI κΈ°μ μ΄ κ³μ λ°μ νκ³ μλ€λ μμμ΄μμ.",
|
| 1136 |
+
"significance": "AIλ μ°λ¦¬ μνμ λ νΈλ¦¬νκ² λ§λ€μ΄μ£Όλ κΈ°μ μ΄μμ.",
|
| 1137 |
"impact_level": "medium",
|
| 1138 |
"impact_text": "μ€κ°",
|
| 1139 |
+
"impact_description": "AI κΈ°μ μ λ°μ μ μ°λ¦¬ λ―Έλμ μ€μν μν₯μ μ€ κ±°μμ.",
|
| 1140 |
+
"action": "AIμ λν΄ λ μμλ³΄κ³ , AIλ₯Ό νμ©νλ λ°©λ²μ λ°°μ보μΈμ!"
|
| 1141 |
}
|
| 1142 |
|
| 1143 |
def analyze_model(self, model_name: str, task: str, downloads: int) -> str:
|
| 1144 |
+
"""νκΉ
νμ΄μ€ λͺ¨λΈ λΆμ - λͺ¨λΈ μΉ΄λλ₯Ό LLMμΌλ‘ λΆμ"""
|
| 1145 |
|
| 1146 |
# 1. λͺ¨λΈ μΉ΄λ κ°μ Έμ€κΈ°
|
| 1147 |
model_card = self.fetch_model_card(model_name)
|
|
|
|
| 1152 |
messages = [
|
| 1153 |
{
|
| 1154 |
"role": "system",
|
| 1155 |
+
"content": "λΉμ μ μ΄λ±νμλ μ΄ν΄ν μ μκ² AI λͺ¨λΈμ μ½κ² μ€λͺ
νλ μ λ¬Έκ°μ
λλ€. νκ΅μ΄λ‘ λ΅λ³νμΈμ."
|
| 1156 |
},
|
| 1157 |
{
|
| 1158 |
"role": "user",
|
|
|
|
| 1160 |
|
| 1161 |
{model_card}
|
| 1162 |
|
| 1163 |
+
μ΄ λͺ¨λΈμ μ΄λ±νμμ΄ μ΄ν΄ν μ μλλ‘ 3-4λ¬Έμ₯μΌλ‘ μ½κ² μ€λͺ
ν΄μ£ΌμΈμ. λ€μ λ΄μ©μ ν¬ν¨νμΈμ:
|
| 1164 |
+
1. μ΄ λͺ¨λΈμ΄ 무μμ νλμ§
|
| 1165 |
+
2. μ΄λ€ νΉμ§μ΄ μλμ§
|
| 1166 |
+
3. λκ° μ¬μ©νλ©΄ μ’μμ§
|
| 1167 |
|
| 1168 |
+
λ΅λ³μ λ°λμ 3-4λ¬Έμ₯μ νκ΅μ΄λ‘λ§ μμ±νμΈμ."""
|
| 1169 |
}
|
| 1170 |
]
|
| 1171 |
|
|
|
|
| 1177 |
except Exception as e:
|
| 1178 |
print(f" β οΈ λͺ¨λΈ λΆμ LLM μ€λ₯: {e}")
|
| 1179 |
|
| 1180 |
+
# 3. Fallback: ν
νλ¦Ώ κΈ°λ° μ€λͺ
|
| 1181 |
task_explanations = {
|
| 1182 |
+
"text-generation": "κΈμ μλμΌλ‘ λ§λ€μ΄μ£Όλ",
|
| 1183 |
+
"image-to-text": "μ¬μ§μ λ³΄κ³ μ€λͺ
μ μ¨μ£Όλ",
|
| 1184 |
+
"text-to-image": "κΈμ μ½κ³ κ·Έλ¦Όμ κ·Έλ €μ£Όλ",
|
| 1185 |
+
"translation": "λ€λ₯Έ μΈμ΄λ‘ λ²μν΄μ£Όλ",
|
| 1186 |
+
"question-answering": "μ§λ¬Έμ λ΅ν΄μ£Όλ",
|
| 1187 |
+
"summarization": "κΈ΄ κΈμ μ§§κ² μμ½ν΄μ£Όλ",
|
| 1188 |
+
"text-classification": "κΈμ λΆλ₯ν΄μ£Όλ",
|
| 1189 |
+
"token-classification": "λ¨μ΄λ₯Ό λΆμν΄μ£Όλ",
|
| 1190 |
+
"fill-mask": "λΉμΉΈμ μ±μμ£Όλ"
|
| 1191 |
}
|
| 1192 |
|
| 1193 |
+
task_desc = task_explanations.get(task, "νΉλ³ν κΈ°λ₯μ νλ")
|
| 1194 |
|
| 1195 |
if downloads > 10000000:
|
| 1196 |
+
popularity = "μμ²λκ² λ§μ"
|
| 1197 |
elif downloads > 1000000:
|
| 1198 |
+
popularity = "μμ£Ό λ§μ"
|
| 1199 |
elif downloads > 100000:
|
| 1200 |
+
popularity = "λ§μ"
|
| 1201 |
else:
|
| 1202 |
+
popularity = "μ΄λ μ λ"
|
| 1203 |
|
| 1204 |
+
return f"μ΄ λͺ¨λΈμ {task_desc} AIμμ. {popularity} μ¬λλ€μ΄ λ€μ΄λ‘λν΄μ μ¬μ©νκ³ μμ΄μ. {model_name.split('/')[-1]}λΌλ μ΄λ¦μΌλ‘ μ λͺ
ν΄μ!"
|
| 1205 |
|
| 1206 |
def analyze_space(self, space_name: str, space_id: str, description: str) -> Dict:
|
| 1207 |
"""νκΉ
νμ΄μ€ μ€νμ΄μ€ λΆμ - app.pyλ₯Ό LLMμΌλ‘ λΆμ"""
|
|
|
|
| 1215 |
messages = [
|
| 1216 |
{
|
| 1217 |
"role": "system",
|
| 1218 |
+
"content": "λΉμ μ μ΄λ±νμλ μ΄ν΄ν μ μκ² AI μ ν리μΌμ΄μ
μ μ½κ² μ€λͺ
νλ μ λ¬Έκ°μ
λλ€. νκ΅μ΄λ‘ λ΅λ³νμΈμ."
|
| 1219 |
},
|
| 1220 |
{
|
| 1221 |
"role": "user",
|
|
|
|
| 1223 |
|
| 1224 |
{app_code}
|
| 1225 |
|
| 1226 |
+
μ΄ μ±μ μ΄λ±νμμ΄ μ΄ν΄ν μ μλλ‘ 3-4λ¬Έμ₯μΌλ‘ μ½κ² μ€λͺ
ν΄μ£ΌμΈμ. λ€μ λ΄μ©μ ν¬ν¨νμΈμ:
|
| 1227 |
+
1. μ΄ μ±μ΄ 무μμ νλμ§
|
| 1228 |
+
2. μ΄λ€ κΈ°μ μ μ¬μ©νλμ§
|
| 1229 |
+
3. μ΄λ»κ² νμ©ν μ μλμ§
|
| 1230 |
|
| 1231 |
+
λ΅λ³μ λ°λμ 3-4λ¬Έμ₯μ νκ΅μ΄λ‘λ§ μμ±νμΈμ."""
|
| 1232 |
}
|
| 1233 |
]
|
| 1234 |
|
|
|
|
| 1261 |
except Exception as e:
|
| 1262 |
print(f" β οΈ μ€νμ΄μ€ λΆμ LLM μ€λ₯: {e}")
|
| 1263 |
|
| 1264 |
+
# 3. Fallback: ν
νλ¦Ώ κΈ°λ° μ€λͺ
|
| 1265 |
return {
|
| 1266 |
+
"simple_explanation": f"{space_name}λ μΉλΈλΌμ°μ μμ λ°λ‘ AIλ₯Ό 체νν΄λ³Ό μ μλ κ³³μ΄μμ. μ€μΉ μμ΄λ μ¬μ©ν μ μμ΄μ νΈλ¦¬ν΄μ! λ§μΉ μ¨λΌμΈ κ²μμ²λΌ λ°λ‘ μ μν΄μ AIλ₯Ό μ¬μ©ν μ μλ΅λλ€.",
|
| 1267 |
"tech_stack": ["Python", "Gradio", "Transformers", "PyTorch"]
|
| 1268 |
}
|
| 1269 |
|
|
|
|
| 1287 |
"""AI Timesμμ μ€λ λ μ§ λ΄μ€ ν¬λ‘€λ§"""
|
| 1288 |
print("π° AI Times λ΄μ€ μμ§ μ€...")
|
| 1289 |
|
| 1290 |
+
# μμ§ν URL λͺ©λ‘
|
| 1291 |
urls = [
|
| 1292 |
'https://www.aitimes.com/news/articleList.html?sc_multi_code=S2&view_type=sm',
|
| 1293 |
'https://www.aitimes.com/news/articleList.html?sc_section_code=S1N24&view_type=sm'
|
| 1294 |
]
|
| 1295 |
|
| 1296 |
all_news = []
|
| 1297 |
+
today = datetime.now().strftime('%m-%d') # μ: '10-10'
|
| 1298 |
|
| 1299 |
for url_idx, url in enumerate(urls, 1):
|
| 1300 |
try:
|
|
|
|
| 1305 |
response.raise_for_status()
|
| 1306 |
response.encoding = 'utf-8'
|
| 1307 |
|
| 1308 |
+
soup = BeautifulSoup(response.text, 'html.parser')
|
| 1309 |
|
| 1310 |
+
# λͺ¨λ λ§ν¬ μ°ΎκΈ°
|
| 1311 |
+
articles = soup.find_all('a', href=re.compile(r'/news/articleView\.html\?idxno=\d+'))
|
| 1312 |
+
|
| 1313 |
+
print(f" β {len(articles)}κ° λ§ν¬ λ°κ²¬")
|
| 1314 |
|
| 1315 |
articles_found = 0
|
| 1316 |
+
for article_tag in articles:
|
| 1317 |
try:
|
| 1318 |
+
# μ λͺ©κ³Ό λ§ν¬
|
| 1319 |
+
title = article_tag.get_text(strip=True)
|
| 1320 |
+
link = article_tag.get('href', '')
|
| 1321 |
+
|
| 1322 |
+
# λ§ν¬ μ κ·ν
|
| 1323 |
+
if link and not link.startswith('http'):
|
| 1324 |
+
if link.startswith('/'):
|
| 1325 |
+
link = 'https://www.aitimes.com' + link
|
| 1326 |
+
else:
|
| 1327 |
+
link = 'https://www.aitimes.com/' + link
|
| 1328 |
|
| 1329 |
+
# μ λͺ©μ΄ λ무 μ§§μΌλ©΄ μ€ν΅
|
| 1330 |
+
if not title or len(title) < 10:
|
| 1331 |
continue
|
| 1332 |
|
| 1333 |
+
# λΆλͺ¨ μμμμ λ μ§ μ°ΎκΈ°
|
| 1334 |
+
parent = article_tag.parent
|
| 1335 |
+
date_text = ''
|
| 1336 |
+
|
| 1337 |
+
# λΆλͺ¨μ λͺ¨λ ν
μ€νΈμμ λ μ§ ν¨ν΄ μ°ΎκΈ°
|
| 1338 |
+
if parent:
|
| 1339 |
+
parent_text = parent.get_text()
|
| 1340 |
+
date_match = re.search(r'(\d{2}-\d{2}\s+\d{2}:\d{2})', parent_text)
|
| 1341 |
+
if date_match:
|
| 1342 |
+
date_text = date_match.group(1)
|
| 1343 |
|
| 1344 |
+
# λ μ§κ° μμΌλ©΄ λ€μ νμ μμλ€ νμΈ
|
| 1345 |
+
if not date_text:
|
| 1346 |
+
for sibling in article_tag.find_next_siblings():
|
| 1347 |
+
sibling_text = sibling.get_text()
|
| 1348 |
+
date_match = re.search(r'(\d{2}-\d{2}\s+\d{2}:\d{2})', sibling_text)
|
| 1349 |
+
if date_match:
|
| 1350 |
+
date_text = date_match.group(1)
|
| 1351 |
+
break
|
| 1352 |
+
|
| 1353 |
+
# λ μ§κ° μ¬μ ν μμΌλ©΄ μ€λ λ μ§ μ¬μ©
|
| 1354 |
+
if not date_text:
|
| 1355 |
+
date_text = today
|
| 1356 |
|
| 1357 |
# μ€λ λ μ§λ§ νν°λ§
|
| 1358 |
if today not in date_text:
|
|
|
|
| 1368 |
|
| 1369 |
all_news.append(news_item)
|
| 1370 |
articles_found += 1
|
| 1371 |
+
|
| 1372 |
print(f" β μΆκ°: {title[:60]}... ({date_text})")
|
| 1373 |
|
| 1374 |
except Exception as e:
|
| 1375 |
continue
|
| 1376 |
|
| 1377 |
+
print(f" β {articles_found}κ° μ€λμ κΈ°μ¬ μμ§\n")
|
| 1378 |
+
time.sleep(1) # μλ² λΆν λ°©μ§
|
| 1379 |
|
| 1380 |
except Exception as e:
|
| 1381 |
print(f" β οΈ URL μμ§ μ€λ₯: {e}\n")
|
| 1382 |
continue
|
| 1383 |
|
| 1384 |
+
# μ€λ³΅ μ κ±° (URL κΈ°μ€)
|
| 1385 |
unique_news = []
|
| 1386 |
seen_urls = set()
|
| 1387 |
for news in all_news:
|
|
|
|
| 1391 |
|
| 1392 |
print(f"β
μ΄ {len(unique_news)}κ° μ€λ³΅ μ κ±°λ μ€λμ λ΄μ€\n")
|
| 1393 |
|
| 1394 |
+
# μ΅μ 3κ°λ 보μ₯ (μμΌλ©΄ μν μΆκ°)
|
| 1395 |
if len(unique_news) < 3:
|
| 1396 |
print("β οΈ λ΄μ€κ° λΆμ‘±νμ¬ μ΅κ·Ό μν μΆκ°\n")
|
| 1397 |
sample_news = [
|
|
|
|
| 1421 |
if sample['url'] not in seen_urls:
|
| 1422 |
unique_news.append(sample)
|
| 1423 |
|
| 1424 |
+
return unique_news[:20] # μ΅λ 20κ°
|
| 1425 |
|
| 1426 |
def fetch_huggingface_models(self, limit: int = 30) -> List[Dict]:
|
| 1427 |
"""νκΉ
νμ΄μ€ νΈλ λ© λͺ¨λΈ 30κ° μμ§ (μ€μ API)"""
|
|
|
|
| 1741 |
return jsonify({
|
| 1742 |
"status": "healthy",
|
| 1743 |
"service": "AI News LLM Analyzer",
|
| 1744 |
+
"version": "3.2.0",
|
| 1745 |
"database": {
|
| 1746 |
"connected": True,
|
| 1747 |
"news_count": news_count,
|
|
|
|
| 1770 |
print(f"""
|
| 1771 |
ββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ
|
| 1772 |
β β
|
| 1773 |
+
β π€ AI λ΄μ€ & νκΉ
νμ΄μ€ LLM λΆμ μΉμ± v3.2 β
|
| 1774 |
β β
|
| 1775 |
ββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββββ
|
| 1776 |
|
| 1777 |
β¨ μ£Όμ κΈ°λ₯:
|
| 1778 |
β’ πΎ SQLite DB μꡬ μ€ν 리μ§
|
| 1779 |
β’ π AI Times μ€μκ° λ΄μ€ ν¬λ‘€λ§ (2κ° μΉμ
)
|
| 1780 |
+
β’ π° λ΄μ€ μ΄λ±νμ μμ€ λΆμ
|
| 1781 |
β’ π€ νκΉ
νμ΄μ€ νΈλ λ© λͺ¨λΈ TOP 30 (λͺ¨λΈ μΉ΄λ λΆμ)
|
| 1782 |
β’ π νκΉ
νμ΄μ€ νΈλ λ© μ€νμ΄μ€ TOP 30 (app.py λΆμ)
|
| 1783 |
β’ π§ Fireworks AI (Qwen3-235B) μ€μκ° LLM λΆμ
|