omniverse1 commited on
Commit
970d73a
ยท
verified ยท
1 Parent(s): db6d471

Update app.py

Browse files
Files changed (1) hide show
  1. app.py +62 -99
app.py CHANGED
@@ -75,22 +75,20 @@ def update_analysis(symbol, prediction_days):
75
 
76
  if not fundamental_info:
77
  return (
78
- "Unable to fetch stock data.",
79
- "No technical signals available.",
80
- "No prediction data available.",
81
  gr.Plot.update(value=None),
82
  gr.Plot.update(value=None),
83
  gr.Plot.update(value=None),
84
  )
85
 
86
  fundamentals = f"""
87
- <h4>COMPANY FUNDAMENTALS</h4>
88
- <b>Name:</b> {fundamental_info.get('name', 'N/A')} ({symbol.upper()})<br>
89
- <b>Current Price:</b> Rp{fundamental_info.get('current_price', 0):,.2f}<br>
90
- <b>Market Cap:</b> {fundamental_info.get('market_cap', 0):,}<br>
91
- <b>P/E Ratio:</b> {fundamental_info.get('pe_ratio', 0):.2f}<br>
92
- <b>Dividend Yield:</b> {fundamental_info.get('dividend_yield', 0):.2f}%<br>
93
- <b>Volume:</b> {fundamental_info.get('volume', 0):,}<br>
94
  """
95
 
96
  details_list = "".join(
@@ -98,127 +96,91 @@ def update_analysis(symbol, prediction_days):
98
  )
99
 
100
  trading_signal = f"""
101
- <h4>TECHNICAL SIGNAL SUMMARY</h4>
102
- <b>Overall Trend:</b> {signals.get('overall', 'N/A')}<br>
103
- <b>Signal Strength:</b> {signals.get('strength', 0):.2f}%<br>
104
- <b>Support:</b> Rp{signals.get('support', 0):,.2f}<br>
105
- <b>Resistance:</b> Rp{signals.get('resistance', 0):,.2f}<br>
106
- <b>Stop Loss:</b> Rp{signals.get('stop_loss', 0):,.2f}<br><br>
107
- <b>Detailed Signals:</b>
108
- <ul style="margin-top: 8px; padding-left: 20px; line-height: 1.6;">
109
- {details_list}
110
- </ul>
111
  """
112
 
113
  prediction = f"""
114
- <h4>30-DAY AI FORECAST (CHRONOS-BOLT)</h4>
115
- <b>Predicted High:</b> Rp{predictions.get('high_30d', 0):,.2f}<br>
116
- <b>Predicted Low:</b> Rp{predictions.get('low_30d', 0):,.2f}<br>
117
- <b>Expected Change:</b> {predictions.get('change_pct', 0):.2f}%<br><br>
118
- <b>TP1:</b> Rp{predictions.get('tp1', 0):,.2f}<br>
119
- <b>TP2:</b> Rp{predictions.get('tp2', 0):,.2f}<br>
120
- <b>Stop Loss:</b> Rp{predictions.get('sl', 0):,.2f}<br><br>
121
- <b>Model Insight:</b><br>{predictions.get('summary', 'No analysis available')}
 
 
 
 
 
 
 
 
 
 
 
122
  """
123
 
124
  return (
125
- f"""
126
- <div class='triple-panel'>
127
- <div class='panel-box'>{fundamentals}</div>
128
- <div class='panel-box'>{trading_signal}</div>
129
- <div class='panel-box'>{prediction}</div>
130
- </div>
131
- """,
132
  fig_price,
133
  fig_technical,
134
  fig_prediction,
135
  )
136
 
