.
This commit is contained in:
parent
3182771455
commit
97cafb3818
@ -46,6 +46,7 @@ Este directorio reúne la documentación técnica, operativa y de apoyo del ERP.
|
|||||||
- [README de `modules/identity`](../modules/identity/README.md)
|
- [README de `modules/identity`](../modules/identity/README.md)
|
||||||
- [README de `modules/companies`](../modules/companies/README.md)
|
- [README de `modules/companies`](../modules/companies/README.md)
|
||||||
- [README de `modules/auth`](../modules/auth/README.md)
|
- [README de `modules/auth`](../modules/auth/README.md)
|
||||||
|
- [API pública de selección y alta rápida de clientes](./customers/customer-selection-and-quick-create.md)
|
||||||
|
|
||||||
#### Guías y estándares
|
#### Guías y estándares
|
||||||
|
|
||||||
|
|||||||
392
docs/customers/customer-selection-and-quick-create.md
Normal file
392
docs/customers/customer-selection-and-quick-create.md
Normal file
@ -0,0 +1,392 @@
|
|||||||
|
# Customer Selection y Quick Create
|
||||||
|
|
||||||
|
## Objetivo
|
||||||
|
|
||||||
|
`modules/customers/src/common/features` es la superficie pública del módulo `customers` para colaboración entre módulos frontend del ERP.
|
||||||
|
|
||||||
|
Estas features permiten que un consumidor:
|
||||||
|
|
||||||
|
- seleccione un cliente existente;
|
||||||
|
- cree un cliente de alta rápida;
|
||||||
|
- reciba siempre un contrato público homogéneo para aplicar el resultado en su propio formulario.
|
||||||
|
|
||||||
|
La dependencia deseada es:
|
||||||
|
|
||||||
|
```text
|
||||||
|
consumer module
|
||||||
|
│
|
||||||
|
▼
|
||||||
|
@erp/customers o @erp/customers/common
|
||||||
|
│
|
||||||
|
▼
|
||||||
|
customers/common/features
|
||||||
|
│
|
||||||
|
├── customer-selection
|
||||||
|
└── quick-create-customer
|
||||||
|
```
|
||||||
|
|
||||||
|
Un consumidor no debe resolver estos flujos importando implementación interna desde:
|
||||||
|
|
||||||
|
- `modules/customers/src/web/create`
|
||||||
|
- `modules/customers/src/web/update`
|
||||||
|
- `modules/customers/src/web/shared`
|
||||||
|
|
||||||
|
Esos directorios siguen siendo responsabilidad interna del módulo `customers`.
|
||||||
|
|
||||||
|
## Features públicas
|
||||||
|
|
||||||
|
### `customer-selection`
|
||||||
|
|
||||||
|
Resuelve el problema de buscar y seleccionar un cliente desde otro módulo, exponiendo un flujo reutilizable con diálogo de selección y un contrato público estable para devolver el cliente elegido.
|
||||||
|
|
||||||
|
API pública real exportada por `modules/customers/src/common/features/customer-selection/index.ts`:
|
||||||
|
|
||||||
|
- `useCustomerSelectionFlow`
|
||||||
|
- `CustomerSelectionCriteria`
|
||||||
|
- `CustomerSelectionOption`
|
||||||
|
- `SelectCustomerDialog`
|
||||||
|
- `buildCustomerSelectionOption`
|
||||||
|
|
||||||
|
Responsabilidades principales:
|
||||||
|
|
||||||
|
- búsqueda y paginación de clientes;
|
||||||
|
- apertura y cierre del selector;
|
||||||
|
- transformación del resultado de listado al contrato público `CustomerSelectionOption`;
|
||||||
|
- coordinación con alta rápida cuando el consumidor usa el flow público;
|
||||||
|
- entrega del cliente seleccionado al callback del consumidor.
|
||||||
|
|
||||||
|
No pertenece a esta feature:
|
||||||
|
|
||||||
|
- construir `CreateCustomerParams`;
|
||||||
|
- conocer el formulario completo de create/update de clientes;
|
||||||
|
- invalidar cachés externas del consumidor;
|
||||||
|
- decidir qué hace el consumidor con el cliente ya seleccionado.
|
||||||
|
|
||||||
|
### `quick-create-customer`
|
||||||
|
|
||||||
|
Resuelve el problema de crear un cliente mínimo y embebible sin exponer al consumidor los detalles internos del CRUD de `customers`.
|
||||||
|
|
||||||
|
API pública real exportada por `modules/customers/src/common/features/quick-create-customer/index.ts`:
|
||||||
|
|
||||||
|
- `useQuickCreateCustomerFlow`
|
||||||
|
- `QuickCustomerCreateResult`
|
||||||
|
- `QuickCreateCustomerDialog`
|
||||||
|
|
||||||
|
Responsabilidades principales:
|
||||||
|
|
||||||
|
- formulario reducido de alta rápida;
|
||||||
|
- validación del formulario;
|
||||||
|
- apertura y cierre del diálogo;
|
||||||
|
- creación mediante la mutation propia de `customers`;
|
||||||
|
- adaptación del resultado de creación a `CustomerSelectionOption`;
|
||||||
|
- gestión de toasts, errores y estado del diálogo;
|
||||||
|
- aplicación de defaults internos y contexto opcional del consumidor.
|
||||||
|
|
||||||
|
No pertenece a esta feature:
|
||||||
|
|
||||||
|
- que el consumidor construya `CreateCustomerParams`;
|
||||||
|
- que el consumidor importe `useCustomerCreateMutation`;
|
||||||
|
- que el consumidor gestione manualmente la caché de `customers`.
|
||||||
|
|
||||||
|
## Contrato público: `CustomerSelectionOption`
|
||||||
|
|
||||||
|
`CustomerSelectionOption` representa la proyección pública que `customers` entrega a otros módulos cuando el resultado del flujo es “ya tienes un cliente seleccionable y aplicable”.
|
||||||
|
|
||||||
|
No es la entity completa del CRUD de `customers`. Es un shape orientado a integración y UI.
|
||||||
|
|
||||||
|
Campos reales actuales:
|
||||||
|
|
||||||
|
- `id`
|
||||||
|
- `status`
|
||||||
|
- `isCompany`
|
||||||
|
- `name`
|
||||||
|
- `tradeName`
|
||||||
|
- `tin`
|
||||||
|
- `street`
|
||||||
|
- `street2`
|
||||||
|
- `city`
|
||||||
|
- `province`
|
||||||
|
- `postalCode`
|
||||||
|
- `country`
|
||||||
|
- `primaryEmail`
|
||||||
|
- `primaryPhone`
|
||||||
|
- `primaryMobile`
|
||||||
|
|
||||||
|
Su objetivo es permitir que el consumidor:
|
||||||
|
|
||||||
|
- persista el identificador funcional (`customerId`);
|
||||||
|
- muestre un resumen útil del cliente;
|
||||||
|
- trate de la misma forma un cliente seleccionado y uno recién creado.
|
||||||
|
|
||||||
|
## Convergencia entre selección y creación
|
||||||
|
|
||||||
|
La convergencia es intencional.
|
||||||
|
|
||||||
|
`modules/customers/src/common/features/quick-create-customer/entities/quick-customer-create-result.entity.ts` define:
|
||||||
|
|
||||||
|
```ts
|
||||||
|
type QuickCustomerCreateResult = CustomerSelectionOption;
|
||||||
|
```
|
||||||
|
|
||||||
|
Eso significa que, para el consumidor, no hay dos contratos distintos:
|
||||||
|
|
||||||
|
```text
|
||||||
|
seleccionar cliente existente ───────┐
|
||||||
|
├──► CustomerSelectionOption
|
||||||
|
crear cliente rápidamente ───────────┘
|
||||||
|
```
|
||||||
|
|
||||||
|
Una vez terminada la operación, el consumidor puede usar el mismo callback para ambos casos. En el flow público actual, ese callback es `onCustomerSelected(customer)`.
|
||||||
|
|
||||||
|
## `useCustomerSelectionFlow`
|
||||||
|
|
||||||
|
`useCustomerSelectionFlow` es el punto de composición pública recomendado cuando una pantalla necesita:
|
||||||
|
|
||||||
|
- seleccionar un cliente existente;
|
||||||
|
- abrir alta rápida desde el selector;
|
||||||
|
- abrir alta rápida directamente desde la pantalla;
|
||||||
|
- recibir siempre un `CustomerSelectionOption`.
|
||||||
|
|
||||||
|
Parámetros públicos actuales:
|
||||||
|
|
||||||
|
- `onCustomerSelected(customer: CustomerSelectionOption)`
|
||||||
|
- `defaultLanguageCode?`
|
||||||
|
- `defaultCurrencyCode?`
|
||||||
|
|
||||||
|
Estado y artefactos que coordina:
|
||||||
|
|
||||||
|
- `selectCtrl` para el selector;
|
||||||
|
- `createCtrl` para el diálogo de alta rápida;
|
||||||
|
- `SelectCustomerDialog`;
|
||||||
|
- `QuickCreateCustomerDialog`;
|
||||||
|
- entrypoints de apertura para creación rápida en distintos contextos.
|
||||||
|
|
||||||
|
El consumidor no debería reproducir manualmente esta coordinación si ya consume este flow.
|
||||||
|
|
||||||
|
## Dos entrypoints de creación rápida
|
||||||
|
|
||||||
|
La implementación actual diferencia dos contextos y su semántica importa.
|
||||||
|
|
||||||
|
### `openQuickCreateDialog`
|
||||||
|
|
||||||
|
Uso típico:
|
||||||
|
|
||||||
|
- botón `Nuevo cliente` de una pantalla consumidora.
|
||||||
|
|
||||||
|
Comportamiento:
|
||||||
|
|
||||||
|
```text
|
||||||
|
abre creación rápida directamente
|
||||||
|
→ cancelar
|
||||||
|
→ simplemente se cierra el diálogo
|
||||||
|
```
|
||||||
|
|
||||||
|
No intenta reabrir el selector porque no presupone que el usuario viniera de ahí.
|
||||||
|
|
||||||
|
### `openQuickCreateFromSelection`
|
||||||
|
|
||||||
|
Uso típico:
|
||||||
|
|
||||||
|
- botón `Nuevo cliente` dentro de `SelectCustomerDialog`.
|
||||||
|
|
||||||
|
Comportamiento:
|
||||||
|
|
||||||
|
```text
|
||||||
|
cierra selector
|
||||||
|
→ abre creación rápida
|
||||||
|
→ cancelar
|
||||||
|
→ vuelve a abrir selector
|
||||||
|
```
|
||||||
|
|
||||||
|
Esta diferencia evita que el consumidor tenga que gestionar manualmente el retorno al selector.
|
||||||
|
|
||||||
|
## Diagrama del flujo
|
||||||
|
|
||||||
|
```text
|
||||||
|
useCustomerSelectionFlow
|
||||||
|
│
|
||||||
|
├── selectCtrl.openDialog()
|
||||||
|
│ │
|
||||||
|
│ ▼
|
||||||
|
│ SelectCustomerDialog
|
||||||
|
│ │
|
||||||
|
│ ├── confirmar selección
|
||||||
|
│ │ │
|
||||||
|
│ │ ▼
|
||||||
|
│ │ onCustomerSelected(CustomerSelectionOption)
|
||||||
|
│ │
|
||||||
|
│ └── Nuevo cliente
|
||||||
|
│ │
|
||||||
|
│ ▼
|
||||||
|
│ openQuickCreateFromSelection()
|
||||||
|
│ │
|
||||||
|
│ ▼
|
||||||
|
│ QuickCreateCustomerDialog
|
||||||
|
│ │
|
||||||
|
│ ├── cancelar
|
||||||
|
│ │ │
|
||||||
|
│ │ ▼
|
||||||
|
│ │ reabrir selector
|
||||||
|
│ │
|
||||||
|
│ └── crear
|
||||||
|
│ │
|
||||||
|
│ ▼
|
||||||
|
│ onCustomerSelected(CustomerSelectionOption)
|
||||||
|
│
|
||||||
|
└── openQuickCreateDialog()
|
||||||
|
│
|
||||||
|
▼
|
||||||
|
QuickCreateCustomerDialog
|
||||||
|
│
|
||||||
|
├── cancelar
|
||||||
|
│ │
|
||||||
|
│ ▼
|
||||||
|
│ cerrar diálogo
|
||||||
|
│
|
||||||
|
└── crear
|
||||||
|
│
|
||||||
|
▼
|
||||||
|
onCustomerSelected(CustomerSelectionOption)
|
||||||
|
```
|
||||||
|
|
||||||
|
## Detalle de `quick-create-customer`
|
||||||
|
|
||||||
|
### Formulario reducido
|
||||||
|
|
||||||
|
La alta rápida no intenta sustituir al CRUD completo de `customers`.
|
||||||
|
|
||||||
|
El schema público de formulario rápido actual (`QuickCustomerCreateFormSchema`) expone solo:
|
||||||
|
|
||||||
|
- `isCompany`
|
||||||
|
- `name`
|
||||||
|
- `tin`
|
||||||
|
- `primaryEmail`
|
||||||
|
|
||||||
|
### Defaults internos y contexto opcional
|
||||||
|
|
||||||
|
La feature reutiliza `buildCustomerCreateDefault()` del área interna de create y resuelve por defecto:
|
||||||
|
|
||||||
|
- `country = ES`
|
||||||
|
- `languageCode = es`
|
||||||
|
- `currencyCode = EUR`
|
||||||
|
|
||||||
|
Además, `useQuickCreateCustomerFlow` y `useQuickCreateCustomerDialogController` admiten contexto opcional:
|
||||||
|
|
||||||
|
- `defaultCountry?`
|
||||||
|
- `defaultLanguageCode?`
|
||||||
|
- `defaultCurrencyCode?`
|
||||||
|
|
||||||
|
Regla conceptual:
|
||||||
|
|
||||||
|
```text
|
||||||
|
consumidor
|
||||||
|
→ aporta contexto opcional
|
||||||
|
|
||||||
|
customers
|
||||||
|
→ sigue construyendo, validando y ejecutando la creación
|
||||||
|
```
|
||||||
|
|
||||||
|
El consumidor no debe construir `CreateCustomerParams`.
|
||||||
|
|
||||||
|
### Validación, errores y toasts
|
||||||
|
|
||||||
|
La responsabilidad de validación y feedback está dentro de `quick-create-customer`:
|
||||||
|
|
||||||
|
- `QuickCustomerCreateFormSchema` valida el formulario;
|
||||||
|
- `useQuickCreateCustomerDialogController` aplica errores de validación al form;
|
||||||
|
- la feature muestra `showSuccessToast`, `showWarningToast` y `showErrorToast`;
|
||||||
|
- el diálogo mantiene `submitError` y el estado `isSubmitting`.
|
||||||
|
|
||||||
|
Por tanto, un consumidor normal no debería duplicar:
|
||||||
|
|
||||||
|
- `try/catch` del submit;
|
||||||
|
- toasts de éxito/error de creación;
|
||||||
|
- `setError` sobre el formulario rápido.
|
||||||
|
|
||||||
|
### Caché
|
||||||
|
|
||||||
|
La creación usa `useCustomerCreateMutation()` desde el módulo `customers`.
|
||||||
|
|
||||||
|
La sincronización de React Query y su estrategia de caché siguen siendo responsabilidad de `customers`. El consumidor no debe invalidar manualmente queries de `customers` tras una creación rápida salvo un caso excepcional y explícitamente justificado.
|
||||||
|
|
||||||
|
## Ejemplo real: `proformas/update`
|
||||||
|
|
||||||
|
Caso real actual:
|
||||||
|
|
||||||
|
- `modules/customer-invoices/src/web/proformas/update/controllers/use-update-proforma-page-controller.ts`
|
||||||
|
- `modules/customer-invoices/src/web/proformas/update/controllers/use-update-proforma-controller.ts`
|
||||||
|
- `modules/customer-invoices/src/web/proformas/update/ui/pages/proforma-update-page.tsx`
|
||||||
|
|
||||||
|
Integración conceptual actual:
|
||||||
|
|
||||||
|
```text
|
||||||
|
useCustomerSelectionFlow(...)
|
||||||
|
│
|
||||||
|
├── seleccionar cliente existente
|
||||||
|
└── crear cliente rápido
|
||||||
|
│
|
||||||
|
▼
|
||||||
|
onCustomerSelected(customer)
|
||||||
|
│
|
||||||
|
▼
|
||||||
|
updateCtrl.setCustomer(customer)
|
||||||
|
│
|
||||||
|
▼
|
||||||
|
form.setValue("customerId", customer.id)
|
||||||
|
```
|
||||||
|
|
||||||
|
En `proformas/update`:
|
||||||
|
|
||||||
|
- el page controller compone `useCustomerSelectionFlow`;
|
||||||
|
- la pantalla usa `selectCustomerCtrl.openQuickCreateDialog` para el botón principal `Nuevo cliente`;
|
||||||
|
- `SelectCustomerDialog` usa `selectCustomerCtrl.openQuickCreateFromSelection` para `Nuevo cliente` dentro del selector;
|
||||||
|
- ambos caminos convergen en `updateCtrl.setCustomer(customer)`.
|
||||||
|
|
||||||
|
## Rehidratación y snapshots externos
|
||||||
|
|
||||||
|
`CustomerSelectionOption` es el contrato ideal que `customers` entrega a consumidores.
|
||||||
|
|
||||||
|
Eso no implica que cualquier otro recurso del ERP tenga que persistir exactamente el mismo shape. Por ejemplo, una proforma puede contener un snapshot suficiente para representar a su cliente, pero no necesariamente todos los campos disponibles en `CustomerSelectionOption`.
|
||||||
|
|
||||||
|
La integración correcta consiste en:
|
||||||
|
|
||||||
|
- usar `CustomerSelectionOption` cuando el dato proviene del flujo público de `customers`;
|
||||||
|
- permitir que recursos externos reconstruyan su propio resumen cuando trabajan con snapshots parciales.
|
||||||
|
|
||||||
|
## Qué debe importar un consumidor
|
||||||
|
|
||||||
|
Imports recomendados:
|
||||||
|
|
||||||
|
```ts
|
||||||
|
import { useCustomerSelectionFlow } from "@erp/customers/common";
|
||||||
|
import type { CustomerSelectionOption } from "@erp/customers";
|
||||||
|
import { QuickCreateCustomerDialog, SelectCustomerDialog } from "@erp/customers";
|
||||||
|
```
|
||||||
|
|
||||||
|
La ruta concreta puede variar según el barrel elegido, pero debe salir de la superficie pública exportada por `@erp/customers` o `@erp/customers/common`.
|
||||||
|
|
||||||
|
## Qué no debe importar un consumidor
|
||||||
|
|
||||||
|
No debe depender directamente de piezas internas del CRUD como:
|
||||||
|
|
||||||
|
- `CreateCustomerParams`
|
||||||
|
- `CustomerCreateForm`
|
||||||
|
- `useCustomerCreateMutation`
|
||||||
|
- `buildCreateCustomerParams`
|
||||||
|
- componentes o hooks desde `modules/customers/src/web/create/*`
|
||||||
|
- detalles internos de `modules/customers/src/web/shared/*`
|
||||||
|
|
||||||
|
## Respuestas rápidas de contrato
|
||||||
|
|
||||||
|
1. `customer-selection` resuelve búsqueda, selección y entrega homogénea de cliente.
|
||||||
|
2. `quick-create-customer` resuelve alta mínima embebible sin exponer el CRUD interno.
|
||||||
|
3. La API pública real está definida por los barrels de cada feature, no por sus internals.
|
||||||
|
4. El consumidor debe importar desde `@erp/customers` o `@erp/customers/common`.
|
||||||
|
5. No debe importar internals de `web/create`, `web/update` o `web/shared`.
|
||||||
|
6. `CustomerSelectionOption` es la proyección pública reutilizable de cliente seleccionado.
|
||||||
|
7. `QuickCustomerCreateResult` converge en el mismo contrato para no bifurcar la integración.
|
||||||
|
8. `openQuickCreateDialog` es apertura directa; `openQuickCreateFromSelection` preserva el retorno al selector.
|
||||||
|
9. La cancelación y la reapertura del selector las gestiona el flow de `customers`.
|
||||||
|
10. La creación, validación, errores y caché pertenecen a `customers`.
|
||||||
|
11. El consumidor integra el resultado aplicando `CustomerSelectionOption` a su propio caso de uso.
|
||||||
|
12. `proformas/update` lo hace actualmente con `updateCtrl.setCustomer(customer)`.
|
||||||
@ -24,11 +24,19 @@ export const useCustomerSelectionFlow = (options: {
|
|||||||
defaultCurrencyCode: options.defaultCurrencyCode,
|
defaultCurrencyCode: options.defaultCurrencyCode,
|
||||||
});
|
});
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Se usa cuando la creación rápida nace dentro del selector.
|
||||||
|
* Si el usuario cancela, `onCancel` reabre el selector.
|
||||||
|
*/
|
||||||
const openQuickCreateFromSelection = () => {
|
const openQuickCreateFromSelection = () => {
|
||||||
selectCtrl.closeDialog();
|
selectCtrl.closeDialog();
|
||||||
quickCreateFlow.createCtrl.openDialog();
|
quickCreateFlow.createCtrl.openDialog();
|
||||||
};
|
};
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Se usa cuando el usuario inicia la creación rápida desde una pantalla consumidora.
|
||||||
|
* Si cancela, el diálogo simplemente se cierra.
|
||||||
|
*/
|
||||||
const openQuickCreateDialog = () => {
|
const openQuickCreateDialog = () => {
|
||||||
quickCreateFlow.createCtrl.openDialog();
|
quickCreateFlow.createCtrl.openDialog();
|
||||||
};
|
};
|
||||||
|
|||||||
@ -2,15 +2,34 @@
|
|||||||
|
|
||||||
Feature pública reutilizable del módulo `customers` para alta rápida embebida.
|
Feature pública reutilizable del módulo `customers` para alta rápida embebida.
|
||||||
|
|
||||||
|
La documentación de diseño e integración entre módulos está consolidada en:
|
||||||
|
|
||||||
|
- [docs/customers/customer-selection-and-quick-create.md](../../../../../../docs/customers/customer-selection-and-quick-create.md)
|
||||||
|
|
||||||
## API pública
|
## API pública
|
||||||
|
|
||||||
```ts
|
```ts
|
||||||
import {
|
import {
|
||||||
QuickCreateCustomerDialog,
|
QuickCreateCustomerDialog,
|
||||||
|
QuickCustomerCreateResult,
|
||||||
useQuickCreateCustomerFlow,
|
useQuickCreateCustomerFlow,
|
||||||
} from "@erp/customers/common";
|
} from "@erp/customers/common";
|
||||||
```
|
```
|
||||||
|
|
||||||
|
## Responsabilidad
|
||||||
|
|
||||||
|
- exponer un diálogo reutilizable de alta rápida;
|
||||||
|
- validar el formulario mínimo;
|
||||||
|
- crear el cliente usando la mutation propia de `customers`;
|
||||||
|
- devolver el resultado como `CustomerSelectionOption`.
|
||||||
|
|
||||||
|
El consumidor no debería importar detalles internos como:
|
||||||
|
|
||||||
|
- `CreateCustomerParams`
|
||||||
|
- `CustomerCreateForm`
|
||||||
|
- `useCustomerCreateMutation`
|
||||||
|
- `buildCreateCustomerParams`
|
||||||
|
|
||||||
## Ejemplo mínimo
|
## Ejemplo mínimo
|
||||||
|
|
||||||
```tsx
|
```tsx
|
||||||
@ -29,3 +48,24 @@ const quickCreate = useQuickCreateCustomerFlow({
|
|||||||
- Éxito: devuelve un `CustomerSelectionOption`, listo para reutilizarse en flujos de selección.
|
- Éxito: devuelve un `CustomerSelectionOption`, listo para reutilizarse en flujos de selección.
|
||||||
- Cancelación: no crea nada, cierra el diálogo y dispara `onCancel` si el consumidor lo ha proporcionado.
|
- Cancelación: no crea nada, cierra el diálogo y dispara `onCancel` si el consumidor lo ha proporcionado.
|
||||||
- Integración con `customer-selection`: puede abrirse desde el selector y devolver el cliente para dejarlo seleccionado automáticamente.
|
- Integración con `customer-selection`: puede abrirse desde el selector y devolver el cliente para dejarlo seleccionado automáticamente.
|
||||||
|
|
||||||
|
## Defaults y contexto
|
||||||
|
|
||||||
|
El formulario rápido actual pide solo:
|
||||||
|
|
||||||
|
- `isCompany`
|
||||||
|
- `name`
|
||||||
|
- `tin`
|
||||||
|
- `primaryEmail`
|
||||||
|
|
||||||
|
Los defaults base de create se resuelven dentro de `customers`. Actualmente la feature conserva:
|
||||||
|
|
||||||
|
- `country = ES`
|
||||||
|
- `languageCode = es`
|
||||||
|
- `currencyCode = EUR`
|
||||||
|
|
||||||
|
Opcionalmente, el consumidor puede aportar contexto mediante:
|
||||||
|
|
||||||
|
- `defaultCountry`
|
||||||
|
- `defaultLanguageCode`
|
||||||
|
- `defaultCurrencyCode`
|
||||||
|
|||||||
Loading…
Reference in New Issue
Block a user