🔱

TRISHULA P&L Analysis

Market-Neutral Portfolio Performance vs BTC Benchmark
April 10 – April 24, 2026 | Binance Futures USDC Testnet
Total P&L
−$39.81
−0.80% return
BTC Benchmark
+7.25%
$72,979 → $78,269
Underperformance
−8.05%
vs buy & hold BTC
Win Rate
39.2%
65 W / 101 L
CryptoPrism-io | Yogesh Sahu | Generated April 24, 2026
Chapter 01

Executive Summary

TRISHULA has been live-trading on Binance Futures USDC testnet for 14 days (April 10–24, 2026). The strategy deploys a market-neutral long/short portfolio driven by a 3-pronged ensemble signal (LSTM + TCN + LightGBM). Over this period, the portfolio generated a net loss of −$39.81 (−0.80%) on ~$5,000 capital, while Bitcoin gained +7.25% — an underperformance of −8.05% vs the simplest benchmark.

Critical Finding

The short leg is the entire drag. Longs generated +$106.69 while shorts lost −$146.50. The strategy would have been profitable as a long-only system. Short signals have a 42% win rate with an asymmetric risk profile: avg loss (−5.1%) is nearly 2x avg win (+2.6%).

Total Trades
186
166 closed, 20 open
Long P&L
+$106.69
93 trades, 46.2% win rate
Short P&L
−$146.50
73 trades, 30.1% win rate
Best Trade
+$32.26
TIA long (+21.5%)
Worst Trade
−$33.53
ENA short (−22.6%)
Avg Hold
3 days
matching label_3d target

Trade Composition

Of 166 closed trades, 41 were noise (account resets, migrations, emergency closes at $0 PnL). Only 125 trades had meaningful P&L. This inflates the loss count and suppresses the true win rate. Excluding flat trades: Long win rate = 58.9% (43/73), Short win rate = 42.3% (22/52).

Close ReasonCountAvg ReturnTotal P&LVerdict
Take Profit (+4.5%)24+6.3%+$154.42Working well
Stop Loss (−8%)9−9.5%−$82.52Working, but hit too often on shorts
Expiry (3-day)32−1.4%−$59.82Signals decaying before expiry
Exchange Reset24−1.5%−$50.51Testnet noise
Emergency/Migration48−0.1%−$10.52Operational noise
Rebalance9+0.08%+$1.17Neutral
Chapter 02

Portfolio Performance & Equity Curve

Daily P&L shows high volatility with two large drawdowns (Apr 14: −$57.25 cumulative, Apr 21: −$33.87). The portfolio briefly went positive on Apr 20 (+$17.95) before a sharp −$51.82 loss wiped the gains.

Cumulative P&L vs BTC Buy & Hold ($5,000 capital)
Daily P&L Breakdown
Drawdown Analysis

Max drawdown: −$57.25 (−1.15% of capital) on April 14. The largest single-day loss was −$51.82 on April 21. Recovery factor: 0.31x (net P&L / max drawdown).

Key Metrics

Sharpe Ratio (daily)
−0.15
below 0 = risk-destroying
Max Drawdown
−$57.25
−1.15% of capital
PnL Std Dev
$7.12
per trade volatility
Chapter 03

Long vs Short Leg Analysis

The strategy is designed to be market-neutral — deploying roughly equal capital to longs and shorts. However, the two legs have diverged sharply in performance, revealing a fundamental asymmetry in the signal model's predictive power.

Long Leg (BUY)
+$106.69
93 trades | 43W 20F 30L | Avg: +0.81%
Avg win: +3.73% | Avg loss: −2.84%
Profit factor: 1.31x
Short Leg (SHORT)
−$146.50
73 trades | 22W 21F 30L | Avg: −1.31%
Avg win: +2.62% | Avg loss: −5.11%
Profit factor: 0.39x
P&L Distribution: Longs vs Shorts
Root Cause: Short Signals Are Inverted