137
 
 
138
  with gr.Blocks(
139
- title="REXPRO FINANCIAL AI DASHBOARD",
140
  theme=gr.themes.Soft(primary_hue="blue", secondary_hue="gray"),
141
- css="""
142
- @import url('https://fonts.googleapis.com/css2?family=Inter:wght@400;500;600;700&display=swap');
143
- body {
144
- background-color: #f9fafb;
145
- color: #1e293b;
146
- font-family: 'Inter', 'Segoe UI', Arial, sans-serif;
147
- }
148
- h1 {
149
- color: #1e40af;
150
- text-align: center;
151
- font-weight: 700;
152
- letter-spacing: 0.5px;
153
- }
154
- h2, h3, h4 {
155
- color: #1e3a8a;
156
- font-weight: 600;
157
- margin-bottom: 6px;
158
- }
159
- .gr-button {
160
- background-color: #2563eb !important;
161
- color: white !important;
162
- font-weight: 600;
163
- border-radius: 8px;
164
- padding: 10px 18px;
165
- }
166
- .panel-box {
167
- background-color: #ffffff;
168
- border-radius: 10px;
169
- border: 1px solid #e2e8f0;
170
- padding: 16px;
171
- flex: 1;
172
- min-width: 30%;
173
- }
174
- .triple-panel {
175
- display: flex;
176
- flex-direction: row;
177
- justify-content: space-between;
178
- gap: 16px;
179
- width: 100%;
180
- }
181
- ul { margin: 0; padding: 0 0 0 18px; }
182
- li { margin-bottom: 4px; }
183
- .gr-plot {
184
- background-color: #ffffff;
185
- border: 1px solid #e2e8f0;
186
- border-radius: 10px;
187
- }
188
- """,
189
  ) as app:
190
- gr.Markdown("# REXPRO FINANCIAL AI DASHBOARD")
191
  gr.Markdown(
192
- "Comprehensive stock analytics powered by **AI forecasting and technical analysis.**"
 
 
 
193
  )
194
 
195
  with gr.Row():
196
  symbol = gr.Textbox(
197
- label="STOCK SYMBOL (IDX)",
198
  value="BBCA",
199
- placeholder="Example: BBCA, TLKM, ADRO, BMRI",
200
- interactive=True,
201
  )
202
  prediction_days = gr.Slider(
203
- label="FORECAST PERIOD (DAYS)",
204
  minimum=5,
205
  maximum=60,
206
  step=5,
207
  value=30,
208
- interactive=True,
209
  )
210
- analyze_button = gr.Button("RUN ANALYSIS")
211
 
212
  gr.Markdown("---")
213
- report_section = gr.HTML()
 
 
214
  gr.Markdown("---")
 
 
 
 
 
215
 
216
- with gr.Tab("MARKET CHARTS"):
217
- with gr.Row():
218
- price_chart = gr.Plot(label="PRICE & MOVING AVERAGES")
219
- technical_chart = gr.Plot(label="TECHNICAL INDICATORS OVERVIEW")
220
- gr.Markdown("---")
221
- prediction_chart = gr.Plot(label="AI FORECAST PROJECTION")
222
 
