Spaces:
Sleeping
Sleeping
Update app.py
Browse files
app.py
CHANGED
|
@@ -28,19 +28,49 @@ ALPHA_VANTAGE_API_KEY = "JK0DVDNTEYBTBP5L"
|
|
| 28 |
# Custom CSS
|
| 29 |
st.markdown("""
|
| 30 |
<style>
|
| 31 |
-
.reportview-container
|
| 32 |
-
|
|
|
|
|
|
|
|
|
|
| 33 |
padding-top: 2rem;
|
| 34 |
padding-bottom: 2rem;
|
| 35 |
}
|
| 36 |
-
|
| 37 |
-
|
| 38 |
-
padding-bottom: 1rem;
|
| 39 |
}
|
| 40 |
.stButton>button {
|
| 41 |
-
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 42 |
}
|
| 43 |
</style>
|
|
|
|
| 44 |
""", unsafe_allow_html=True)
|
| 45 |
|
| 46 |
@st.cache_data
|
|
@@ -475,67 +505,73 @@ def analyze_stock(ticker, start_date, end_date, use_ai_assistant):
|
|
| 475 |
return None
|
| 476 |
|
| 477 |
def main():
|
| 478 |
-
st.title("Advanced Stock Analysis App")
|
| 479 |
st.markdown("Enter a stock ticker and date range to perform comprehensive stock analysis.")
|
| 480 |
|
| 481 |
-
col1, col2, col3 = st.columns(
|
| 482 |
with col1:
|
| 483 |
ticker = st.text_input("Stock Ticker", value="MSFT")
|
| 484 |
with col2:
|
| 485 |
start_date = st.date_input("Start Date", value=datetime(2015, 1, 1))
|
| 486 |
with col3:
|
| 487 |
end_date = st.date_input("End Date", value=datetime.now())
|
|
|
|
|
|
|
| 488 |
|
| 489 |
-
|
| 490 |
-
|
| 491 |
-
if st.button("Analyze Stock"):
|
| 492 |
results = analyze_stock(ticker, start_date, end_date, use_ai_assistant)
|
| 493 |
|
| 494 |
if results:
|
| 495 |
-
st.
|
| 496 |
col1, col2, col3 = st.columns(3)
|
| 497 |
with col1:
|
| 498 |
st.metric("Current Price", f"${results['latest_close']:.2f}")
|
| 499 |
with col2:
|
|
|
|
| 500 |
st.metric("Estimated Fair Value", f"${results['latest_fair_value']:.2f}",
|
| 501 |
-
f"{
|
|
|
|
| 502 |
with col3:
|
| 503 |
st.metric("R-squared Score", f"{results['r2']:.4f}")
|
| 504 |
|
| 505 |
st.metric("Price Prediction Range",
|
| 506 |
f"${results['latest_lower_bound']:.2f} to ${results['latest_upper_bound']:.2f}")
|
| 507 |
|
| 508 |
-
st.subheader("Fair Price Prediction")
|
| 509 |
st.plotly_chart(results['fig'], use_container_width=True)
|
| 510 |
|
| 511 |
col1, col2 = st.columns(2)
|
| 512 |
with col1:
|
| 513 |
-
st.subheader("SHAP Feature Importance")
|
| 514 |
st.pyplot(results['shap_fig'])
|
| 515 |
with col2:
|
| 516 |
-
st.subheader("Top 10 Important Features")
|
| 517 |
-
st.dataframe(results['feature_importance_df'].head(10))
|
| 518 |
|
| 519 |
-
st.subheader("Monthly Seasonality")
|
| 520 |
st.plotly_chart(results['seasonality_fig'], use_container_width=True)
|
| 521 |
|
| 522 |
current_month = datetime.now().month
|
| 523 |
next_month = (current_month % 12) + 1
|
| 524 |
col1, col2 = st.columns(2)
|
| 525 |
with col1:
|
|
|
|
| 526 |
st.metric(f"Current month ({datetime.now().strftime('%B')})",
|
| 527 |
-
f"{
|
| 528 |
-
f"{results['seasonality'].loc[current_month, 'Positive Periods']*100:.1f}% probability of positive return"
|
|
|
|
| 529 |
with col2:
|
|
|
|
| 530 |
st.metric(f"Next month ({(datetime.now() + timedelta(days=31)).strftime('%B')})",
|
| 531 |
-
f"{
|
| 532 |
-
f"{results['seasonality'].loc[next_month, 'Positive Periods']*100:.1f}% probability of positive return"
|
|
|
|
| 533 |
|
| 534 |
if results['gpt_analysis'] != "AI assistant analysis not requested.":
|
| 535 |
-
st.subheader("AI Assistant Analysis")
|
| 536 |
st.text_area("Analysis", value=results['gpt_analysis'], height=300)
|
| 537 |
|
| 538 |
-
st.subheader("Logarithmic Stock Chart")
|
| 539 |
st.plotly_chart(results['log_chart'], use_container_width=True)
|
| 540 |
|
| 541 |
if __name__ == "__main__":
|
|
|
|
| 28 |
# Custom CSS
|
| 29 |
st.markdown("""
|
| 30 |
<style>
|
| 31 |
+
.reportview-container {
|
| 32 |
+
background: linear-gradient(to right, #1e3c72, #2a5298);
|
| 33 |
+
}
|
| 34 |
+
.main .block-container {
|
| 35 |
+
max-width: 95%;
|
| 36 |
padding-top: 2rem;
|
| 37 |
padding-bottom: 2rem;
|
| 38 |
}
|
| 39 |
+
h1, h2, h3 {
|
| 40 |
+
color: #f0f2f6;
|
|
|
|
| 41 |
}
|
| 42 |
.stButton>button {
|
| 43 |
+
color: #ffffff;
|
| 44 |
+
background-color: #4CAF50;
|
| 45 |
+
border-radius: 5px;
|
| 46 |
+
border: none;
|
| 47 |
+
padding: 10px 24px;
|
| 48 |
+
transition: all 0.3s ease 0s;
|
| 49 |
+
}
|
| 50 |
+
.stButton>button:hover {
|
| 51 |
+
background-color: #45a049;
|
| 52 |
+
}
|
| 53 |
+
.stTextInput>div>div>input {
|
| 54 |
+
color: #1e3c72;
|
| 55 |
+
}
|
| 56 |
+
.stDateInput>div>div>input {
|
| 57 |
+
color: #1e3c72;
|
| 58 |
+
}
|
| 59 |
+
.stPlotlyChart {
|
| 60 |
+
background-color: rgba(255, 255, 255, 0.1);
|
| 61 |
+
border-radius: 5px;
|
| 62 |
+
padding: 10px;
|
| 63 |
+
}
|
| 64 |
+
.css-1d391kg {
|
| 65 |
+
background-color: rgba(255, 255, 255, 0.05);
|
| 66 |
+
}
|
| 67 |
+
.stDataFrame {
|
| 68 |
+
background-color: rgba(255, 255, 255, 0.1);
|
| 69 |
+
border-radius: 5px;
|
| 70 |
+
padding: 10px;
|
| 71 |
}
|
| 72 |
</style>
|
| 73 |
+
|
| 74 |
""", unsafe_allow_html=True)
|
| 75 |
|
| 76 |
@st.cache_data
|
|
|
|
| 505 |
return None
|
| 506 |
|
| 507 |
def main():
|
| 508 |
+
st.title("π Advanced Stock Analysis App")
|
| 509 |
st.markdown("Enter a stock ticker and date range to perform comprehensive stock analysis.")
|
| 510 |
|
| 511 |
+
col1, col2, col3, col4 = st.columns([2,2,2,1])
|
| 512 |
with col1:
|
| 513 |
ticker = st.text_input("Stock Ticker", value="MSFT")
|
| 514 |
with col2:
|
| 515 |
start_date = st.date_input("Start Date", value=datetime(2015, 1, 1))
|
| 516 |
with col3:
|
| 517 |
end_date = st.date_input("End Date", value=datetime.now())
|
| 518 |
+
with col4:
|
| 519 |
+
use_ai_assistant = st.checkbox("Use AI Assistant")
|
| 520 |
|
| 521 |
+
if st.button("Analyze Stock", key="analyze_button"):
|
|
|
|
|
|
|
| 522 |
results = analyze_stock(ticker, start_date, end_date, use_ai_assistant)
|
| 523 |
|
| 524 |
if results:
|
| 525 |
+
st.header("π Fair Price Analysis")
|
| 526 |
col1, col2, col3 = st.columns(3)
|
| 527 |
with col1:
|
| 528 |
st.metric("Current Price", f"${results['latest_close']:.2f}")
|
| 529 |
with col2:
|
| 530 |
+
change_pct = ((results['latest_fair_value'] - results['latest_close']) / results['latest_close'] * 100)
|
| 531 |
st.metric("Estimated Fair Value", f"${results['latest_fair_value']:.2f}",
|
| 532 |
+
f"{change_pct:+.2f}%",
|
| 533 |
+
delta_color="normal" if change_pct >= 0 else "inverse")
|
| 534 |
with col3:
|
| 535 |
st.metric("R-squared Score", f"{results['r2']:.4f}")
|
| 536 |
|
| 537 |
st.metric("Price Prediction Range",
|
| 538 |
f"${results['latest_lower_bound']:.2f} to ${results['latest_upper_bound']:.2f}")
|
| 539 |
|
| 540 |
+
st.subheader("π Fair Price Prediction")
|
| 541 |
st.plotly_chart(results['fig'], use_container_width=True)
|
| 542 |
|
| 543 |
col1, col2 = st.columns(2)
|
| 544 |
with col1:
|
| 545 |
+
st.subheader("π SHAP Feature Importance")
|
| 546 |
st.pyplot(results['shap_fig'])
|
| 547 |
with col2:
|
| 548 |
+
st.subheader("π Top 10 Important Features")
|
| 549 |
+
st.dataframe(results['feature_importance_df'].head(10), height=400)
|
| 550 |
|
| 551 |
+
st.subheader("π
Monthly Seasonality")
|
| 552 |
st.plotly_chart(results['seasonality_fig'], use_container_width=True)
|
| 553 |
|
| 554 |
current_month = datetime.now().month
|
| 555 |
next_month = (current_month % 12) + 1
|
| 556 |
col1, col2 = st.columns(2)
|
| 557 |
with col1:
|
| 558 |
+
current_change = results['seasonality'].loc[current_month, 'Mean Change%']*100
|
| 559 |
st.metric(f"Current month ({datetime.now().strftime('%B')})",
|
| 560 |
+
f"{current_change:.2f}%",
|
| 561 |
+
f"{results['seasonality'].loc[current_month, 'Positive Periods']*100:.1f}% probability of positive return",
|
| 562 |
+
delta_color="normal" if current_change >= 0 else "inverse")
|
| 563 |
with col2:
|
| 564 |
+
next_change = results['seasonality'].loc[next_month, 'Mean Change%']*100
|
| 565 |
st.metric(f"Next month ({(datetime.now() + timedelta(days=31)).strftime('%B')})",
|
| 566 |
+
f"{next_change:.2f}%",
|
| 567 |
+
f"{results['seasonality'].loc[next_month, 'Positive Periods']*100:.1f}% probability of positive return",
|
| 568 |
+
delta_color="normal" if next_change >= 0 else "inverse")
|
| 569 |
|
| 570 |
if results['gpt_analysis'] != "AI assistant analysis not requested.":
|
| 571 |
+
st.subheader("π€ AI Assistant Analysis")
|
| 572 |
st.text_area("Analysis", value=results['gpt_analysis'], height=300)
|
| 573 |
|
| 574 |
+
st.subheader("π Logarithmic Stock Chart")
|
| 575 |
st.plotly_chart(results['log_chart'], use_container_width=True)
|
| 576 |
|
| 577 |
if __name__ == "__main__":
|