The model's "most bearish" signals (lowest signal_score) should predict price declines. Instead, many shorted coins rallied — the average short loses −5.11% when it loses, nearly 2x the average win of +2.62%. This asymmetry suggests the short signal is capturing momentum (coins dropping hard then bouncing) rather than future weakness.

What If We Were Long-Only?

If TRISHULA ran as a long-only system (no shorts), deploying the same $2,500 per side into longs only:

Long-Only P&L
+$106.69
+4.27% return — still trails BTC (+7.25%)
Long-Only vs BTC Gap
−2.98%
Much closer than current −8.05%
Chapter 04

Coin-Level P&L Breakdown

P&L by Coin (Closed Trades Only)

Top 5 Performers

CoinTradesTotal P&LAvg P&L%Win RateCapital
ZEC (Zcash)11+$28.18+1.59%45% (5/11)$2,331.68
ARB (Arbitrum)8+$26.50+2.12%50% (4/8)$1,774.87
SUI8+$24.87+1.96%63% (5/8)$1,778.00
LINK (Chainlink)8+$22.81+1.80%75% (6/8)$1,774.21
XRP7+$11.64+1.14%29% (2/7)$1,934.56

Bottom 5 Performers

CoinTradesTotal P&LAvg P&L%Win RateCapital
AAVE9−$52.70−3.52%22% (2/9)$1,630.49
ENA (Ethena)6−$49.19−5.36%33% (2/6)$887.82
UNI (Uniswap)8−$30.18−2.54%13% (1/8)$1,813.61
TIA (Celestia)7−$27.26−2.30%14% (1/7)$1,061.81
FIL (Filecoin)8−$16.82−1.41%13% (1/8)$1,823.34
Pattern: Losers Are Predominantly Shorted

The 5 worst performers (AAVE, ENA, UNI, TIA, FIL) have combined 24 short trades that account for most of the losses. These are high-beta altcoins that rallied during the BTC uptrend. The model shorted them because of negative signal scores, but in a risk_on regime, negative-score altcoins still rally with the market.

Chapter 05

Signal Quality Analysis

The ensemble model produces a signal_score for each coin. Positive scores predict outperformance (→ long), negative scores predict underperformance (→ short). The critical question: does signal_score actually predict returns?

Signal Score vs Realized P&L% (Each Dot = One Trade)

Signal Score Buckets

Score RangeDirectionTradesAvg P&L%Win RateVerdict
> 0.05LONG4+2.42%75%Strong signal
0.01 to 0.05LONG5+0.69%60%Decent
−0.02 to 0.01LONG14+1.74%43%Mixed — high variance
−0.03 to −0.02LONG32+1.10%50%Bulk of longs, slightly positive
−0.05 to −0.03SHORT30−1.79%33%Signal failing
< −0.05SHORT33−0.16%39%Flat — no edge
Signal-PnL Correlation Is Near Zero for Shorts

Long signals show weak but positive correlation: higher scores → better returns. But short signals show no correlation — the most negative scores (−0.05 to −0.14) perform almost the same as mildly negative scores (−0.03 to −0.05). The model has predictive power for "what will go up" but not "what will go down."

Signal Score Distribution

Nearly all signals cluster in a narrow band: −0.05 to +0.05. The model rarely produces high-conviction signals. This means the portfolio is mostly filled with low-confidence positions, diluting any edge. The few high-confidence long trades (score > 0.05) actually perform well.

Long IC (Score → Return)
~0.08
Weak but positive — longs have directional edge
Short IC (Score → Return)
~−0.02
Near zero — shorts have no edge
Chapter 06

Position Sizing & Risk Management

Current Configuration

ParameterValueAssessment
Max Positions per Side15Appropriate for diversification
Target Deploy %95%Aggressive — leaves no dry powder
Hold Period3 daysMatches label_3d signal
Stop Loss−8%Reasonable for 3-day hold
Take Profit+4.5%Asymmetric: TP < SL → cuts winners short
Min Signal (Long)> −0.15Too wide — includes low-conviction entries
Max Signal (Short)< 0.00Too permissive — any negative signal triggers short
Take-Profit / Stop-Loss Asymmetry

