Update app.py
Browse files
app.py
CHANGED
@@ -1,142 +1,43 @@
|
|
|
|
1 |
import subprocess
|
2 |
-
|
3 |
-
# ํ์ํ ๋ผ์ด๋ธ๋ฌ๋ฆฌ ์ค์น ๋ฐ ์
๋ฐ์ดํธ
|
4 |
-
subprocess.run(["pip", "install", "--upgrade", "pip"])
|
5 |
-
subprocess.run(["pip", "install", "--upgrade", "openai", "yfinance", "gradio", "matplotlib", "Pillow"])
|
6 |
-
|
7 |
-
import os
|
8 |
import matplotlib.font_manager as fm
|
9 |
import matplotlib.pyplot as plt
|
10 |
-
import yfinance as yf
|
11 |
-
import numpy as np
|
12 |
-
import re # ํ๊ธ, ์ซ์, ๊ธฐํธ๋ฅผ ๋จ๊ธฐ๊ธฐ ์ํ ์ ๊ท ํํ์์ ์ฌ์ฉ
|
13 |
import gradio as gr
|
14 |
import io
|
15 |
from PIL import Image
|
16 |
from datetime import datetime, timedelta
|
17 |
-
|
18 |
-
|
19 |
-
# 1. ๋๋๊ณ ๋ ํฐํธ ์ค์น ๋ฐ ์ ์ฉ
|
20 |
-
def install_nanum_font():
|
21 |
-
try:
|
22 |
-
subprocess.run(["apt-get", "update"], check=True)
|
23 |
-
subprocess.run(["apt-get", "install", "-y", "fonts-nanum"], check=True)
|
24 |
-
subprocess.run(["fc-cache", "-fv"], check=True)
|
25 |
-
except Exception as e:
|
26 |
-
print(f"ํฐํธ ์ค์น ์ค ์ค๋ฅ๊ฐ ๋ฐ์ํ์ต๋๋ค: {e}")
|
27 |
-
|
28 |
-
install_nanum_font()
|
29 |
-
|
30 |
-
# ๋๋๊ณ ๋ ํฐํธ ๊ฒฝ๋ก ์ค์ ๋ฐ ๊ฐ์ ์ ์ฉ
|
31 |
-
font_path = '/usr/share/fonts/truetype/nanum/NanumGothic.ttf'
|
32 |
-
|
33 |
-
if os.path.exists(font_path):
|
34 |
-
fm.fontManager.addfont(font_path)
|
35 |
-
else:
|
36 |
-
print("ํฐํธ๋ฅผ ์ฐพ์ ์ ์์ต๋๋ค.")
|
37 |
-
|
38 |
-
# ๋๋๊ณ ๋ ํฐํธ ๊ฐ์ ์ ์ฉ
|
39 |
-
font_prop = fm.FontProperties(fname=font_path)
|
40 |
-
plt.rcParams['font.family'] = font_prop.get_name()
|
41 |
-
plt.rcParams['axes.unicode_minus'] = False # ๋ง์ด๋์ค ๋ถํธ ๊นจ์ง ๋ฐฉ์ง
|
42 |
-
|
43 |
-
# 2. yfinance๋ก ์ฃผ๊ฐ ๋ฐ์ดํฐ ๊ฐ์ ธ์ค๊ธฐ (์ผ์ฑ์ ์ ์์)
|
44 |
-
ticker = '005930.KS' # ์ผ์ฑ์ ์ ํฐ์ปค
|
45 |
-
stock = yf.Ticker(ticker)
|
46 |
-
stock_data = stock.history(period="max")
|
47 |
-
|
48 |
-
# ์ฃผ๊ฐ ๋ฐ์ดํฐ ์ถ๋ ฅ ํ์ธ
|
49 |
-
print(stock_data.head()) # ์ฃผ๊ฐ ๋ฐ์ดํฐ ์ผ๋ถ ํ์ธ
|
50 |
-
|
51 |
-
# 3. ์ฃผ๊ฐ ๋ฐ์ดํฐ ์๊ฐํ (pandas ๋ฐ์ดํฐํ๋ ์์ numpy ๋ฐฐ์ด๋ก ๋ณํํ์ฌ ์ฒ๋ฆฌ)
|
52 |
-
plt.figure(figsize=(10, 6))
|
53 |
-
|
54 |
-
# ์ธ๋ฑ์ค์ ์ข
๊ฐ ๋ฐ์ดํฐ๋ฅผ numpy ๋ฐฐ์ด๋ก ๋ณํ
|
55 |
-
dates = stock_data.index.to_numpy()
|
56 |
-
closing_prices = stock_data['Close'].to_numpy()
|
57 |
-
|
58 |
-
# ์ฃผ๊ฐ ๋ฐ์ดํฐ ์๊ฐํ
|
59 |
-
plt.plot(dates, closing_prices, label='์ผ์ฑ์ ์ ์ข
๊ฐ')
|
60 |
-
|
61 |
-
# ๊ทธ๋ํ ์ ๋ชฉ, ์ถ ๋ผ๋ฒจ์ ํ๊ธ๋ก ์ค์
|
62 |
-
plt.title('์ผ์ฑ์ ์ ์ฃผ๊ฐ ์ถ์ด', fontproperties=font_prop)
|
63 |
-
plt.xlabel('๋ ์ง', fontproperties=font_prop)
|
64 |
-
plt.ylabel('์ข
๊ฐ', fontproperties=font_prop)
|
65 |
-
plt.legend(prop=font_prop)
|
66 |
|
67 |
-
#
|
|
|
|
|
68 |
|
69 |
# Perplexity AI API ์ค์
|
70 |
API_KEY = "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" # ์ฌ๊ธฐ์ Perplexity AI API ํค๋ฅผ ์
๋ ฅํ์ธ์.
|
71 |
|
72 |
-
#
|
73 |
-
def
|
74 |
-
#
|
75 |
-
|
76 |
-
|
77 |
-
|
78 |
-
target_date = datetime.strptime(date, '%Y-%m-%d')
|
79 |
-
start_date = (target_date - timedelta(days=1)).strftime('%Y-%m-%d')
|
80 |
-
end_date = (target_date + timedelta(days=1)).strftime('%Y-%m-%d')
|
81 |
-
|
82 |
-
# API ์์ฒญ์ ์ํ ๋ฉ์์ง ๊ตฌ์ฑ - ํ๊ตญ์ด๋ก๋ง ์๋ต์ ๋ฐ๋๋ก ์ง์
|
83 |
-
messages = [
|
84 |
-
{"role": "system", "content": "You are a helpful assistant that summarizes stock news strictly in Korean."},
|
85 |
-
{"role": "user", "content": f"Summarize the stock news for {company} between {start_date} and {end_date} in Korean. Only focus on news within this date range."}
|
86 |
-
]
|
87 |
-
|
88 |
-
try:
|
89 |
-
# API ์์ฒญ
|
90 |
-
response = client.chat.completions.create(
|
91 |
-
model="llama-3.1-sonar-large-128k-online",
|
92 |
-
messages=messages
|
93 |
-
)
|
94 |
-
|
95 |
-
# ์๋ต์์ ์์ฝ ์ถ์ถ
|
96 |
-
summary = response.choices[0].message.content
|
97 |
|
98 |
-
|
99 |
-
|
|
|
|
|
100 |
|
101 |
-
|
102 |
-
|
|
|
103 |
|
104 |
-
|
105 |
-
except Exception as e:
|
106 |
-
return f"๋ด์ค ์์ฝ ์ค ์๋ฌ๊ฐ ๋ฐ์ํ์ต๋๋ค: {str(e)}"
|
107 |
-
|
108 |
-
# ๋ด์ค ์์ฝ์ ๊ฐ์ ธ์ค๋ ํจ์
|
109 |
-
def handle_click(company_name, date_clicked):
|
110 |
-
return get_real_news_summary(company_name, date_clicked)
|
111 |
-
|
112 |
-
# Gradio์์ ์ฌ์ฉํ ํจ์ (๋ด์ค ์์ฝ ํฌํจ)
|
113 |
-
def update_news(input_value, selected_date):
|
114 |
-
if selected_date == "" or selected_date is None:
|
115 |
-
return "๋ ์ง๋ฅผ ์ ํํด์ฃผ์ธ์."
|
116 |
-
else:
|
117 |
-
# ์ข
๋ชฉ๋ช
์ ๊ฐ์ ธ์์ Perplexity๋ก ๊ฒ์
|
118 |
-
ticker = name_to_ticker.get(input_value, input_value)
|
119 |
-
company_name = input_value if ticker == input_value else list(name_to_ticker.keys())[list(name_to_ticker.values()).index(ticker)]
|
120 |
-
return handle_click(company_name, selected_date)
|
121 |
|
122 |
# ์ข
๋ชฉ๋ช
๊ณผ ํฐ์ปค๋ฅผ ๋งคํํ๋ ๋์
๋๋ฆฌ ํ์ฅ ๋ฐ ์กฐ๊ฑด๋ณ ์ข
๋ชฉ ๋งคํ
|
123 |
name_to_ticker = {
|
124 |
-
"์ผ์ฑ์ ์": "005930.KS",
|
125 |
-
"SK๋ฐ์ด์คํ": "326030.KS",
|
126 |
-
"Apple": "AAPL",
|
127 |
-
"Nvidia": "NVDA",
|
128 |
-
"Vertex": "VRTX",
|
129 |
-
"ํ๋์ฐจ": "005380.KS",
|
130 |
-
"์นด์นด์ค": "035720.KS",
|
131 |
-
"LGํํ": "051910.KS",
|
132 |
-
"์
ํธ๋ฆฌ์จ": "068270.KS",
|
133 |
-
"๋ค์ด๋ฒ": "035420.KS",
|
134 |
-
"์์ฝํ๋ก๋น์ ": "247540.KS",
|
135 |
-
"์ํ
์ค์ ": "196170.KQ",
|
136 |
-
# ์ต์ ์๊ฐ์ด์ก ์์ ์ข
๋ชฉ์ ๋ฐ์ํ์ฌ ์
๋ฐ์ดํธ
|
137 |
"๋์ค๋ฅ ์์ด 1์": "AAPL", # Apple
|
138 |
"๋์ค๋ฅ ๋ฐ์ด์คํ
์์ด 1์": "VRTX", # Vertex Pharmaceuticals
|
139 |
-
"๋์ค๋ฅ
|
140 |
"์ฝ์คํผ ์์ด 1์": "005930.KS", # ์ผ์ฑ์ ์
|
141 |
"์ฝ์ค๋ฅ ์์ด 1์": "196170.KQ", # ์ํ
์ค์
|
142 |
}
|
@@ -153,7 +54,6 @@ def display_stock_with_highlight(input_value, change_type, percent_change):
|
|
153 |
return "์ฃผ๊ฐ ๋ฐ์ดํฐ๋ฅผ ์ฐพ์ ์ ์์ต๋๋ค.", []
|
154 |
|
155 |
stock_data['Change'] = stock_data['Close'].pct_change() * 100
|
156 |
-
|
157 |
percent_change = float(percent_change)
|
158 |
|
159 |
if change_type == "์์น":
|
@@ -176,11 +76,9 @@ def display_stock_with_highlight(input_value, change_type, percent_change):
|
|
176 |
plt.text(index, row['Close'], index.strftime('%Y-%m-%d'), fontsize=10, fontweight='bold', color=color, ha='right')
|
177 |
plt.axvline(x=index, color=color, linestyle='--', linewidth=1) # x์ถ๊ณผ์ ์ฐ๊ฒฐ์ ์ ์ ์ผ๋ก ํ์
|
178 |
|
179 |
-
|
180 |
-
|
181 |
-
plt.
|
182 |
-
plt.xlabel('๋ ์ง', fontproperties=font_prop)
|
183 |
-
plt.ylabel('์ข
๊ฐ', fontproperties=font_prop)
|
184 |
plt.legend()
|
185 |
|
186 |
buf = io.BytesIO()
|
@@ -210,8 +108,8 @@ with gr.Blocks() as demo:
|
|
210 |
# ์์ (์ด์ ๋ ์ด์์์ผ๋ก ๋ณต์)
|
211 |
examples = [["SK๋ฐ์ด์คํ"],
|
212 |
["๋์ค๋ฅ ์์ด 1์"],
|
213 |
-
["๋์ค๋ฅ ์ ์ฝ์ฃผ ์์ด 1์"],
|
214 |
["๋์ค๋ฅ ๋ฐ์ด์คํ
์์ด 1์"],
|
|
|
215 |
["์ฝ์คํผ ์์ด 1์"],
|
216 |
["์ฝ์ค๋ฅ ์์ด 1์"]]
|
217 |
gr.Examples(examples=examples, inputs=[input_value])
|
@@ -221,7 +119,6 @@ with gr.Blocks() as demo:
|
|
221 |
date_dropdown = gr.Dropdown(label="์กฐ๊ฑด์ ํด๋นํ๋ ๋ ์ง ์ ํ", choices=[])
|
222 |
|
223 |
with gr.Column(): # ๋ด์ค ์์ฝ์ ์ถ๋ ฅํ ์ธ ๋ฒ์งธ ์ด
|
224 |
-
# news_output์ gr.Markdown์ผ๋ก ๋ณ๊ฒฝ
|
225 |
news_output = gr.Markdown(label="๋ด์ค ์์ฝ", value="") # ๋น ์นธ์ผ๋ก ๊ธฐ๋ณธ ํ์
|
226 |
|
227 |
# Submit ๋ฒํผ ํด๋ฆญ ์ ๊ทธ๋ํ ๋ฐ ๋ ์ง ๋๋กญ๋ค์ด ์
๋ฐ์ดํธ
|
|
|
1 |
+
import yfinance as yf
|
2 |
import subprocess
|
|
|
|
|
|
|
|
|
|
|
|
|
3 |
import matplotlib.font_manager as fm
|
4 |
import matplotlib.pyplot as plt
|
|
|
|
|
|
|
5 |
import gradio as gr
|
6 |
import io
|
7 |
from PIL import Image
|
8 |
from datetime import datetime, timedelta
|
9 |
+
import os
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
10 |
|
11 |
+
# ํ์ํ ๋ผ์ด๋ธ๋ฌ๋ฆฌ ์ค์น ๋ฐ ์
๋ฐ์ดํธ
|
12 |
+
subprocess.run(["pip", "install", "--upgrade", "pip"])
|
13 |
+
subprocess.run(["pip", "install", "--upgrade", "openai", "yfinance", "gradio", "matplotlib", "Pillow"])
|
14 |
|
15 |
# Perplexity AI API ์ค์
|
16 |
API_KEY = "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" # ์ฌ๊ธฐ์ Perplexity AI API ํค๋ฅผ ์
๋ ฅํ์ธ์.
|
17 |
|
18 |
+
# yfinance๋ก ๋์ค๋ฅ ํฌ์ค์ผ์ด ์์ด 1์ ์ข
๋ชฉ ๊ฐ์ ธ์ค๊ธฐ
|
19 |
+
def get_nasdaq_healthcare_leader():
|
20 |
+
# ํฌ์ค์ผ์ด ์นํฐ ์์ ๊ธฐ์
๋ค์ ๊ฐ์ ธ์ด
|
21 |
+
healthcare_tickers = ["JNJ", "PFE", "MRNA", "VRTX", "AMGN"] # ์์๋ก ๋์ค๋ฅ ํฌ์ค์ผ์ด ์์ ํฐ์ปค๋ค
|
22 |
+
largest_market_cap = 0
|
23 |
+
leader_ticker = ""
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
24 |
|
25 |
+
for ticker in healthcare_tickers:
|
26 |
+
stock = yf.Ticker(ticker)
|
27 |
+
stock_data = stock.history(period="1d") # ์ ์ผ ์ข
๊ฐ ๊ธฐ์ค
|
28 |
+
market_cap = stock.info.get('marketCap', 0)
|
29 |
|
30 |
+
if market_cap > largest_market_cap:
|
31 |
+
largest_market_cap = market_cap
|
32 |
+
leader_ticker = ticker
|
33 |
|
34 |
+
return leader_ticker
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
35 |
|
36 |
# ์ข
๋ชฉ๋ช
๊ณผ ํฐ์ปค๋ฅผ ๋งคํํ๋ ๋์
๋๋ฆฌ ํ์ฅ ๋ฐ ์กฐ๊ฑด๋ณ ์ข
๋ชฉ ๋งคํ
|
37 |
name_to_ticker = {
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
38 |
"๋์ค๋ฅ ์์ด 1์": "AAPL", # Apple
|
39 |
"๋์ค๋ฅ ๋ฐ์ด์คํ
์์ด 1์": "VRTX", # Vertex Pharmaceuticals
|
40 |
+
"๋์ค๋ฅ ํฌ์ค์ผ์ด ์์ด 1์": get_nasdaq_healthcare_leader(), # yfinance๋ก ๋์ ์ผ๋ก ์ค์
|
41 |
"์ฝ์คํผ ์์ด 1์": "005930.KS", # ์ผ์ฑ์ ์
|
42 |
"์ฝ์ค๋ฅ ์์ด 1์": "196170.KQ", # ์ํ
์ค์
|
43 |
}
|
|
|
54 |
return "์ฃผ๊ฐ ๋ฐ์ดํฐ๋ฅผ ์ฐพ์ ์ ์์ต๋๋ค.", []
|
55 |
|
56 |
stock_data['Change'] = stock_data['Close'].pct_change() * 100
|
|
|
57 |
percent_change = float(percent_change)
|
58 |
|
59 |
if change_type == "์์น":
|
|
|
76 |
plt.text(index, row['Close'], index.strftime('%Y-%m-%d'), fontsize=10, fontweight='bold', color=color, ha='right')
|
77 |
plt.axvline(x=index, color=color, linestyle='--', linewidth=1) # x์ถ๊ณผ์ ์ฐ๊ฒฐ์ ์ ์ ์ผ๋ก ํ์
|
78 |
|
79 |
+
plt.title(f'{input_value} ์ฃผ๊ฐ ์ถ์ด')
|
80 |
+
plt.xlabel('๋ ์ง')
|
81 |
+
plt.ylabel('์ข
๊ฐ')
|
|
|
|
|
82 |
plt.legend()
|
83 |
|
84 |
buf = io.BytesIO()
|
|
|
108 |
# ์์ (์ด์ ๋ ์ด์์์ผ๋ก ๋ณต์)
|
109 |
examples = [["SK๋ฐ์ด์คํ"],
|
110 |
["๋์ค๋ฅ ์์ด 1์"],
|
|
|
111 |
["๋์ค๋ฅ ๋ฐ์ด์คํ
์์ด 1์"],
|
112 |
+
["๋์ค๋ฅ ํฌ์ค์ผ์ด ์์ด 1์"], # ์์ ๋ ์์
|
113 |
["์ฝ์คํผ ์์ด 1์"],
|
114 |
["์ฝ์ค๋ฅ ์์ด 1์"]]
|
115 |
gr.Examples(examples=examples, inputs=[input_value])
|
|
|
119 |
date_dropdown = gr.Dropdown(label="์กฐ๊ฑด์ ํด๋นํ๋ ๋ ์ง ์ ํ", choices=[])
|
120 |
|
121 |
with gr.Column(): # ๋ด์ค ์์ฝ์ ์ถ๋ ฅํ ์ธ ๋ฒ์งธ ์ด
|
|
|
122 |
news_output = gr.Markdown(label="๋ด์ค ์์ฝ", value="") # ๋น ์นธ์ผ๋ก ๊ธฐ๋ณธ ํ์
|
123 |
|
124 |
# Submit ๋ฒํผ ํด๋ฆญ ์ ๊ทธ๋ํ ๋ฐ ๋ ์ง ๋๋กญ๋ค์ด ์
๋ฐ์ดํธ
|