# Implementer evidence — CLUB-003 ## Resumen Implementé la integración del Club en el TPV: resolución de socio por código, acumulación de cashback en ledger idempotente y campos de respuesta en venta POS. ## Qué se añadió ### 1) Endpoint de resolución de socio - `GET /club/resolve?memberCode=MDV-XXXXXXXX` en `project/src/modules/club/api/club.routes.ts` - Método `resolveByCode` en `ClubService` - Método `findMemberByCode` en `PgClubRepository` (solo socios activos) ### 2) Integración de cashback en venta POS - `PosSaleInput` ahora acepta `clubMemberId?: string` (domain type) - `PosSaleResult` ahora devuelve `clubEarnedCents` y `clubMemberCode` - `CreatePosSaleUseCase`: - Al completar una venta (orderState === 'COMPLETED'), si hay `clubMemberId`: - Consulta `club_enabled` y `club_cashback_bps` de `store_settings` - Calcula `cashbackCents = round(totalCents * cashbackBps / 10_000)` - Inserta transacción de ledger idempotente con `idempotency_key = club-earn-${orderId}` dentro de la misma transacción DB que la venta - Si la insercción falla, continúa sin bloquear la venta (fail-safe) - `loadResult` recupera el `clubEarnedCents` del ledger al recargar una venta por idempotency key - `receive-rest-payment.ts` devuelve `clubEarnedCents: 0` (pagos adicionales no re-acumulan cashback) ### 3) API del TPV - El body de `POST /pos/sales` acepta `clubMemberId` con validación UUID - La respuesta de venta incluye `clubEarnedCents` y `clubMemberCode` ### 4) Tipos frontend - `PosSaleResponse` en `apps/pos/src/types/checkout.ts` incluye `clubEarnedCents` y `clubMemberCode` ## Decisiones técnicas - El cashback se acumula **solo cuando la venta pasa a COMPLETED**, no en ventas PENDING. - Si la escritura de ledger falla, la venta sigue adelante (fail-safe). - El idempotency key del ledger incluye el `orderId` (`club-earn-${orderId}`), garantizando una única acumulación por venta. - El `loadResult` recupera el cashback del ledger para mantener consistencia en respuestas por idempotency. ## Validación ejecutada - `cd project && npm run typecheck` ✅ - `cd project && npm run build` ✅ - `cd project/apps/pos && npm run build` ✅ - `./scripts/verify.sh` ✅ - `cd project && npx vitest run src/modules/pos/tests/payment-allocation.test.ts` ✅ - `cd project && npx vitest run src/modules/club/tests/` ✅ - `git diff --check` ✅ ## Riesgos / siguiente paso - CLUB-004 debe implementar el flujo de devolución TPV que revierte el cashback acumulado cuando se reintegran artículos. - El frontend TPV (interfaz de búsqueda de socio Club) queda pendiente de implementar en la UI del terminal; los campos del endpoint ya están listos.