TP at +4.5% vs SL at −8% creates a negative expected value structure. Take-profit fires on winners at +4.5%, but losers can bleed to −8% before being stopped. This is backwards: winners should be allowed to run further than losers. Recommended: TP ≥ SL (e.g., TP=8%, SL=5%) or use trailing stops.

Exit Analysis

P&L by Exit Reason
Take Profits
24
14.5% of closed trades
Stop Losses
9
5.4% hit rate
Expiry Exits
32
Most trades expire at a loss

Open Portfolio (20 positions)

CoinDirEntrySize (USDC)ScoreOpened
ZECLONG$356.47$161.84+0.103Apr 24 12:00
ARBLONG$0.1303$162.23+0.046Apr 24 12:00
SOLLONG$86.16$161.12+0.044Apr 24 12:00
DOGELONG$0.0982$161.59+0.038Apr 24 12:00
TIALONG$0.3555$147.89+0.035Apr 23 04:00
LTCLONG$55.44$143.42+0.019Apr 21 12:00
AAVELONG$93.47$140.20+0.019Apr 24 04:00
LINKLONG$9.284$140.37+0.015Apr 24 04:00
ETHLONG$2,329.42$160.73+0.012Apr 24 12:00
XRPLONG$1.4385$161.69+0.005Apr 24 12:00
BNBLONG$638.66$159.67−0.002Apr 24 12:00
ENALONG$0.1101$180.64−0.006Apr 24 00:00
SUILONG$0.9691$167.27−0.011Apr 22 08:00
CRVLONG$0.2205$157.24−0.011Apr 23 20:00
ADALONG$0.251$161.74−0.012Apr 24 12:00
BTCSHORT$78,237.90$156.48−0.014Apr 24 12:00
NEOSHORT$2.878$156.62−0.029Apr 24 12:00
UNISHORT$3.257$156.34−0.030Apr 24 12:00
BCHSHORT$457.36$156.87−0.030Apr 24 12:00
FILSHORT$0.948$166.37−0.044Apr 22 08:00
Chapter 07

Trading System Function Audit

In-depth analysis of every function in spot_bot.py (561 lines) and futures_exchange.py (272 lines), identifying bugs, risks, and optimization opportunities.

Core Trading Functions

run_signal_cycle() — spot_bot.py:192
Main trading loop: sync → close expired → open longs → open shorts → notify Telegram
ISSUE: total_equity calculated in long block is used in short block (line 360) without recalculation — if a long trade depletes balance, short sizing uses stale equity.
ISSUE: open_positions fetched at line 295 is stale — doesn't include positions just opened in the same cycle. The slug dedup via open_slugs dict works, but size calculations may be off.
sync_db_with_exchange() — spot_bot.py:60
Compares DB OPEN positions vs Binance positions. Ghost-closes any positions not found on exchange.
OK: Correctly handles testnet resets, manual closes, liquidations. Added Apr 23 to prevent ghost-position buildup.
get_long_signals() / get_short_signals() — spot_bot.py:111, 127
Queries ML_SIGNALS_V2 for latest date, filters by tradeable slugs and score thresholds.
ISSUE: Uses DATE(timestamp) which means signals from any hour on the latest day are used. If hourly signals run at :00 and the bot runs at :30, it correctly gets the latest batch. But if the ensemble fails silently, yesterday's stale signals are used with no warning.
ISSUE: MIN_SIGNAL_SCORE = -0.15 for longs is too permissive — most longs have scores between −0.03 and 0.00, meaning the filter barely removes anything.
close_trade() — spot_bot.py:160
Closes a trade by updating DB with exit price, P&L calculation, and timestamp.
OK: Correctly calculates P&L for both long (exit−entry) and short (entry−exit) directions.
insert_trade() — spot_bot.py:143
Inserts new trade record into ML_TRADES.
OK: Clean parameterized SQL, no injection risk.

Exchange Functions