223
  analyze_button.click(
224
  fn=update_analysis,
@@ -226,5 +188,6 @@ with gr.Blocks(
226
  outputs=[report_section, price_chart, technical_chart, prediction_chart],
227
  )
228
 
 
229
  if __name__ == "__main__":
230
  app.launch(server_name="0.0.0.0", server_port=7860, ssr_mode=True)
 
75
 
76
  if not fundamental_info:
77
  return (
78
+ "โš ๏ธ Unable to fetch stock data.",
 
 
79
  gr.Plot.update(value=None),
80
  gr.Plot.update(value=None),
81
  gr.Plot.update(value=None),
82
  )
83
 
84
  fundamentals = f"""
85
+ ### ๐Ÿข Company Fundamentals
86
+ **Name:** {fundamental_info.get('name', 'N/A')} ({symbol.upper()})
87
+ **Current Price:** Rp{fundamental_info.get('current_price', 0):,.2f}
88
+ **Market Cap:** {fundamental_info.get('market_cap', 0):,}
89
+ **P/E Ratio:** {fundamental_info.get('pe_ratio', 0):.2f}
90
+ **Dividend Yield:** {fundamental_info.get('dividend_yield', 0):.2f}%
91
+ **Volume:** {fundamental_info.get('volume', 0):,}
92
  """
93
 
94
  details_list = "".join(
 
96
  )
97
 
98
  trading_signal = f"""
99
+ ### ๐Ÿ“Š Technical Signal Summary
100
+ **Overall Trend:** {signals.get('overall', 'N/A')}
101
+ **Signal Strength:** {signals.get('strength', 0):.2f}%
102
+ **Support:** Rp{signals.get('support', 0):,.2f}
103
+ **Resistance:** Rp{signals.get('resistance', 0):,.2f}
104
+ **Stop Loss:** Rp{signals.get('stop_loss', 0):,.2f}
105
+
106
+ **Detailed Signals:**
107
+ <ul style="margin-top:6px; padding-left:20px;">{details_list}</ul>
 
108
  """
109
 
110
  prediction = f"""
111
+ ### ๐Ÿค– 30-Day AI Forecast (Chronos-Bolt)
112
+ **Predicted High:** Rp{predictions.get('high_30d', 0):,.2f}
113
+ **Predicted Low:** Rp{predictions.get('low_30d', 0):,.2f}
114
+ **Expected Change:** {predictions.get('change_pct', 0):.2f}%
115
+
116
+ **TP1:** Rp{predictions.get('tp1', 0):,.2f}
117
+ **TP2:** Rp{predictions.get('tp2', 0):,.2f}
118
+ **Stop Loss:** Rp{predictions.get('sl', 0):,.2f}
119
+
120
+ **Model Insight:**
121
+ {predictions.get('summary', 'No analysis available')}
122
+ """
123
+
124
+ combined = f"""
125
+ <div style="display:flex;flex-wrap:wrap;gap:12px;justify-content:space-between;">
126
+ <div style="flex:1;min-width:300px;background-color:white;border-radius:8px;padding:12px;border:1px solid #e5e7eb;">{fundamentals}</div>
127
+ <div style="flex:1;min-width:300px;background-color:white;border-radius:8px;padding:12px;border:1px solid #e5e7eb;">{trading_signal}</div>
128
+ <div style="flex:1;min-width:300px;background-color:white;border-radius:8px;padding:12px;border:1px solid #e5e7eb;">{prediction}</div>
129
+ </div>
130
  """
131
 
132
  return (
133
+ combined,
 
 
 
 
 
 
134
  fig_price,
135
  fig_technical,
136
  fig_prediction,
137
  )
138
 
139
 
140
+ # ---------------------- UI ----------------------
141
  with gr.Blocks(
142
+ title="REXPRO Financial AI Dashboard",
143
  theme=gr.themes.Soft(primary_hue="blue", secondary_hue="gray"),
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
144
  ) as app:
145
+
146
  gr.Markdown(
147
+ """
148
+ # ๐Ÿ’น REXPRO Financial AI Dashboard
149
+ Analyze **Indonesian stocks (IDX)** using AI-powered forecasting and technical indicators.
150
+ """
151
  )
152
 
153
  with gr.Row():
154
  symbol = gr.Textbox(
155
+ label="Stock Symbol (IDX)",
156
  value="BBCA",
157
+ placeholder="e.g., BBCA, TLKM, ADRO, BMRI",
 
158
  )
159
  prediction_days = gr.Slider(
160
+ label="Forecast Period (Days)",
161
  minimum=5,
162
  maximum=60,
163
  step=5,
164
  value=30,
 
165
  )
166
+ analyze_button = gr.Button("๐Ÿ” Run Analysis", variant="primary")
167
 
168
  gr.Markdown("---")
169
+
170
+ report_section = gr.HTML(label="Analysis Summary")
171
+
172
  gr.Markdown("---")
173
+ gr.Markdown("### ๐Ÿ“ˆ Market Charts")
174
+
175
+ with gr.Tabs():
176
+ with gr.Tab("Price Overview"):
177
+ price_chart = gr.Plot(label="Price & Moving Averages")
178
 
179
+ with gr.Tab("Technical Indicators"):
180
+ technical_chart = gr.Plot(label="Technical Indicator Overview")
181
+
182
+ with gr.Tab("AI Forecast"):
183
+ prediction_chart = gr.Plot(label="AI Forecast Projection")
 
184
 
185
  analyze_button.click(
186
  fn=update_analysis,
 
188
  outputs=[report_section, price_chart, technical_chart, prediction_chart],
189
  )
190
 
191
+
192
  if __name__ == "__main__":
193
  app.launch(server_name="0.0.0.0", server_port=7860, ssr_mode=True)