diff --git a/app/Domains/Cart/documentacion/README.md b/app/Domains/Cart/documentacion/README.md index a757dda..d2a5b6e 100644 --- a/app/Domains/Cart/documentacion/README.md +++ b/app/Domains/Cart/documentacion/README.md @@ -36,4 +36,4 @@ Un carrito puede pasar a `checkout`. Las compras directas usan un carrito técni Cada edición sincroniza una única reserva para el carrito completo. Si varios ítems o bundles consumen el mismo inventario, se persiste una sola línea con la cantidad agregada. Al editar durante checkout, la compra anterior queda `superseded`, se desvincula y el carrito conserva la misma reserva activa con sus líneas actualizadas. -El comando unificado `php artisan reservations:expire` recorre una sola vez las reservas activas cuyo `expires_at` haya vencido. Cuando pertenecen a un carrito, conserva la reserva y sus líneas como historial, libera el stock como conjunto y deja intactos el carrito y sus ítems. El carrito mantiene la referencia a esa reserva terminal: no permite editar, cancelar ni iniciar checkout, y nunca crea otra automáticamente. Para continuar, el cliente debe invocar explícitamente `POST /cart/restart`; el carrito anterior queda `abandoned` y el nuevo comienza vacío. +El comando unificado `php artisan reservations:expire` recorre una sola vez las reservas activas cuyo `expires_at` haya vencido. Cuando pertenecen a un carrito, conserva la reserva y sus líneas como historial, libera el stock como conjunto y cambia el carrito asociado a `expired` sin eliminar sus ítems. El carrito mantiene la referencia a esa reserva terminal: puede consultarse, pero no permite editar, cancelar ni iniciar checkout y nunca crea otra automáticamente. Para continuar, el cliente debe invocar explícitamente `POST /cart/restart`; el carrito anterior queda `abandoned` y el nuevo comienza vacío. diff --git a/app/Domains/Catalog/documentacion/README.md b/app/Domains/Catalog/documentacion/README.md index 3b34860..c484772 100644 --- a/app/Domains/Catalog/documentacion/README.md +++ b/app/Domains/Catalog/documentacion/README.md @@ -9,7 +9,7 @@ Modela y publica la oferta comercial del tenant: productos, variantes, categorí - `CatalogItem` es la raíz del producto y se relaciona con tenant, categoría, marca, inventario, variantes, atributos, adjuntos y grupos destacados. - `Variant`, `ItemAttribute`, `Attribute`, `AttributeOption` y `VariantDefinition` describen opciones comercializables. - `Inventory` administra stock disponible, reservado y comprado. -- `StockReservation` representa la reserva completa de un carrito o checkout, con estados `active`, `committed`, `released` y `expired`. Su `expires_at` es el único reloj del bloqueo. Sus estados terminales nunca se reactivan ni se reemplazan implícitamente. Sus `StockReservationLine` agregan la cantidad requerida por inventario, incluso cuando varios ítems o bundles consumen el mismo stock. +- `StockReservation` representa la reserva completa de un carrito o checkout, con estados `active`, `committed`, `released` y `expired`. Su `expires_at` es el único reloj del bloqueo. Al expirar, también pasan a `expired` la compra pagable y el carrito asociados dentro de la misma transacción. Sus estados terminales nunca se reactivan ni se reemplazan implícitamente. Sus `StockReservationLine` agregan la cantidad requerida por inventario, incluso cuando varios ítems o bundles consumen el mismo stock. - `Category` soporta jerarquía y categorías globales o propias del tenant. - `FeaturedGroup` y `FeaturedItem` organizan secciones destacadas. - `BundleComponent` representa los componentes de un paquete. diff --git a/app/Domains/Purchase/documentacion/README.md b/app/Domains/Purchase/documentacion/README.md index 08a4da1..7410245 100644 --- a/app/Domains/Purchase/documentacion/README.md +++ b/app/Domains/Purchase/documentacion/README.md @@ -22,9 +22,9 @@ Implementa el ciclo de compra y checkout: crea la cabecera de compra desde un ca - `SourceCartService`: sincroniza o finaliza el carrito de checkout asociado a la compra. - `CatalogSelectionResolver` y `PurchaseItemSnapshotFactory`: resuelven selecciones y generan snapshots. -Al iniciar checkout o elegir un medio de pago se refresca directamente `StockReservation.expires_at`, que es la única fuente de verdad y se expone como `expires_at` en la respuesta pública de la compra. El refresco sólo se permite mientras la reserva siga vigente; una fecha vencida bloquea todas las mutaciones aun antes de que corra el scheduler. Al cancelar o reemplazar una compra recuperable, ésta se desvincula y el carrito conserva la misma reserva activa. Al informar una transferencia, la compra pasa de `pending_payment` a `in_review` y ese vencimiento se limpia. Si el comprador abandona el checkout durante la revisión, la compra y sus reservas permanecen intactas y se crea un carrito activo nuevo para que pueda seguir comprando. Adminapp puede confirmar o anular explícitamente la compra en revisión. +Al iniciar checkout o elegir un medio de pago se refresca directamente `StockReservation.expires_at`, que es la única fuente de verdad y se expone como `expires_at` en la respuesta pública de la compra. El refresco sólo se permite mientras la reserva siga vigente; una fecha vencida bloquea todas las mutaciones aun antes de que corra el scheduler. Al materializar la expiración, la compra pagable, su carrito y la reserva pasan a `expired` dentro de la misma transacción. Al cancelar o reemplazar una compra recuperable, ésta se desvincula y el carrito conserva la misma reserva activa. Al informar una transferencia, la compra pasa de `pending_payment` a `in_review` y ese vencimiento se limpia. Si el comprador abandona el checkout durante la revisión, la compra y sus reservas permanecen intactas y se crea un carrito activo nuevo para que pueda seguir comprando. Adminapp puede confirmar o anular explícitamente la compra en revisión. -Las cantidades y variantes se editan mediante el dominio Cart. El endpoint autenticado `PATCH /checkout-carts/{cart}/items/{cartItem}` valida que el carrito pertenezca al usuario y a una compra editable. Cuando existe un cambio real, invalida atómicamente el intento de pago anterior, libera su reserva completa y crea otra para el contenido actualizado; Purchase no expone operaciones sobre líneas antes de la confirmación. +Las cantidades y variantes se editan mediante el dominio Cart. El endpoint autenticado `PATCH /checkout-carts/{cart}/items/{cartItem}` valida que el carrito pertenezca al usuario y a una compra editable. Cuando existe un cambio real, invalida atómicamente el intento de pago anterior, devuelve la misma reserva activa al carrito y sincroniza sus líneas con el contenido actualizado; Purchase no expone operaciones sobre líneas antes de la confirmación. `UserPurchaseLimitService` controla límites de compra y `CheckoutService` conserva el punto de entrada para controladores e integraciones.