<!-- keywords: novedades, cambios, precuenta, propina, impresora, pago, api, integracion, mesas, inventario, receta, estacion, agregados, boleta, kds, cocina -->
# Lo nuevo para tu café

## Qué es esta guía

Este documento resume qué cambió en ExtraLatte desde la última vez que
hablamos, dónde encontrar cada cosa en el panel, y qué falta todavía. Está
pensada para que se la reenvíes a tu equipo y a la persona que te programó
la integración con tu propio sistema (POS, app de mesero, lo que sea que
uses para tomar pedidos).

Todo lo de la sección 1 ya está funcionando en el sistema real, hoy. Las
secciones 4 y 5 son distintas: la 4 es información técnica para tu
desarrollador, y la 5 es una lista honesta de lo que todavía no existe.

---

## 1. Ya está funcionando

### Precuenta imprimible

Antes de cobrar, tu sistema le puede pedir a ExtraLatte que imprima la
"precuenta" — el papel de "esto es lo que se debe", con el aviso de que no
es boleta ni factura. No es un botón dentro del panel de ExtraLatte: se lo
pide tu propio sistema (el que ya tienen conectado por API), así que para
tu equipo de mesones no cambia nada — el papel sale solo cuando lo piden
desde su pantalla habitual.

**Dónde revisar que esté lista:** en el menú lateral, entra a
**Impresoras**. Ahí, en el conector de tu local, tiene que estar elegida
una **"Impresora de tickets de cliente"** — es la que imprime la
precuenta y la boleta. Si dice "(la decide el conector)" y nunca falla, no
necesitas tocar nada; si alguna vez la precuenta sale por la impresora
equivocada, ese es el campo que hay que fijar.

### El conector de impresión con formato propio y la leyenda de propina

La versión más nueva del programa que conecta tu impresora (`cafe-printerd
v0.3.0`) imprime la precuenta con su propio encabezado ("PRECUENTA", bien
distinto de una boleta) y, cuando corresponde, la línea **"La propina es
voluntaria."** debajo del monto sugerido — para que nadie la confunda con
un cobro obligatorio.

**Dónde revisar:** en **Impresoras**, el conector de tu local muestra su
versión. Si está en `v0.3.0` o más nueva, ya tienes el formato nuevo sin
hacer nada. Si es más vieja, la precuenta igual imprime, pero con el
formato antiguo de boleta (sin el encabezado ni la leyenda) — conviene
actualizar el conector cuando puedan.

### La impresora de tickets se elige desde el panel

Ya no depende de un archivo en el computador del local: desde
**Impresoras**, para cada conector, eliges en un menú desplegable qué
impresora física usa cada estación de cocina y cuál es la impresora de
tickets de cliente. Lo que eliges ahí manda sobre lo que tenga configurado
el computador.

### El pago se puede registrar desde su propio sistema

Cuando cobran en su propia caja (no en la de ExtraLatte), su sistema le
puede avisar a ExtraLatte "este pedido ya se pagó, ciérralo" — con el
método de pago, la propina y, si corresponde, el sello de fidelidad del
cliente. Esto es lo que hace que un pedido de mesa cobrado afuera también
salga del tablero de cocina y libere la mesa; antes no existía ninguna
forma de avisarlo y el pedido se quedaba "pendiente" para siempre.

**Dónde revisar:** esto lo hace tu propio sistema al llamar a la API, no
es un botón del panel. Lo único que necesitas confirmar es que la llave
(API key) que le diste a tu desarrollador tenga el permiso correspondiente
— se revisa en **Organización → Configuración → API keys de integración
→ Gestionar API keys**. Si ya la usan para mandar pedidos, no necesitan
crear una llave nueva: la que tienen ganó este permiso solo, sin que
tengan que hacer nada.

### El tablero de cocina se vacía solo a las 24 horas

Si alguna vez una mesa queda cobrada afuera pero nadie le avisa a
ExtraLatte a tiempo (o un pedido se olvida sin cerrar), a las 24 horas el
sistema lo cierra solo, lo marca como pagado y lo saca del tablero — así
la cocina nunca ve pedidos fantasma acumulados de días anteriores. Esto es
un piso de seguridad, no reemplaza cerrar el pedido cuando corresponde.

**Dónde se nota:** en **Cocina** (el tablero KDS) — un pedido que llevaba
mucho tiempo ahí simplemente desaparece al otro día.

### Las mesas se liberan

Cuando un pedido de mesa se cierra — sea porque lo cobraron y avisaron por
API, sea porque lo cobraron en la caja de ExtraLatte, o sea por el barrido
automático de 24 horas de arriba — la mesa queda libre para el siguiente
cliente sin que nadie tenga que "resetearla" a mano.

**Dónde se nota:** en **Organización → Mesas**, y en la pantalla de mozo
si la usan.

### La pantalla de cocina muestra los agregados

Hasta ahora el papel de la comanda imprimía `+ Leche de almendra` y la
pantalla del KDS no: una cocina que trabaja mirando la pantalla podía saltarse
un agregado. Ya aparecen en pantalla, debajo del producto, igual que en el
papel.

