trading-platform/docs/02-definicion-modulos/OQI-003-trading-charts/historias-usuario/US-TRD-012-configurar-tp-sl.md
rckrdmrd a7cca885f0 feat: Major platform documentation and architecture updates
Changes include:
- Updated architecture documentation
- Enhanced module definitions (OQI-001 to OQI-008)
- ML integration documentation updates
- Trading strategies documentation
- Orchestration and inventory updates
- Docker configuration updates

🤖 Generated with [Claude Code](https://claude.com/claude-code)

Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
2026-01-07 05:33:35 -06:00

379 lines
14 KiB
Markdown

---
id: "US-TRD-012"
title: "Configurar Take Profit y Stop Loss"
type: "User Story"
status: "Done"
priority: "Alta"
epic: "OQI-003"
story_points: 5
created_date: "2025-12-05"
updated_date: "2026-01-04"
---
# US-TRD-012: Configurar Take Profit y Stop Loss
## Metadata
| Campo | Valor |
|-------|-------|
| **ID** | US-TRD-012 |
| **Épica** | OQI-003 - Trading y Charts |
| **Módulo** | trading |
| **Prioridad** | P1 |
| **Story Points** | 3 |
| **Sprint** | Sprint 5 |
| **Estado** | Pendiente |
| **Asignado a** | Por asignar |
---
## Historia de Usuario
**Como** trader practicante,
**quiero** configurar niveles de Take Profit y Stop Loss en mis posiciones,
**para** automatizar la gestión de riesgo y asegurar ganancias sin monitoreo constante.
## Descripción Detallada
El usuario debe poder establecer niveles de Take Profit (TP) y Stop Loss (SL) en posiciones abiertas, tanto al crear una orden como después de que la posición esté abierta. El sistema debe monitorear estos niveles y ejecutar automáticamente el cierre cuando el precio los alcance.
## Mockups/Wireframes
```
┌─────────────────────────────────────────────────────────────────┐
│ CONFIGURE TP/SL - BTCUSDT LONG Position │
├─────────────────────────────────────────────────────────────────┤
│ Position Details: │
│ Size: 0.1 BTC | Entry: $95,000 | Current: $97,234.50 │
│ Current P&L: +$223.45 (+2.35%) │
│ │
│ ┌───────────────────────────────────────────────────────────┐ │
│ │ TAKE PROFIT [✓ Enable]│ │
│ ├───────────────────────────────────────────────────────────┤ │
│ │ Price: │ │
│ │ ┌─────────────────────────────────────┐ │ │
│ │ │ 100,000.00 │ │ │
│ │ └─────────────────────────────────────┘ │ │
│ │ Distance: +2.84% (+$2,765.50) │ │
│ │ [Set 1%] [Set 2%] [Set 5%] [Set 10%] │ │
│ │ │ │
│ │ Est. Profit if triggered: +$500.00 (+5.26%) │ │
│ └───────────────────────────────────────────────────────────┘ │
│ │
│ ┌───────────────────────────────────────────────────────────┐ │
│ │ STOP LOSS [✓ Enable]│ │
│ ├───────────────────────────────────────────────────────────┤ │
│ │ Price: │ │
│ │ ┌─────────────────────────────────────┐ │ │
│ │ │ 93,000.00 │ │ │
│ │ └─────────────────────────────────────┘ │ │
│ │ Distance: -4.35% (-$4,234.50) │ │
│ │ [Set 1%] [Set 2%] [Set 5%] [Set 10%] │ │
│ │ │ │
│ │ Est. Loss if triggered: -$200.00 (-2.11%) │ │
│ │ ⚠ Warning: SL is below entry price │ │
│ └───────────────────────────────────────────────────────────┘ │
│ │
│ Risk/Reward Ratio: 2.50 (Good) │
│ │
│ ┌───────────────────────────────────────────────────────────┐ │
│ │ │ │
│ │ Chart Preview: │ │
│ │ $100,000 ─────────────────── TP (Green line) │ │
│ │ $97,234 ████ Current Price │ │
│ │ $95,000 ──── Entry (Blue line) │ │
│ │ $93,000 ─────────────────── SL (Red line) │ │
│ │ │ │
│ └───────────────────────────────────────────────────────────┘ │
│ │
│ [Cancel] [Save TP/SL] │
└─────────────────────────────────────────────────────────────────┘
```
---
## Criterios de Aceptación
**Escenario 1: Configurar TP y SL en posición existente**
```gherkin
DADO que el usuario tiene posición long BTCUSDT a $95,000
Y el precio actual es $97,234.50
CUANDO abre el diálogo de TP/SL
Y habilita Take Profit en $100,000
Y habilita Stop Loss en $93,000
Y hace click en "Save"
ENTONCES se guardan los niveles
Y aparecen en el panel de posiciones
Y se muestran líneas horizontales en el chart
Y el sistema comienza a monitorear estos niveles
```
**Escenario 2: Activación automática de Take Profit**
```gherkin
DADO que la posición tiene TP en $100,000
CUANDO el precio sube y alcanza $100,000
ENTONCES se ejecuta automáticamente orden market sell
Y la posición se cierra
Y el P&L realizado es +$500.00
Y el close_reason es "take_profit"
Y se envía notificación "Take Profit triggered at $100,000"
```
**Escenario 3: Activación automática de Stop Loss**
```gherkin
DADO que la posición tiene SL en $93,000
CUANDO el precio baja y alcanza $93,000
ENTONCES se ejecuta automáticamente orden market sell
Y la posición se cierra con pérdida
Y el P&L realizado es -$200.00
Y el close_reason es "stop_loss"
Y se envía notificación "Stop Loss triggered at $93,000"
```
**Escenario 4: Validación de niveles lógicos**
```gherkin
DADO que el usuario tiene posición LONG
CUANDO intenta configurar TP=$90,000 (menor al precio actual)
ENTONCES se muestra warning "TP should be above current price for LONG"
Y permite continuar (puede ser trailing stop futuro)
CUANDO intenta configurar SL=$105,000 (mayor al precio actual)
ENTONCES se muestra warning "SL should be below current price for LONG"
```
**Escenario 5: Modificar TP/SL existentes**
```gherkin
DADO que la posición tiene TP=$100,000 y SL=$93,000
CUANDO el usuario modifica TP a $105,000
Y guarda los cambios
ENTONCES el sistema actualiza solo el TP
Y mantiene el SL en $93,000
Y las líneas en el chart se actualizan
```
**Escenario 6: Deshabilitar TP o SL**
```gherkin
DADO que la posición tiene TP y SL configurados
CUANDO el usuario deshabilita el checkbox de TP
Y guarda
ENTONCES el TP se elimina
Y solo queda activo el SL
Y la línea verde desaparece del chart
```
**Escenario 7: Mostrar Risk/Reward Ratio**
```gherkin
DADO que el usuario configura TP=$100,000 y SL=$93,000
CUANDO el sistema calcula
ENTONCES muestra Risk/Reward = 2.50
- Potencial ganancia: $500 (riesgo hacia arriba)
- Potencial pérdida: $200 (riesgo hacia abajo)
- Ratio: 500 / 200 = 2.50
Y muestra indicador "Good" si ratio > 2.0
```
## Criterios Adicionales
- [ ] Botones rápidos para configurar TP/SL en %
- [ ] Trailing Stop Loss (futuro enhancement)
- [ ] Notificación cuando el precio se acerca a TP/SL (±1%)
- [ ] Mostrar distancia a TP/SL en tiempo real
- [ ] Histórico de TP/SL activados
---
## Tareas Técnicas
**Database:**
- [ ] DB-TRD-019: Añadir campos take_profit, stop_loss a paper_positions
- [ ] DB-TRD-020: Añadir índice en (take_profit, stop_loss) para queries
**Backend:**
- [ ] BE-TRD-064: Crear endpoint PATCH /trading/paper/positions/:id/tp-sl
- [ ] BE-TRD-065: Implementar PositionService.updateTPSL()
- [ ] BE-TRD-066: Implementar TPSLMonitorService (background job)
- [ ] BE-TRD-067: Implementar lógica de activación de TP
- [ ] BE-TRD-068: Implementar lógica de activación de SL
- [ ] BE-TRD-069: Integrar con PositionService.closePosition()
**Frontend:**
- [ ] FE-TRD-064: Crear componente ConfigureTPSLDialog.tsx
- [ ] FE-TRD-065: Crear componente TPSLInput.tsx
- [ ] FE-TRD-066: Crear componente RiskRewardIndicator.tsx
- [ ] FE-TRD-067: Añadir líneas de TP/SL en TradingChart
- [ ] FE-TRD-068: Implementar hook useConfigureTPSL
- [ ] FE-TRD-069: Actualizar PositionRow con indicadores de TP/SL
**Tests:**
- [ ] TEST-TRD-031: Test unitario cálculo risk/reward
- [ ] TEST-TRD-032: Test integración activación TP/SL
- [ ] TEST-TRD-033: Test E2E flujo completo TP/SL
---
## Dependencias
**Depende de:**
- [ ] US-TRD-009: Ver posiciones - Estado: Pendiente
- [ ] US-TRD-008: Cerrar posición - Estado: Pendiente
**Bloquea:**
- Ninguna
---
## Notas Técnicas
**Endpoints involucrados:**
| Método | Endpoint | Descripción |
|--------|----------|-------------|
| PATCH | /trading/paper/positions/:id/tp-sl | Configurar/actualizar TP/SL |
| DELETE | /trading/paper/positions/:id/tp-sl | Eliminar TP/SL |
**Entidades/Tablas:**
```sql
ALTER TABLE trading.paper_positions
ADD COLUMN take_profit DECIMAL(20, 8),
ADD COLUMN stop_loss DECIMAL(20, 8);
CREATE INDEX idx_positions_tp_sl
ON trading.paper_positions(take_profit, stop_loss)
WHERE take_profit IS NOT NULL OR stop_loss IS NOT NULL;
```
**Componentes UI:**
- `ConfigureTPSLDialog`: Modal de configuración
- `TPSLInput`: Input con validación
- `RiskRewardIndicator`: Indicador de ratio
- `TPSLLines`: Líneas horizontales en chart
- `QuickPercentButtons`: Botones de % rápidos
**Request Body:**
```typescript
{
takeProfit: 100000.00, // null para deshabilitar
stopLoss: 93000.00 // null para deshabilitar
}
```
**Response:**
```typescript
{
position: {
id: "uuid",
symbol: "BTCUSDT",
side: "long",
quantity: 0.1,
entryPrice: 95000.00,
currentPrice: 97234.50,
takeProfit: 100000.00,
stopLoss: 93000.00,
riskRewardRatio: 2.50
},
preview: {
distanceToTP: 2.84,
distanceToSL: -4.35,
potentialProfit: 500.00,
potentialLoss: -200.00,
riskRewardRatio: 2.50
}
}
```
**TP/SL Monitor Logic (Background Job - cada segundo):**
```typescript
// Para posición LONG
const positions = await getPositionsWithTPSL();
for (const position of positions) {
const currentPrice = await getCurrentPrice(position.symbol);
// Check Take Profit
if (position.takeProfit && currentPrice >= position.takeProfit) {
await closePosition(position.id, 'take_profit');
await sendNotification(`TP triggered at ${currentPrice}`);
}
// Check Stop Loss
if (position.stopLoss && currentPrice <= position.stopLoss) {
await closePosition(position.id, 'stop_loss');
await sendNotification(`SL triggered at ${currentPrice}`);
}
}
// Para posición SHORT (lógica inversa)
// TP se activa cuando currentPrice <= takeProfit
// SL se activa cuando currentPrice >= stopLoss
```
**Cálculos:**
```typescript
// Risk/Reward Ratio
const potentialProfit = Math.abs(takeProfit - entryPrice) * quantity;
const potentialLoss = Math.abs(entryPrice - stopLoss) * quantity;
const riskRewardRatio = potentialProfit / potentialLoss;
// Distance to TP/SL (%)
const distanceToTP = ((takeProfit - currentPrice) / currentPrice) * 100;
const distanceToSL = ((stopLoss - currentPrice) / currentPrice) * 100;
// Validaciones para LONG
const validTPForLong = takeProfit > currentPrice;
const validSLForLong = stopLoss < currentPrice;
// Validaciones para SHORT
const validTPForShort = takeProfit < currentPrice;
const validSLForShort = stopLoss > currentPrice;
```
**Quick Percentage Buttons:**
```typescript
// Para posición LONG, TP
const tp1Percent = currentPrice * 1.01; // +1%
const tp2Percent = currentPrice * 1.02; // +2%
const tp5Percent = currentPrice * 1.05; // +5%
const tp10Percent = currentPrice * 1.10; // +10%
// Para posición LONG, SL
const sl1Percent = currentPrice * 0.99; // -1%
const sl2Percent = currentPrice * 0.98; // -2%
const sl5Percent = currentPrice * 0.95; // -5%
const sl10Percent = currentPrice * 0.90; // -10%
```
---
## Definition of Ready (DoR)
- [x] Historia claramente escrita
- [x] Criterios de aceptación definidos
- [x] Story points estimados
- [x] Dependencias identificadas
- [x] Sin bloqueadores
- [ ] Diseño/mockup disponible
- [ ] API spec disponible
## Definition of Done (DoD)
- [ ] Código implementado según criterios
- [ ] Tests unitarios escritos y pasando
- [ ] Tests de integración pasando
- [ ] Code review aprobado
- [ ] Documentación actualizada
- [ ] QA aprobado
- [ ] Desplegado en ambiente de pruebas
---
## Historial de Cambios
| Fecha | Cambio | Autor |
|-------|--------|-------|
| 2025-12-05 | Creación | Requirements-Analyst |
---
**Creada por:** Requirements-Analyst
**Fecha:** 2025-12-05
**Última actualización:** 2025-12-05