## Contrato del wizard de reserva (`servicios_completos`)

Este documento define la **estructura canónica** del estado del wizard que se serializa en el input hidden `servicios_completos` y se envía a `POST /mis-citas` (`CitaController@store`) y `PUT /mis-citas/{cita}` (`CitaController@update`).

### JSON (shape)

```json
{
  "version": 1,
  "tipos_seleccionados": {
    "manicura": [1],
    "pedicura": [2]
  },
  "servicios_adicionales": [10, 11],
  "opciones_por_uña": {
    "izquierda": {
      "pulgar": { "servicio_id": 100, "precio": 2.5, "nombre": "NailArt", "imagen": "/..." },
      "indice":  { "servicio_id": 101, "precio": 1.0 }
    },
    "derecha": { "pulgar": { "servicio_id": 100, "precio": 2.5 } },
    "pie1": { "pulgar": { "servicio_id": 110, "precio": 1.5 } },
    "pie2": { "pulgar": { "servicio_id": 110, "precio": 1.5 } }
  },
  "subtotal": 0,
  "descuentos": {
    "total": 0,
    "detalles": []
  },
  "total_final": 0,
  "duracion": {
    "modo": "range",
    "min": 0,
    "max": 0,
    "incompleta": false
  },
  "descuentos_aplicados": {}
}
```

### Significado (resumen)
- **`tipos_seleccionados`**: IDs de servicios subcategoría `tipo` por categoría (`manicura`, `pedicura`). Requerido al confirmar.
- **`servicios_adicionales`**: IDs de servicios subcategoría `adicional`. Opcional.
- **`opciones_por_uña`**: mapa por mano/pie → dedo → selección. Solo aplica si el usuario elige personalización por uña.
  - Para manicura: dedos requeridos por mano: `pulgar`, `indice`, `medio`, `anular`, `meñique`.
  - Para pedicura: mínimo 1 pulgar por pie (según UI actual).
- **`subtotal/descuentos/total_final`**: valores calculados en cliente para UI; el servidor debe recalcular/validar.
- **`duracion`**: cálculo de duración basado en `servicios.tiempo_aproximado`.

## Validación por pasos (wizard)

### Paso1_fecha
- Requiere `fecha_hora` válida y en el futuro.

### Paso2_servicio
- Requiere al menos un `tipo` seleccionado en alguna categoría.

### Paso3_personalizacion (condicional)
- Si hay manicura seleccionada y el modo es “por uña”, requiere **10/10 dedos** (2 manos * 5 dedos).
- Si hay pedicura seleccionada y el modo es “por uña”, requiere al menos 1 selección por pie según reglas actuales.

### Paso4_extras_descuentos
- Opcional; debe mantener consistencia (IDs numéricos existentes).

### Paso5_confirmacion
- Serializa el JSON completo en `servicios_completos` y envía el formulario.

## Duración (estimación “honesta”)

Regla UX: **no mostrar un número exacto** hasta que el usuario haya elegido lo mínimo (tipos + extras).

- **Sin selección (Paso1)**: mostrar placeholder “Se calcula al elegir servicio”.
- **Selección parcial (Paso2-4)**: mostrar rango:
  - `min = suma(tiempo_aproximado)` de servicios seleccionados con `tiempo_aproximado > 0`
  - `max = min + buffer` (p. ej. 10–25%) o incluir servicios con `tiempo_aproximado = 0` como incertidumbre.
  - `incompleta = true` si algún servicio seleccionado tiene `tiempo_aproximado` nulo/0.
- **Selección completa**: si todos los servicios seleccionados tienen duración > 0, `modo = exact` y `min=max=suma`.