**Dónde se nota:** en **Cocina**, y en la pantalla de expedición si la usan.

### Los permisos de una llave se editan sin romper a nadie

Antes, para darle un permiso nuevo a la llave que usa su desarrollador había
que emitir una llave nueva — y eso dejaba de funcionar la que ya estaba
programada. Ahora los permisos se editan sobre la llave existente: el sistema
avisa antes de guardar, y **la llave no cambia**, así que quien la use no tiene
que tocar nada. Quitar un permiso sí corta a quien lo estaba usando, y la
pantalla lo dice antes de que lo hagan.

Además, la página ahora distingue las **llaves de integración** de los
**conectores de impresión** de su local. Se veían iguales, y borrar un conector
creyendo que era una llave sin uso dejaba a la cocina sin imprimir. El botón
del conector ahora dice "Desvincular" y avisa exactamente eso.

**Dónde revisar:** **Organización → Configuración → API keys de integración
→ Gestionar API keys**.

---

## 2. Dos cosas que van a notar y no son errores

**Sus ventas de mesa van a aparecer por primera vez.** Hasta ahora, un
pedido de mesa cobrado en su propia caja nunca quedaba registrado como
venta cerrada del lado de ExtraLatte — se quedaba abierto para siempre.
Con el pago registrado desde su sistema (arriba), esas ventas van a
aparecer en sus reportes y en caja como corresponde. Si de un día para
otro ven más ventas de mesa que antes, es porque **ahora sí se están
contando** — no es que estén vendiendo más.

**Su inventario va a empezar a descontarse.** Hoy solo 7 de sus 205
productos tienen receta cargada (los que sí la tienen ya descontaban
antes), así que el efecto va a ser chico y gradual al principio, pero
real: cada venta de esos 7 productos va a bajar el stock del insumo
correspondiente. Si quieren que más productos descuenten stock
automáticamente, hay que cargarles receta — pregúntennos si quieren ayuda
con eso.

---

## 3. Una cosa que pueden arreglar hoy, en dos clics

Sus categorías **"Agregados"** y **"Extra"** no tienen ninguna estación de
cocina asignada. El efecto concreto: cuando alguien pide un café con un
agregado, sale **una comanda para el café** (a la estación que corresponde,
por ejemplo Barra) **y una segunda comanda separada para el agregado**, que
cae en la impresora por defecto — y esa, casi siempre, no es la de la
estación donde realmente se prepara.

**Por qué asignar una estación no alcanza por sí solo.** Miramos su
categoría "Agregados" y está mezclada: conviven cosas de barra (Extra Shot
Café, Leche Almendra, Syrups, Salsas, Scoop de Helado) con cosas de cocina
(Atún, Carne, Palta, Pollo, Huevo cocido, Tomate). Una categoría solo puede
apuntar a **una** estación, así que cualquiera que elijan deja a la otra
mitad en la estación equivocada — y la comanda sigue saliendo partida en
dos. Preferimos decirlo antes de que lo prueben.

Hay dos caminos, y el segundo es el bueno.

### Camino rápido: separar la categoría en dos

Creen **"Agregados barra"** y **"Agregados cocina"**, muevan cada agregado a
la que le corresponde, y asignen a cada una su estación (Menú → editar
categoría con el ícono de lápiz → campo **"Estación de cocina"**). A partir
de ahí, una bebida con un agregado de barra sale en **una sola comanda**, y
un sándwich con un agregado de cocina también. Toma un rato la primera vez y
después queda resuelto.

### Camino correcto: que el agregado deje de ser un producto suelto

Desde ahora ExtraLatte entiende **agregados de verdad**: en vez de ser un
producto aparte que se agrega como otra línea, el agregado vive *dentro* del
producto al que pertenece. En Menú, entren a un producto y usen el panel de
**opciones y agregados**: crean un grupo (por ejemplo "Leche"), le agregan
las opciones con su precio (Leche de almendra +$800), y definen si es
obligatorio elegir y cuántas opciones se pueden marcar.

Qué cambia con eso:

- La comanda sale **una sola**, con el agregado impreso debajo de su
  producto (`+ Leche de almendra`), en la estación del producto.
- El precio se cobra bien **solo**: la precuenta y el total ya lo incluyen,
  sin que nadie tenga que acordarse de sumar una línea.
- En la caja, al tocar el producto se abre la lista de opciones, y no se
  puede agregar sin elegir lo obligatorio.

Es más trabajo de configuración que separar categorías, pero es la forma en
que el sistema entiende un agregado — y es la que le sirve también a su
desarrollador, porque puede mandarlos dentro de la línea del pedido.

---

## 4. Para su desarrollador

Dos respuestas concretas a lo que preguntaron:

### (a) Una mesa ya puede ser una sola cuenta

