Project 01  ·  Shipped

Autonomous Market
Monitoring System

A production AI agent that observes market conditions, evaluates signals, manages risk, and executes paper trades without human intervention — every hour the market is open.

Status
Live
Equities watched
10
Tick frequency
1 hr
Backtest return
+7.4%

Not a demo. A running system.

Most AI projects in a portfolio are prototypes — things that worked once, in a controlled environment, on a good day. This is not that.

This system runs on the Alpaca Markets paper trading API, pulls live market data every hour, evaluates 10 equities against a multi-signal strategy, and places real simulated orders. The dashboard updates in real time. The risk manager has hard limits. The trade log persists across sessions.

It was built, debugged, backtested, and parameter-tuned in a single session. The parameters running live today were selected after a sweep across 4 configurations and 365 days of hourly data across 4 symbols.

01
Data ingestion
Alpaca Markets API pulls hourly OHLCV bars for all 10 symbols. 60-bar rolling window. IEX feed.
02
Signal engine
RSI(14), SMA crossover (9/21), 50-bar trend filter, MACD histogram. Requires confluence — no single-indicator trades.
03
Risk layer
Hard stop-loss at 3%. Trailing stop at 3.5%. Daily loss circuit breaker at 5% of portfolio. Position size capped at 10%.
04
Execution
Market orders via Alpaca. Paper trading mode. Configurable for live with a single env variable change.
05
State management
Thread-safe state store tracks positions, peak prices, bars held, cooldown periods, and trade history.
06
Dashboard
Flask API + vanilla JS frontend. Auto-refreshes every 30s. Stop/Start bot controls. Accessible on local network.

How the bot decides.

Every hourly tick runs each symbol through the same decision tree. The strategy requires multiple conditions to align — it doesn't trade noise.

01
Trend filter

Price must be above the 50-bar SMA. No buys in downtrending stocks. This single filter eliminates the majority of losing setups.

Required
02
RSI dip entry

RSI(14) below 40 signals a short-term oversold condition within an uptrend. Buying weakness, not strength.

OR
03
MA crossover + MACD confirmation

9-bar SMA crossing above 21-bar SMA, confirmed by positive MACD histogram. Momentum-based entry requiring two signals to agree.

OR
04
Exit: trailing stop

Once in a position, peak price is tracked. A 3.5% drop from peak triggers exit. Locks in gains on winners, limits losses on losers.

Exit
05
Exit: signal deterioration

RSI overbought above 65, MA cross down, or MACD turning negative triggers a sell after minimum hold period of 3 bars.

Exit

Run the strategy yourself.

Adjust the parameters and see how strategy behavior changes. Runs the actual trading logic against synthetic market data generated from real statistical properties.

Strategy simulator — synthetic data Not financial advice
40
3.5%
3
10%
2
Total return
Total trades
Win rate
Max drawdown

The guardrails.

Every autonomous system that touches money needs hard limits that can't be reasoned around. These are the live parameters running on the paper account today.

Hard stop-loss
3.0%

Maximum loss per position before forced exit. No exceptions, no overrides.

Trailing stop
3.5%

Tracks peak price from entry. Locks in gains as the position moves in your favor.

Daily loss limit
5.0%

Circuit breaker. If realized losses hit 5% of portfolio value, no new trades fire for the rest of the day.

Max position size
10%

No single position exceeds 10% of available cash. Enforced at order placement.

The point is the deployment.

This isn't an AI strategy exercise. It's a production deployment of an autonomous decision-making agent — with a data pipeline, a signal engine, a risk layer, a state manager, an API integration, and a monitoring interface.

That stack is structurally identical to any enterprise AI agent: ingest data, evaluate against rules, manage state, execute actions, observe outputs. The domain is financial markets. The pattern is universal.

# The core decision loop — runs every hour the market is open

def get_signal(df, bars_held, bars_since_exit, in_position):
  # Enforce minimum hold — prevents panic selling
  if in_position and bars_held < MIN_HOLD_BARS:
    return "hold"

  # Trend filter — no buys in downtrends
  if not in_uptrend:
    return "hold"

  # Cooldown after stop-loss — prevents revenge trading
  if bars_since_exit < COOLDOWN_BARS:
    return "hold"

  # Entry: RSI dip OR MA crossover with MACD confirmation
  if rsi < RSI_OVERSOLD or (ma_cross_up and macd_bullish):
    return "buy"

  return "hold"