Files
trading_bot_v3/test-sl-tp-fix.js
mindesbunister 167d7ff5bc feat: implement comprehensive AI decision display and reasoning panel
Major Features Added:
- Complete AI decision tracking system with detailed reasoning display
- Prominent gradient-styled AI reasoning panel on automation-v2 page
- Test AI decision generator with realistic trading scenarios
- Enhanced decision transparency showing entry/exit logic and leverage calculations

- Fixed orphaned order cleanup to preserve reduce-only SL/TP orders
- Integrated AI leverage calculator with 100x capability (up from 10x limit)
- Added lastDecision property to automation status for UI display
- Enhanced position monitoring with better cleanup triggers

- Beautiful gradient-styled AI Trading Analysis panel
- Color-coded confidence levels and recommendation displays
- Detailed breakdown of entry strategy, stop loss logic, and take profit targets
- Real-time display of AI leverage reasoning with safety buffer explanations
- Test AI button for demonstration of decision-making process

- SL/TP orders now execute properly (fixed cleanup interference)
- AI calculates sophisticated leverage (8.8x-42.2x vs previous 1x hardcoded)
- Complete decision audit trail with execution details
- Risk management transparency with liquidation safety calculations

- Why This Decision? - Prominent reasoning section
- Entry & Exit Strategy - Price levels with color coding
- AI Leverage Decision - Detailed calculation explanations
- Execution status with success/failure indicators
- Transaction IDs and comprehensive trade details

All systems now provide full transparency of AI decision-making process.
2025-07-26 22:41:55 +02:00

164 lines
5.9 KiB
JavaScript
Raw Permalink Blame History

This file contains invisible Unicode characters
This file contains invisible Unicode characters that are indistinguishable to humans but may be processed differently by a computer. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.
#!/usr/bin/env node
/**
* Test Stop Loss / Take Profit Preservation Fix
* Verifies that SL/TP orders are not being incorrectly canceled as orphaned orders
*/
console.log('🧪 Testing Stop Loss / Take Profit Preservation Fix...');
async function testSLTPPreservation() {
try {
console.log('\n1⃣ Testing Cleanup Logic...');
// Simulate position data
const mockPositions = [
{
marketIndex: 0, // SOL-PERP
symbol: 'SOL-PERP',
side: 'long',
size: 1.5,
entryPrice: 165.50
}
];
// Simulate orders including SL/TP
const mockOrders = [
{
orderId: 1,
marketIndex: 0, // Same market as position
direction: 1, // SHORT (opposite to position - correct for SL)
reduceOnly: true, // This is a Stop Loss order
baseAssetAmount: { isZero: () => false },
status: { open: true }
},
{
orderId: 2,
marketIndex: 0, // Same market as position
direction: 1, // SHORT (opposite to position - correct for TP)
reduceOnly: true, // This is a Take Profit order
baseAssetAmount: { isZero: () => false },
status: { open: true }
},
{
orderId: 3,
marketIndex: 1, // Different market - truly orphaned
direction: 0, // LONG
reduceOnly: false, // Regular order
baseAssetAmount: { isZero: () => false },
status: { open: true }
}
];
// Test the fixed logic
const positionMarkets = new Set(mockPositions.map(pos => pos.marketIndex));
console.log('📊 Position markets:', Array.from(positionMarkets));
// OLD BROKEN LOGIC (what was causing the bug):
const oldOrphanedOrders = mockOrders.filter(order =>
!positionMarkets.has(order.marketIndex) ||
(order.reduceOnly && !positionMarkets.has(order.marketIndex))
);
// NEW FIXED LOGIC:
const newOrphanedOrders = mockOrders.filter(order =>
!positionMarkets.has(order.marketIndex) && !order.reduceOnly
);
console.log(`❌ OLD LOGIC would cancel: ${oldOrphanedOrders.length} orders`);
oldOrphanedOrders.forEach(order => {
const type = order.reduceOnly ? 'SL/TP' : 'Regular';
console.log(` - Order ${order.orderId} (${type}) on market ${order.marketIndex}`);
});
console.log(`✅ NEW LOGIC will cancel: ${newOrphanedOrders.length} orders`);
newOrphanedOrders.forEach(order => {
const type = order.reduceOnly ? 'SL/TP' : 'Regular';
console.log(` - Order ${order.orderId} (${type}) on market ${order.marketIndex}`);
});
// Verify the fix
const slTpOrdersPreserved = mockOrders
.filter(order => order.reduceOnly && positionMarkets.has(order.marketIndex))
.filter(order => !newOrphanedOrders.includes(order));
console.log(`🛡️ SL/TP orders preserved: ${slTpOrdersPreserved.length}`);
slTpOrdersPreserved.forEach(order => {
console.log(` ✅ Order ${order.orderId} (SL/TP) preserved for market ${order.marketIndex}`);
});
console.log('\n2⃣ Testing API Endpoints...');
// Test cleanup API with mock data
console.log('📡 Testing cleanup-orders API...');
const baseUrl = 'http://localhost:9001';
// Test positions endpoint
try {
const positionsResponse = await fetch(`${baseUrl}/api/drift/positions`);
const positionsData = await positionsResponse.json();
console.log(`✅ Positions API: ${positionsData.success ? 'Working' : 'Failed'}`);
if (positionsData.success) {
console.log(` 📊 Found ${positionsData.positions?.length || 0} positions`);
}
} catch (error) {
console.log(`❌ Positions API error: ${error.message}`);
}
// Test orders endpoint
try {
const ordersResponse = await fetch(`${baseUrl}/api/drift/orders`);
const ordersData = await ordersResponse.json();
console.log(`✅ Orders API: ${ordersData.success ? 'Working' : 'Failed'}`);
if (ordersData.success) {
console.log(` 📋 Found ${ordersData.orders?.length || 0} orders`);
// Analyze order types
const orders = ordersData.orders || [];
const reduceOnlyOrders = orders.filter(order => order.reduceOnly);
const regularOrders = orders.filter(order => !order.reduceOnly);
console.log(` 🛡️ Reduce-only orders (SL/TP): ${reduceOnlyOrders.length}`);
console.log(` 📈 Regular orders: ${regularOrders.length}`);
}
} catch (error) {
console.log(`❌ Orders API error: ${error.message}`);
}
console.log('\n3⃣ Testing Position Monitor...');
try {
const monitorResponse = await fetch(`${baseUrl}/api/automation/position-monitor`);
const monitorData = await monitorResponse.json();
if (monitorData.success) {
const monitor = monitorData.monitor;
console.log(`✅ Position Monitor: Working`);
console.log(` 📊 Has Position: ${monitor.hasPosition}`);
console.log(` 🧹 Cleanup Triggered: ${monitor.orphanedOrderCleanup?.triggered || false}`);
console.log(` 📝 Message: ${monitor.orphanedOrderCleanup?.message || 'N/A'}`);
} else {
console.log(`❌ Position Monitor failed: ${monitorData.error}`);
}
} catch (error) {
console.log(`❌ Position Monitor error: ${error.message}`);
}
console.log('\n✅ Testing Complete!');
console.log('\n📋 Summary of Fixes:');
console.log(' 🛡️ Stop Loss and Take Profit orders are now preserved');
console.log(' 🧹 Only truly orphaned orders (non-reduce-only) will be cleaned up');
console.log(' 📊 Position monitor is more conservative about cleanup');
console.log(' ⚠️ Background cleanup services should be stopped to prevent interference');
} catch (error) {
console.error('❌ Test failed:', error);
}
}
// Run the test
testSLTPPreservation();