build_futures_exchange() — futures_exchange.py:57
Creates ccxt.binanceusdm client with testnet URL overrides.
ISSUE: set_sandbox_mode(True) wrapped in try/except (line 76) — works with pinned ccxt 4.3.85 but will break silently if upgraded. URL override on line 80 is the real testnet config.
open_long() / open_short() — futures_exchange.py:123, 183
Market orders with 1x leverage, isolated margin. Returns fill details.
ISSUE: open_short parameter is named usdt_amount (line 183) — should be usdc_amount for consistency with the USDC migration. Cosmetic but confusing.
get_futures_balance() — futures_exchange.py:243
Returns USDC free/total balance.
ISSUE: Return keys are usdt_free and usdt_total (line 247-248) even though fetching USDC balance. Should be renamed to usdc_free/usdc_total to avoid confusion.
show_status() — spot_bot.py:452
CLI portfolio status display.
BUG: Calls build_exchange() (line 454) and get_price()/get_balance() — these functions don't exist in the current codebase. This function is broken and will crash on execution. Likely a leftover from the spot trading era.

Configuration Issues

Take-Profit / Stop-Loss Ratio
TP=+4.5%, SL=−8% → Risk/reward ratio of 0.56
ISSUE: Winners are capped at +4.5% but losers can bleed to −8%. This means you need a >64% win rate to break even. Current win rate (excl flat) is 52% — not enough. Either raise TP to ≥8% or lower SL to ≤4.5%.
Signal Score Thresholds
Long: > −0.15, Short: < 0.00
ISSUE: MIN_SIGNAL_SCORE at −0.15 barely filters anything (99% of signals pass). Should be tightened to −0.03 or higher based on signal bucket analysis. Short threshold at 0.00 is also too permissive — should require < −0.05 minimum.
Chapter 08

Recommendations & Next Steps

VERDICT: LOSING TO BTC BY −8.05%

−$39.81

14-day performance on $5,000 testnet capital

Priority 1: Fix the Short Leg

Option A: Disable Shorts (Immediate)

Set SHORT_N = 0 or MAX_OPEN_POSITIONS = 0 for shorts. This alone would have turned −$39.81 into +$106.69. The model doesn't predict downside — don't force it to.

Option B: Retrain Short Signal (Medium-term)

Train a dedicated short model with different features: volume decline, on-chain outflows, funding rate, open interest decay. The current signal_score is optimized for long prediction and inverted for shorts — that doesn't work.

Priority 2: Fix TP/SL Asymmetry

CurrentRecommendedRationale
TP: +4.5%TP: +8% or trailingLet winners run to match SL magnitude
SL: −8%SL: −5%Cut losers faster, reduce avg loss
Hold: 3 days fixedHold: 3-5 days adaptiveExtend if in profit, cut if flat

Priority 3: Tighten Entry Filters

ParameterCurrentRecommended
MIN_SIGNAL_SCORE (Long)−0.15−0.03 or 0.00
MAX_SIGNAL_SCORE (Short)0.00−0.05
LONG_N1510 (concentrate on highest conviction)
SHORT_N155 or 0 (reduce exposure)

Priority 4: Fix Code Bugs

BugFile:LineImpact
show_status() calls undefined build_exchange()spot_bot.py:454--status flag crashes
usdt_amount parameter name in open_short()futures_exchange.py:183Cosmetic confusion
Balance keys usdt_free/usdt_totalfutures_exchange.py:247Naming inconsistency with USDC
Stale signal detection missingspot_bot.py:116Trades on old signals if ensemble fails
What's Working

Long signals are profitable. The ensemble has genuine predictive power for upside: +$106.69 over 14 days, 58.9% win rate (excl flat), average win (+3.73%) exceeds average loss (−2.84%). ZEC, ARB, SUI, and LINK consistently profit. The signal model is valid — the deployment strategy needs fixing.

CryptoPrism-io | TRISHULA P&L Analysis | April 24, 2026
Generated by Claude Code for Yogesh Sahu