Interface RiskContract

Contract for risk rejection events.

Emitted by riskSubject ONLY when a signal is REJECTED due to risk validation failure. Used for tracking actual risk violations and monitoring rejected signals.

Events are emitted only when risk limits are violated (not for allowed signals). This prevents spam and allows focusing on actual risk management interventions.

Consumers:

  • RiskMarkdownService: Accumulates rejection events for report generation
  • User callbacks via listenRisk() / listenRiskOnce()
import { listenRisk } from "backtest-kit";

// Listen to all risk rejection events
listenRisk((event) => {
console.log(`[RISK REJECTED] Signal for ${event.symbol}`);
console.log(`Strategy: ${event.strategyName}`);
console.log(`Active positions: ${event.activePositionCount}`);
console.log(`Price: ${event.currentPrice}`);
console.log(`Timestamp: ${new Date(event.timestamp).toISOString()}`);
});

// Alert on risk rejections for specific symbol
listenRisk((event) => {
if (event.symbol === "BTCUSDT") {
console.warn("BTC signal rejected due to risk limits!");
}
});
interface RiskContract {
    activePositionCount: number;
    backtest: boolean;
    currentPrice: number;
    exchangeName: string;
    frameName: string;
    pendingSignal: ISignalDto;
    rejectionId: string;
    rejectionNote: string;
    strategyName: string;
    symbol: string;
    timestamp: number;
}

Properties

activePositionCount: number

Number of currently active positions across all strategies at rejection time. Used to track portfolio-level exposure when signal was rejected.

backtest: boolean

Whether this event is from backtest mode (true) or live mode (false). Used to separate backtest and live risk rejection tracking.

currentPrice: number

Current VWAP price at the time of rejection. Market price when risk check was performed.

exchangeName: string

Exchange name. Identifies which exchange this signal was for.

frameName: string

Frame name used in backtest execution. Identifies which frame this signal was for in backtest execution.

pendingSignal: ISignalDto

Pending signal to apply. Contains signal details (position, priceOpen, priceTakeProfit, priceStopLoss, etc).

rejectionId: string

Unique identifier for this rejection instance. Generated by ClientRisk for tracking and debugging purposes. Null if validation threw exception without custom ID.

rejectionNote: string

Human-readable reason why the signal was rejected. Captured from IRiskValidation.note or error message.

console.log(`Rejection reason: ${event.rejectionNote}`);
// Output: "Rejection reason: Max 3 positions allowed"
strategyName: string

Strategy name requesting to open a position. Identifies which strategy attempted to create the signal.

symbol: string

Trading pair symbol (e.g., "BTCUSDT"). Identifies which market this rejected signal belongs to.

timestamp: number

Event timestamp in milliseconds since Unix epoch. Represents when the signal was rejected.

const eventDate = new Date(event.timestamp);
console.log(`Signal rejected at: ${eventDate.toISOString()}`);