A production-quality Python project for fetching, analysing, and visualising stock market data — complete with technical indicators, ML-based price prediction, a backtesting engine, and an interactive Plotly/Dash dashboard.
stock_analyzer/
├── app.py # Dash dashboard entry point
├── requirements.txt
├── pytest.ini
├── src/
│ ├── __init__.py
│ ├── data_fetcher.py # yfinance wrapper with caching
│ ├── indicators.py # Technical indicators + signal generator
│ ├── backtester.py # Event-driven backtesting engine
│ ├── predictor.py # Random Forest / GBM price direction model
│ └── charts.py # Plotly chart builders
├── tests/
│ ├── test_indicators.py
│ └── test_backtester.py
└── .vscode/
├── settings.json
└── launch.json
cd stock_analyzer
code .python -m venv .venv
# Windows:
.venv\Scripts\activate
# macOS/Linux:
source .venv/bin/activatepip install -r requirements.txtpython app.pyOpen http://localhost:8050 in your browser.
pytest tests/ -v| Module | What it does |
|---|---|
data_fetcher.py |
Downloads OHLCV + metadata via yfinance; in-memory cache; multi-ticker support |
indicators.py |
SMA, EMA, RSI, MACD, Bollinger Bands, Stochastic, ATR, OBV; composite signal generator |
backtester.py |
Signal-driven backtest; tracks trades, equity curve, Sharpe, max drawdown, win rate |
predictor.py |
RandomForest / GradientBoosting next-day direction prediction; time-series CV |
charts.py |
Candlestick + volume, RSI, MACD, equity curve, multi-stock comparison (all dark-themed Plotly) |
app.py |
Dash dashboard wiring everything together with live KPI cards and comparison mode |
# src/indicators.py
@staticmethod
def add_vwap(df: pd.DataFrame) -> pd.DataFrame:
df = df.copy()
typical_price = (df["High"] + df["Low"] + df["Close"]) / 3
df["VWAP"] = (typical_price * df["Volume"]).cumsum() / df["Volume"].cumsum()
return df# Create a custom signal column before calling Backtester.run()
df["MySignal"] = 0
df.loc[df["RSI"] < 25, "MySignal"] = 1 # Very oversold → BUY
df.loc[df["RSI"] > 75, "MySignal"] = -1 # Very overbought → SELL
bt = Backtester(initial_capital=10_000)
result = bt.run(df, signal_col="MySignal")
print(bt.summary(result))predictor = PricePredictor(model_type="gradient_boost")
predictor.train(df)
direction, confidence = predictor.predict_next(df)| Library | Purpose |
|---|---|
yfinance |
Stock data from Yahoo Finance |
pandas / numpy |
Data manipulation |
ta |
40+ technical indicators |
scikit-learn |
ML models + preprocessing |
plotly |
Interactive charts |
dash |
Web dashboard framework |
dash-bootstrap-components |
UI components |
Tests use pytest with synthetic data (no network calls required):
pytest tests/ -v # All tests
pytest tests/test_indicators.py # Just indicators
pytest -k "TestRSI" # Filter by class/name- Add portfolio optimisation (Markowitz / Sharpe maximisation)
- Integrate live WebSocket price feeds
- Add SQLite persistence for historical backtest results
- Deploy to Render / Railway as a web app
- Add email/Telegram alerts for signal changes
- Implement LSTM / Transformer for time-series prediction
- Add options chain analysis