998 lines
29 KiB
YAML
998 lines
29 KiB
YAML
# GRAFO DE DEPENDENCIAS VALIDADO - RETAIL
|
|
# Fecha: 2025-12-18
|
|
# Fase: 4 - Validacion
|
|
|
|
metadata:
|
|
version: "1.0"
|
|
proyecto: erp-suite/retail
|
|
total_modulos: 10
|
|
total_entidades: 56
|
|
total_servicios: 48
|
|
|
|
# ============================================================
|
|
# MODULOS CORE (PRERREQUISITOS)
|
|
# ============================================================
|
|
|
|
core_modules:
|
|
MGN-001-auth:
|
|
nombre: "Autenticacion"
|
|
estado: 40%
|
|
requerido: 100%
|
|
bloqueante: true
|
|
entidades:
|
|
- name: tenants
|
|
schema: auth
|
|
estado: existe
|
|
usado_por: [todos]
|
|
- name: users
|
|
schema: auth
|
|
estado: existe
|
|
usado_por: [RT-001, RT-002, RT-007]
|
|
- name: roles
|
|
schema: auth
|
|
estado: parcial
|
|
usado_por: [RT-001]
|
|
- name: permissions
|
|
schema: auth
|
|
estado: no_existe
|
|
usado_por: [RT-001]
|
|
- name: user_roles
|
|
schema: auth
|
|
estado: no_existe
|
|
usado_por: [RT-001]
|
|
servicios:
|
|
- name: AuthService
|
|
estado: parcial
|
|
metodos_faltantes: [validatePermission, refreshToken]
|
|
- name: PermissionsService
|
|
estado: no_existe
|
|
dependencias: []
|
|
|
|
MGN-005-catalogs:
|
|
nombre: "Catalogos"
|
|
estado: 0%
|
|
requerido: 100%
|
|
bloqueante: true
|
|
entidades:
|
|
- name: countries
|
|
schema: core
|
|
estado: no_existe
|
|
usado_por: [MGN-012]
|
|
- name: currencies
|
|
schema: core
|
|
estado: no_existe
|
|
usado_por: [RT-006, RT-010]
|
|
- name: uom_categories
|
|
schema: core
|
|
estado: no_existe
|
|
usado_por: [MGN-011]
|
|
- name: uom
|
|
schema: core
|
|
estado: no_existe
|
|
usado_por: [MGN-011, RT-010]
|
|
- name: sequences
|
|
schema: core
|
|
estado: no_existe
|
|
usado_por: [RT-002, RT-003, RT-004, RT-009, RT-010]
|
|
servicios:
|
|
- name: CountriesService
|
|
estado: no_existe
|
|
- name: CurrenciesService
|
|
estado: no_existe
|
|
- name: UoMService
|
|
estado: no_existe
|
|
- name: SequencesService
|
|
estado: no_existe
|
|
dependencias: []
|
|
|
|
MGN-010-financial:
|
|
nombre: "Financiero"
|
|
estado: 70%
|
|
requerido: 90%
|
|
bloqueante: true
|
|
entidades:
|
|
- name: tax_groups
|
|
schema: financial
|
|
estado: no_existe
|
|
usado_por: [RT-010]
|
|
- name: taxes
|
|
schema: financial
|
|
estado: existe
|
|
usado_por: [RT-006, RT-010]
|
|
- name: accounts
|
|
schema: financial
|
|
estado: existe
|
|
usado_por: []
|
|
- name: journals
|
|
schema: financial
|
|
estado: existe
|
|
usado_por: []
|
|
- name: payment_methods
|
|
schema: financial
|
|
estado: no_existe
|
|
usado_por: [RT-002, RT-009]
|
|
servicios:
|
|
- name: TaxesService
|
|
estado: parcial
|
|
nota: "Migrar a TypeORM"
|
|
- name: PaymentMethodsService
|
|
estado: no_existe
|
|
dependencias: [MGN-001-auth]
|
|
|
|
MGN-011-inventory:
|
|
nombre: "Inventario"
|
|
estado: 60%
|
|
requerido: 80%
|
|
bloqueante: true
|
|
entidades:
|
|
- name: product_categories
|
|
schema: inventory
|
|
estado: existe
|
|
usado_por: [RT-006]
|
|
- name: products
|
|
schema: inventory
|
|
estado: existe
|
|
usado_por: [RT-002, RT-003, RT-004, RT-006, RT-009, RT-010]
|
|
- name: warehouses
|
|
schema: inventory
|
|
estado: existe
|
|
usado_por: [RT-001, RT-003]
|
|
- name: stock_quants
|
|
schema: inventory
|
|
estado: parcial
|
|
usado_por: [RT-003, RT-008]
|
|
servicios:
|
|
- name: ProductsService
|
|
estado: existe
|
|
- name: WarehousesService
|
|
estado: existe
|
|
- name: StockService
|
|
estado: parcial
|
|
nota: "Falta reservar/liberar stock"
|
|
dependencias: [MGN-001-auth, MGN-005-catalogs]
|
|
|
|
MGN-012-partners:
|
|
nombre: "Partners"
|
|
estado: 50%
|
|
requerido: 80%
|
|
bloqueante: false
|
|
entidades:
|
|
- name: partners
|
|
schema: core
|
|
estado: parcial
|
|
usado_por: [RT-002, RT-004, RT-005, RT-009, RT-010]
|
|
servicios:
|
|
- name: PartnersService
|
|
estado: parcial
|
|
metodos_faltantes: [getCustomers, getSuppliers]
|
|
dependencias: [MGN-001-auth, MGN-005-catalogs]
|
|
|
|
MGN-013-sales:
|
|
nombre: "Ventas"
|
|
estado: 50%
|
|
requerido: 70%
|
|
bloqueante: true
|
|
entidades:
|
|
- name: pricelists
|
|
schema: sales
|
|
estado: no_existe
|
|
usado_por: [RT-006]
|
|
- name: pricelist_items
|
|
schema: sales
|
|
estado: no_existe
|
|
usado_por: [RT-006]
|
|
servicios:
|
|
- name: PricelistsService
|
|
estado: no_existe
|
|
dependencias: [MGN-001-auth, MGN-011-inventory]
|
|
|
|
# ============================================================
|
|
# MODULOS RETAIL
|
|
# ============================================================
|
|
|
|
retail_modules:
|
|
RT-001-fundamentos:
|
|
nombre: "Fundamentos Retail"
|
|
prioridad: P0
|
|
story_points: 0
|
|
herencia: 100%
|
|
sprint: 5
|
|
entidades:
|
|
- name: branches
|
|
schema: retail
|
|
estado: planificado
|
|
columnas: [id, tenant_id, code, name, address, phone, email, warehouse_id, is_active, is_main, config]
|
|
foreign_keys:
|
|
- column: tenant_id
|
|
references: auth.tenants(id)
|
|
- column: warehouse_id
|
|
references: inventory.warehouses(id)
|
|
indices: [tenant_id]
|
|
rls: true
|
|
|
|
- name: cash_registers
|
|
schema: retail
|
|
estado: planificado
|
|
columnas: [id, tenant_id, branch_id, code, name, is_active, default_payment_method, config]
|
|
foreign_keys:
|
|
- column: tenant_id
|
|
references: auth.tenants(id)
|
|
- column: branch_id
|
|
references: retail.branches(id)
|
|
indices: [branch_id]
|
|
rls: true
|
|
|
|
- name: branch_users
|
|
schema: retail
|
|
estado: planificado
|
|
columnas: [id, tenant_id, branch_id, user_id, role, is_primary]
|
|
foreign_keys:
|
|
- column: tenant_id
|
|
references: auth.tenants(id)
|
|
- column: branch_id
|
|
references: retail.branches(id)
|
|
- column: user_id
|
|
references: auth.users(id)
|
|
indices: [user_id]
|
|
unique: [tenant_id, branch_id, user_id]
|
|
rls: true
|
|
|
|
servicios:
|
|
- name: BranchesService
|
|
tipo: nuevo
|
|
metodos: [create, findAll, findById, update, delete, getByTenant]
|
|
- name: CashRegistersService
|
|
tipo: nuevo
|
|
metodos: [create, findByBranch, activate, deactivate]
|
|
- name: BranchUsersService
|
|
tipo: nuevo
|
|
metodos: [assign, remove, getByUser, getByBranch]
|
|
|
|
dependencias:
|
|
core: [MGN-001-auth, MGN-011-inventory]
|
|
retail: []
|
|
|
|
RT-002-pos:
|
|
nombre: "Punto de Venta"
|
|
prioridad: P0
|
|
story_points: 55
|
|
herencia: 20%
|
|
sprint: [8, 9, 10, 11]
|
|
entidades:
|
|
- name: pos_sessions
|
|
schema: retail
|
|
estado: planificado
|
|
columnas: [id, tenant_id, branch_id, register_id, user_id, status, opening_balance, closing_balance, opened_at, closed_at, notes]
|
|
foreign_keys:
|
|
- column: tenant_id
|
|
references: auth.tenants(id)
|
|
- column: branch_id
|
|
references: retail.branches(id)
|
|
- column: register_id
|
|
references: retail.cash_registers(id)
|
|
- column: user_id
|
|
references: auth.users(id)
|
|
indices: [branch_id, user_id, status]
|
|
rls: true
|
|
|
|
- name: pos_orders
|
|
schema: retail
|
|
estado: planificado
|
|
columnas: [id, tenant_id, session_id, order_number, customer_id, status, order_date, subtotal, discount_amount, tax_amount, total, notes, offline_id, synced_at, is_invoiced, invoice_id]
|
|
foreign_keys:
|
|
- column: tenant_id
|
|
references: auth.tenants(id)
|
|
- column: session_id
|
|
references: retail.pos_sessions(id)
|
|
- column: customer_id
|
|
references: core.partners(id)
|
|
indices: [session_id, customer_id, order_date, offline_id]
|
|
unique: [tenant_id, order_number]
|
|
rls: true
|
|
|
|
- name: pos_order_lines
|
|
schema: retail
|
|
estado: planificado
|
|
columnas: [id, tenant_id, order_id, product_id, product_name, quantity, unit_price, discount_percent, discount_amount, tax_amount, total, notes]
|
|
foreign_keys:
|
|
- column: tenant_id
|
|
references: auth.tenants(id)
|
|
- column: order_id
|
|
references: retail.pos_orders(id)
|
|
- column: product_id
|
|
references: inventory.products(id)
|
|
indices: [product_id]
|
|
rls: true
|
|
|
|
- name: pos_payments
|
|
schema: retail
|
|
estado: planificado
|
|
columnas: [id, tenant_id, order_id, payment_method, amount, received_amount, change_amount, reference, card_last_four, authorization_code]
|
|
foreign_keys:
|
|
- column: tenant_id
|
|
references: auth.tenants(id)
|
|
- column: order_id
|
|
references: retail.pos_orders(id)
|
|
indices: [order_id]
|
|
rls: true
|
|
|
|
servicios:
|
|
- name: POSSessionService
|
|
tipo: nuevo
|
|
metodos: [openSession, closeSession, getActiveSession, getSummary]
|
|
dependencias: [CashRegistersService]
|
|
- name: POSOrderService
|
|
tipo: nuevo
|
|
metodos: [createOrder, addLine, updateLine, removeLine, setCustomer, applyDiscount, confirmOrder, refundOrder, cancelOrder]
|
|
dependencias: [PriceEngineService, RetailStockService, LoyaltyService]
|
|
- name: POSPaymentService
|
|
tipo: nuevo
|
|
metodos: [addPayment, processPayments, calculateChange]
|
|
- name: POSSyncService
|
|
tipo: nuevo
|
|
metodos: [syncOfflineOrders, getByOfflineId]
|
|
dependencias: [POSOrderService]
|
|
|
|
controllers:
|
|
- name: POSController
|
|
endpoints:
|
|
- POST /pos/sessions/open
|
|
- GET /pos/sessions/active
|
|
- POST /pos/sessions/:id/close
|
|
- POST /pos/orders
|
|
- POST /pos/orders/:id/lines
|
|
- POST /pos/orders/:id/confirm
|
|
- POST /pos/orders/:id/refund
|
|
- POST /pos/sync
|
|
|
|
gateways:
|
|
- name: POSGateway
|
|
namespace: /pos
|
|
events: [sync:orders, order:created, session:updated]
|
|
|
|
frontend:
|
|
pages:
|
|
- path: /login
|
|
componentes: [LoginForm, BranchSelector]
|
|
- path: /select-register
|
|
componentes: [RegisterList]
|
|
- path: /open-session
|
|
componentes: [OpenSessionForm]
|
|
- path: /sales
|
|
componentes: [ProductSearch, CategoryTabs, ProductGrid, OrderLines, OrderTotals, CustomerSelector]
|
|
- path: /sales/checkout
|
|
componentes: [PaymentMethodButton, CashPaymentInput, CardPaymentInput, PointsRedemption, PaymentsList]
|
|
- path: /history
|
|
componentes: [OrderHistoryList]
|
|
- path: /offline
|
|
componentes: [SyncQueue, SyncStatus]
|
|
|
|
dependencias:
|
|
core: [MGN-001-auth, MGN-010-financial, MGN-011-inventory, MGN-012-partners]
|
|
retail: [RT-001-fundamentos, RT-006-precios, RT-003-inventario, RT-005-clientes]
|
|
|
|
RT-003-inventario:
|
|
nombre: "Inventario Multi-sucursal"
|
|
prioridad: P0
|
|
story_points: 42
|
|
herencia: 60%
|
|
sprint: 7
|
|
entidades:
|
|
- name: stock_transfers
|
|
schema: retail
|
|
estado: planificado
|
|
columnas: [id, tenant_id, transfer_number, source_branch_id, dest_branch_id, status, requested_by, confirmed_by, received_by, requested_date, confirmed_date, received_date, notes]
|
|
foreign_keys:
|
|
- column: source_branch_id
|
|
references: retail.branches(id)
|
|
- column: dest_branch_id
|
|
references: retail.branches(id)
|
|
indices: [source_branch_id, dest_branch_id, status]
|
|
unique: [tenant_id, transfer_number]
|
|
rls: true
|
|
|
|
- name: stock_transfer_lines
|
|
schema: retail
|
|
estado: planificado
|
|
foreign_keys:
|
|
- column: transfer_id
|
|
references: retail.stock_transfers(id)
|
|
- column: product_id
|
|
references: inventory.products(id)
|
|
rls: true
|
|
|
|
- name: stock_adjustments
|
|
schema: retail
|
|
estado: planificado
|
|
foreign_keys:
|
|
- column: branch_id
|
|
references: retail.branches(id)
|
|
indices: [branch_id]
|
|
unique: [tenant_id, adjustment_number]
|
|
rls: true
|
|
|
|
- name: stock_adjustment_lines
|
|
schema: retail
|
|
estado: planificado
|
|
foreign_keys:
|
|
- column: adjustment_id
|
|
references: retail.stock_adjustments(id)
|
|
- column: product_id
|
|
references: inventory.products(id)
|
|
rls: true
|
|
|
|
views:
|
|
- name: branch_stock
|
|
schema: retail
|
|
tipo: view
|
|
descripcion: "Vista de stock por sucursal"
|
|
tablas_fuente: [inventory.stock_quants, retail.branches, inventory.products]
|
|
|
|
servicios:
|
|
- name: RetailStockService
|
|
tipo: extendido
|
|
extiende: StockService
|
|
metodos: [getStockByBranch, getMultiBranchStock, decrementStock, incrementStock]
|
|
- name: TransfersService
|
|
tipo: nuevo
|
|
metodos: [createTransfer, confirmTransfer, sendTransfer, receiveTransfer, cancelTransfer]
|
|
- name: AdjustmentsService
|
|
tipo: nuevo
|
|
metodos: [createAdjustment, confirmAdjustment, cancelAdjustment]
|
|
|
|
dependencias:
|
|
core: [MGN-011-inventory]
|
|
retail: [RT-001-fundamentos]
|
|
|
|
RT-004-compras:
|
|
nombre: "Compras y Reabastecimiento"
|
|
prioridad: P1
|
|
story_points: 38
|
|
herencia: 80%
|
|
sprint: 15
|
|
entidades:
|
|
- name: purchase_suggestions
|
|
schema: retail
|
|
estado: planificado
|
|
rls: true
|
|
|
|
- name: supplier_orders
|
|
schema: retail
|
|
estado: planificado
|
|
foreign_keys:
|
|
- column: supplier_id
|
|
references: core.partners(id)
|
|
- column: branch_id
|
|
references: retail.branches(id)
|
|
rls: true
|
|
|
|
- name: supplier_order_lines
|
|
schema: retail
|
|
estado: planificado
|
|
foreign_keys:
|
|
- column: order_id
|
|
references: retail.supplier_orders(id)
|
|
- column: product_id
|
|
references: inventory.products(id)
|
|
rls: true
|
|
|
|
- name: goods_receipts
|
|
schema: retail
|
|
estado: planificado
|
|
foreign_keys:
|
|
- column: supplier_order_id
|
|
references: retail.supplier_orders(id)
|
|
- column: branch_id
|
|
references: retail.branches(id)
|
|
rls: true
|
|
|
|
- name: goods_receipt_lines
|
|
schema: retail
|
|
estado: planificado
|
|
rls: true
|
|
|
|
servicios:
|
|
- name: RetailPurchaseService
|
|
tipo: extendido
|
|
extiende: PurchaseService
|
|
metodos: [suggestRestock, createFromSuggestion]
|
|
- name: PurchaseSuggestionsService
|
|
tipo: nuevo
|
|
metodos: [generate, getByBranch, markOrdered, markIgnored]
|
|
- name: GoodsReceiptService
|
|
tipo: nuevo
|
|
metodos: [createReceipt, confirmReceipt, cancelReceipt]
|
|
|
|
dependencias:
|
|
core: [MGN-011-inventory, MGN-012-partners]
|
|
retail: [RT-001-fundamentos, RT-003-inventario]
|
|
|
|
RT-005-clientes:
|
|
nombre: "Clientes y Lealtad"
|
|
prioridad: P1
|
|
story_points: 34
|
|
herencia: 40%
|
|
sprint: 14
|
|
entidades:
|
|
- name: loyalty_programs
|
|
schema: retail
|
|
estado: planificado
|
|
rls: true
|
|
|
|
- name: membership_levels
|
|
schema: retail
|
|
estado: planificado
|
|
foreign_keys:
|
|
- column: program_id
|
|
references: retail.loyalty_programs(id)
|
|
rls: true
|
|
|
|
- name: loyalty_transactions
|
|
schema: retail
|
|
estado: planificado
|
|
foreign_keys:
|
|
- column: customer_id
|
|
references: core.partners(id)
|
|
- column: program_id
|
|
references: retail.loyalty_programs(id)
|
|
- column: order_id
|
|
references: retail.pos_orders(id)
|
|
indices: [customer_id, created_at]
|
|
rls: true
|
|
|
|
- name: customer_memberships
|
|
schema: retail
|
|
estado: planificado
|
|
foreign_keys:
|
|
- column: customer_id
|
|
references: core.partners(id)
|
|
- column: program_id
|
|
references: retail.loyalty_programs(id)
|
|
- column: level_id
|
|
references: retail.membership_levels(id)
|
|
unique: [tenant_id, membership_number]
|
|
rls: true
|
|
|
|
servicios:
|
|
- name: RetailCustomersService
|
|
tipo: extendido
|
|
extiende: PartnersService
|
|
metodos: [createCustomer, getWithMembership, searchByPhone]
|
|
- name: LoyaltyService
|
|
tipo: nuevo
|
|
metodos: [enrollCustomer, earnPoints, redeemPoints, getBalance, getHistory, checkLevelUpgrade]
|
|
|
|
dependencias:
|
|
core: [MGN-012-partners]
|
|
retail: [RT-001-fundamentos, RT-002-pos]
|
|
|
|
RT-006-precios:
|
|
nombre: "Precios y Promociones"
|
|
prioridad: P0
|
|
story_points: 36
|
|
herencia: 30%
|
|
sprint: 6
|
|
entidades:
|
|
- name: promotions
|
|
schema: retail
|
|
estado: planificado
|
|
indices: [is_active, start_date, end_date, branch_ids]
|
|
rls: true
|
|
|
|
- name: promotion_products
|
|
schema: retail
|
|
estado: planificado
|
|
foreign_keys:
|
|
- column: promotion_id
|
|
references: retail.promotions(id)
|
|
- column: product_id
|
|
references: inventory.products(id)
|
|
- column: category_id
|
|
references: inventory.product_categories(id)
|
|
rls: true
|
|
|
|
- name: coupons
|
|
schema: retail
|
|
estado: planificado
|
|
foreign_keys:
|
|
- column: customer_id
|
|
references: core.partners(id)
|
|
indices: [code, valid_from, valid_until]
|
|
unique: [tenant_id, code]
|
|
rls: true
|
|
|
|
- name: coupon_redemptions
|
|
schema: retail
|
|
estado: planificado
|
|
foreign_keys:
|
|
- column: coupon_id
|
|
references: retail.coupons(id)
|
|
- column: order_id
|
|
references: retail.pos_orders(id)
|
|
rls: true
|
|
|
|
servicios:
|
|
- name: PriceEngineService
|
|
tipo: nuevo
|
|
metodos: [calculatePrice, applyPricelist, evaluatePromotions, evaluateVolumeDiscount]
|
|
dependencias: [PricelistsService, PromotionsService, CouponsService]
|
|
- name: PromotionsService
|
|
tipo: nuevo
|
|
metodos: [create, update, activate, deactivate, getActiveForProduct, incrementUse]
|
|
- name: CouponsService
|
|
tipo: nuevo
|
|
metodos: [generate, validate, redeem, getByCode]
|
|
|
|
dependencias:
|
|
core: [MGN-011-inventory, MGN-013-sales]
|
|
retail: [RT-001-fundamentos]
|
|
|
|
RT-007-caja:
|
|
nombre: "Caja y Cortes"
|
|
prioridad: P0
|
|
story_points: 28
|
|
herencia: 10%
|
|
sprint: 10
|
|
entidades:
|
|
- name: cash_movements
|
|
schema: retail
|
|
estado: planificado
|
|
foreign_keys:
|
|
- column: session_id
|
|
references: retail.pos_sessions(id)
|
|
- column: authorized_by
|
|
references: auth.users(id)
|
|
indices: [session_id]
|
|
rls: true
|
|
|
|
- name: cash_closings
|
|
schema: retail
|
|
estado: planificado
|
|
columnas_generadas:
|
|
- name: cash_difference
|
|
formula: "declared_cash - expected_cash"
|
|
- name: card_difference
|
|
formula: "declared_card - expected_card"
|
|
- name: transfer_difference
|
|
formula: "declared_transfer - expected_transfer"
|
|
foreign_keys:
|
|
- column: session_id
|
|
references: retail.pos_sessions(id)
|
|
unique: [session_id]
|
|
indices: [closing_date]
|
|
rls: true
|
|
|
|
- name: cash_counts
|
|
schema: retail
|
|
estado: planificado
|
|
columnas_generadas:
|
|
- name: difference
|
|
formula: "counted_amount - expected_amount"
|
|
foreign_keys:
|
|
- column: session_id
|
|
references: retail.pos_sessions(id)
|
|
indices: [session_id]
|
|
rls: true
|
|
|
|
servicios:
|
|
- name: CashSessionService
|
|
tipo: nuevo
|
|
metodos: [getSummary, calculateExpected]
|
|
dependencias: [POSSessionService]
|
|
- name: CashMovementService
|
|
tipo: nuevo
|
|
metodos: [createIn, createOut, getBySession, validateAuthorization]
|
|
- name: CashClosingService
|
|
tipo: nuevo
|
|
metodos: [prepareClosing, createClosing, approveClosing, rejectClosing]
|
|
|
|
dependencias:
|
|
core: [MGN-001-auth]
|
|
retail: [RT-001-fundamentos, RT-002-pos]
|
|
|
|
RT-008-reportes:
|
|
nombre: "Reportes y Dashboard"
|
|
prioridad: P1
|
|
story_points: 30
|
|
herencia: 70%
|
|
sprint: 16
|
|
materialized_views:
|
|
- name: mv_daily_sales
|
|
schema: retail
|
|
refresh: "hourly"
|
|
indices: [sale_date, tenant_id, branch_id, cashier_id]
|
|
|
|
- name: mv_product_sales
|
|
schema: retail
|
|
refresh: "hourly"
|
|
indices: [product_id, tenant_id, branch_id, sale_month]
|
|
|
|
- name: mv_branch_stock_summary
|
|
schema: retail
|
|
refresh: "hourly"
|
|
indices: [tenant_id, branch_id]
|
|
|
|
servicios:
|
|
- name: DashboardService
|
|
tipo: nuevo
|
|
metodos: [getDashboard, getKPIs, getCharts, getAlerts]
|
|
- name: SalesReportService
|
|
tipo: extendido
|
|
extiende: ReportsService
|
|
metodos: [generate, getByPeriod, getSalesByHour, getSalesByCashier]
|
|
- name: ProductReportService
|
|
tipo: nuevo
|
|
metodos: [getTopSelling, getSlowMoving, getABCAnalysis]
|
|
- name: CashReportService
|
|
tipo: nuevo
|
|
metodos: [getClosingsReport, getDifferencesReport]
|
|
- name: ExportService
|
|
tipo: nuevo
|
|
metodos: [toExcel, toPDF]
|
|
|
|
dependencias:
|
|
core: []
|
|
retail: [RT-002-pos, RT-003-inventario, RT-005-clientes, RT-007-caja]
|
|
|
|
RT-009-ecommerce:
|
|
nombre: "E-commerce"
|
|
prioridad: P2
|
|
story_points: 55
|
|
herencia: 20%
|
|
sprint: [17, 18, 19, 20]
|
|
entidades:
|
|
- name: carts
|
|
schema: retail
|
|
estado: planificado
|
|
foreign_keys:
|
|
- column: customer_id
|
|
references: core.partners(id)
|
|
indices: [customer_id, session_id, expires_at]
|
|
rls: true
|
|
|
|
- name: cart_items
|
|
schema: retail
|
|
estado: planificado
|
|
foreign_keys:
|
|
- column: cart_id
|
|
references: retail.carts(id)
|
|
- column: product_id
|
|
references: inventory.products(id)
|
|
rls: true
|
|
|
|
- name: ecommerce_orders
|
|
schema: retail
|
|
estado: planificado
|
|
foreign_keys:
|
|
- column: customer_id
|
|
references: core.partners(id)
|
|
- column: pickup_branch_id
|
|
references: retail.branches(id)
|
|
indices: [customer_id, status, order_date]
|
|
unique: [tenant_id, order_number]
|
|
rls: true
|
|
|
|
- name: ecommerce_order_lines
|
|
schema: retail
|
|
estado: planificado
|
|
foreign_keys:
|
|
- column: order_id
|
|
references: retail.ecommerce_orders(id)
|
|
- column: product_id
|
|
references: inventory.products(id)
|
|
rls: true
|
|
|
|
- name: shipping_rates
|
|
schema: retail
|
|
estado: planificado
|
|
rls: true
|
|
|
|
servicios:
|
|
- name: CatalogService
|
|
tipo: nuevo
|
|
metodos: [search, getProduct, getByCategory, getRelated]
|
|
- name: CartService
|
|
tipo: nuevo
|
|
metodos: [getOrCreateCart, addItem, updateItem, removeItem, clear, mergeGuestCart]
|
|
- name: CheckoutService
|
|
tipo: nuevo
|
|
metodos: [validate, calculateTotals, complete]
|
|
dependencias: [CartService, PriceEngineService, RetailStockService]
|
|
- name: PaymentGatewayService
|
|
tipo: nuevo
|
|
metodos: [createPayment, capturePayment, refund, handleWebhook]
|
|
providers: [StripeGateway, ConektaGateway, MercadoPagoGateway]
|
|
- name: ShippingService
|
|
tipo: nuevo
|
|
metodos: [calculateRates, createShipment, getTracking]
|
|
providers: [FedexProvider, DHLProvider]
|
|
- name: EcommerceOrderService
|
|
tipo: nuevo
|
|
metodos: [create, updateStatus, getByCustomer, markAsShipped]
|
|
|
|
controllers:
|
|
- name: StorefrontController
|
|
endpoints:
|
|
- GET /store/products
|
|
- GET /store/products/:id
|
|
- GET /store/products/search
|
|
- GET /store/categories
|
|
- GET /store/cart
|
|
- POST /store/cart/items
|
|
- PUT /store/cart/items/:id
|
|
- DELETE /store/cart/items/:id
|
|
- POST /store/checkout/validate
|
|
- GET /store/checkout/shipping-rates
|
|
- POST /store/checkout/complete
|
|
- POST /store/payments/create
|
|
- POST /store/payments/webhook
|
|
- GET /store/orders
|
|
- GET /store/orders/:id
|
|
|
|
- name: EcommerceAdminController
|
|
endpoints:
|
|
- GET /ecommerce/orders
|
|
- PUT /ecommerce/orders/:id/status
|
|
- POST /ecommerce/orders/:id/ship
|
|
- GET /ecommerce/shipping-rates
|
|
- POST /ecommerce/shipping-rates
|
|
|
|
dependencias:
|
|
core: [MGN-011-inventory, MGN-012-partners]
|
|
retail: [RT-001-fundamentos, RT-003-inventario, RT-005-clientes, RT-006-precios]
|
|
|
|
RT-010-facturacion:
|
|
nombre: "Facturacion CFDI 4.0"
|
|
prioridad: P0
|
|
story_points: 35
|
|
herencia: 60%
|
|
sprint: [12, 13]
|
|
entidades:
|
|
- name: cfdi_config
|
|
schema: retail
|
|
estado: planificado
|
|
unique: [tenant_id]
|
|
rls: true
|
|
|
|
- name: cfdis
|
|
schema: retail
|
|
estado: planificado
|
|
foreign_keys:
|
|
- column: source_id
|
|
references: dynamic
|
|
nota: "pos_orders o ecommerce_orders segun source_type"
|
|
indices: [source_type, source_id, uuid, fecha_emision, receptor_rfc, status]
|
|
unique: [tenant_id, uuid]
|
|
rls: true
|
|
|
|
servicios:
|
|
- name: CFDIService
|
|
tipo: nuevo
|
|
metodos: [generateFromPOS, generateFromEcommerce, generatePublicInvoice, cancel, getXML, getPDF]
|
|
dependencias: [CFDIBuilderService, PACService, XMLService, PDFService]
|
|
- name: CFDIBuilderService
|
|
tipo: nuevo
|
|
metodos: [fromPOSOrder, fromEcommerceOrder, buildConceptos, buildImpuestos]
|
|
- name: PACService
|
|
tipo: nuevo
|
|
metodos: [timbrar, consultar, cancelar]
|
|
providers: [FinkokPAC, FacturamaPAC]
|
|
- name: XMLService
|
|
tipo: nuevo
|
|
metodos: [buildXML, parseXML, sign, validate]
|
|
- name: PDFService
|
|
tipo: nuevo
|
|
metodos: [generate, getTemplate]
|
|
- name: AutofacturaService
|
|
tipo: nuevo
|
|
metodos: [validateTicket, generateFromTicket]
|
|
dependencias: [CFDIService]
|
|
|
|
controllers:
|
|
- name: CFDIController
|
|
endpoints:
|
|
- POST /cfdi/pos/:orderId
|
|
- POST /cfdi/ecommerce/:orderId
|
|
- POST /cfdi/public/:orderId
|
|
- GET /cfdi/:id
|
|
- GET /cfdi/:id/xml
|
|
- GET /cfdi/:id/pdf
|
|
- POST /cfdi/:id/cancel
|
|
- POST /cfdi/credit-note
|
|
- GET /cfdi/report/monthly
|
|
|
|
- name: AutofacturaController
|
|
endpoints:
|
|
- GET /autofactura/validate/:ticketNumber
|
|
- POST /autofactura/generate
|
|
- GET /autofactura/download/:uuid
|
|
|
|
dependencias:
|
|
core: [MGN-010-financial, MGN-012-partners]
|
|
retail: [RT-002-pos, RT-009-ecommerce]
|
|
|
|
# ============================================================
|
|
# VALIDACION DE DEPENDENCIAS
|
|
# ============================================================
|
|
|
|
validation:
|
|
resultado: "APROBADO_CON_GAPS"
|
|
gaps_bloqueantes: 4
|
|
gaps_no_bloqueantes: 0
|
|
|
|
gaps:
|
|
- id: GAP-DEP-001
|
|
tipo: bloqueante
|
|
origen: MGN-005-catalogs
|
|
descripcion: "Modulo de catalogos no implementado"
|
|
impacto: [RT-001, RT-006, RT-010]
|
|
accion: "Implementar en Sprints 1-2"
|
|
|
|
- id: GAP-DEP-002
|
|
tipo: bloqueante
|
|
origen: MGN-001-auth
|
|
descripcion: "Sistema de permisos incompleto"
|
|
impacto: [RT-001, RT-002]
|
|
accion: "Completar en Sprint 1"
|
|
|
|
- id: GAP-DEP-003
|
|
tipo: bloqueante
|
|
origen: MGN-013-sales
|
|
descripcion: "Pricelists no implementado"
|
|
impacto: [RT-006]
|
|
accion: "Implementar en Sprint 4"
|
|
|
|
- id: GAP-DEP-004
|
|
tipo: bloqueante
|
|
origen: MGN-010-financial
|
|
descripcion: "PaymentMethods no implementado"
|
|
impacto: [RT-002, RT-009]
|
|
accion: "Implementar en Sprint 3"
|
|
|
|
dependencias_circulares: []
|
|
|
|
orden_implementacion:
|
|
- paso: 1
|
|
modulos: [MGN-001-auth, MGN-005-catalogs]
|
|
sprint: [1, 2]
|
|
|
|
- paso: 2
|
|
modulos: [MGN-010-financial, MGN-011-inventory]
|
|
sprint: [3, 4]
|
|
|
|
- paso: 3
|
|
modulos: [MGN-012-partners, MGN-013-sales]
|
|
sprint: [4]
|
|
|
|
- paso: 4
|
|
modulos: [RT-001-fundamentos]
|
|
sprint: [5]
|
|
|
|
- paso: 5
|
|
modulos: [RT-006-precios, RT-003-inventario]
|
|
sprint: [6, 7]
|
|
|
|
- paso: 6
|
|
modulos: [RT-002-pos]
|
|
sprint: [8, 9]
|
|
|
|
- paso: 7
|
|
modulos: [RT-007-caja]
|
|
sprint: [10]
|
|
|
|
- paso: 8
|
|
modulos: [RT-010-facturacion]
|
|
sprint: [12, 13]
|
|
|
|
- paso: 9
|
|
modulos: [RT-005-clientes]
|
|
sprint: [14]
|
|
|
|
- paso: 10
|
|
modulos: [RT-004-compras, RT-008-reportes]
|
|
sprint: [15, 16]
|
|
|
|
- paso: 11
|
|
modulos: [RT-009-ecommerce]
|
|
sprint: [17, 18, 19, 20]
|