Hasta ahora, cuando mandaban un `POST /orders` por cada ronda que pedía la
misma mesa (para que la cocina no rehiciera lo ya despachado — el patrón que
usaban era correcto dado lo que la API ofrecía), cada uno de esos pedidos era
su propio `order_id`, con su propio total, su propia precuenta y su propio
cobro. Pedir la precuenta "de la mesa 5" significaba hacerlo tres veces.

Ya existe **`POST /orders/{order_id}/items`**: la ronda nueva entra al **mismo
pedido**, y la comanda que sale a la cocina lleva **solo lo nuevo**, con el
número de ronda en el encabezado (`Mesa 5 · ronda 2`). Nada de lo ya despachado
se reimprime. Con eso la mesa vuelve a ser una sola cuenta de punta a punta:
una precuenta, un cobro.

Lo que le importa a quien programa:

- La forma de `items` es la misma de `POST /orders`, agregados incluidos.
- Un pedido ya pagado o cerrado responde `409`: alguien cobró contra un total
  que la línea nueva movería. Ahí corresponde abrir un pedido nuevo, y la API
  lo dice en vez de aceptar en silencio una línea que nadie va a cobrar.
- `print_full_order: true` imprime la mesa entera marcando lo nuevo, para
  cocinas que prefieren ver todo el pedido en el papel.
- **Manden `Idempotency-Key`.** Agregar ítems no es idempotente por
  naturaleza: una misma mesa puede pedir el mismo café dos veces y eso es
  legítimo, así que el sistema no puede adivinar si una segunda llamada es un
  reintento o una ronda real. Con el encabezado, el reintento devuelve la
  misma respuesta. El papel está protegido por separado: una misma ronda no se
  imprime dos veces aunque la llamada se repita.

### (b) Los agregados con precio ya se pueden mandar dentro de la línea del pedido

Ya está en producción y lo pueden usar. El flujo es:

1. Sincronizan el agregado como parte del producto, con su propio precio y
   su propio SKU:

   ```
   PUT /products/ICED-AME
   {
     "name": "Iced Americano", "price": 2500, "category": "Bebidas Frías",
     "option_groups": [
       { "name": "Extras",
         "options": [ { "sku": "SHOT-EXTRA", "name": "Shot extra", "price": 500 } ] }
     ]
   }
   ```

2. Al mandar el pedido, el agregado va **dentro de la línea**, no como
   línea aparte ni como texto en `notes`:

   ```
   POST /orders
   { "items": [ { "sku": "ICED-AME", "quantity": 1, "modifiers": ["SHOT-EXTRA"] } ] }
   ```

   El precio del shot ($500) lo pone ExtraLatte desde el catálogo — nunca
   lo mandan ustedes — y queda sumado en el total de esa línea
   (`(2500 + 500) × 1`), no como un producto suelto. Esto es justamente lo
   que evita el problema de la doble comanda que tenían con "Cappuccino +
   leche de almendra": el agregado deja de necesitar su propio SKU-producto
   y su propia estación.

El contrato completo de las dos cosas — todos los campos, todos los errores —
está en **`/integration/guia`** §6, la misma guía que ya usan para el resto de
la API.

### Además: ahora también se puede consultar, no solo escribir

Hasta ahora la API servía para **mandarle** cosas a ExtraLatte. Su
desarrollador ya puede también **preguntarle**: la lista de pedidos con sus
filtros (abiertos, de una mesa, de un rango de fechas), las mesas con el
pedido que tiene cada una, y los métodos de pago que ustedes tienen
configurados. Es lo que faltaba para que una instrucción como "cobra la mesa
5" se resuelva sola, sin que nadie tenga que buscar a mano el pedido correcto.
Y como muchos equipos hoy programan con ayuda de un asistente de IA, dejamos
un documento listo para pegárselo: está en **`/integration/skill.md`** y reúne
en un solo lugar las reglas de la API, qué errores se reintentan y cuáles no, y
qué llamadas imprimen papel o mueven plata en el local.

---

## 5. Lo que todavía no

Para que no haya sorpresas:

- **El inventario no sabe de rondas ni de mesas abiertas**, pero eso no es un
  problema: descuenta por producto vendido, así que una mesa con tres rondas
  descuenta lo mismo que tres pedidos separados. Lo aclaramos porque es la
  primera pregunta que suele aparecer.
- **El inventario todavía no entiende agregados ni cambios de leche.** Un
  agregado (p. ej. el shot extra) no descuenta ningún insumo, y un
  *cambio* de leche (p. ej. piden leche de almendra en vez de la de
  siempre) sigue descontando la leche normal — porque hoy el sistema solo
  sabe "sumar", no "reemplazar". Esto es una limitación real, no un bug
  chico; lo estamos registrando para una fase futura.
- **ExtraLatte todavía no emite boleta electrónica.** Por eso ustedes
  siguen emitiendo su propia boleta para cada venta — eso no cambia con
  nada de lo de arriba. El día que esto cambie, se los vamos a avisar con
  su propia guía.

---

¿Dudas sobre algo de esta lista? Respondan este mismo documento o
escríbannos directo — preferimos aclarar antes que ustedes se encuentren
con la sorpresa en el local.
