Saltar a contenido

RF-010 — Tipos de campo de los formularios

Estado Implementado en el CMS. El render en la tienda lo hace otro desarrollador
Tipo Extensión de plugin-form-builder
Depende de RF-000 · el plugin aporta forms y form-submissions
Reversibilidad Alta para los tipos habilitados —se apagan con una línea—; media para los propios, porque su tabla queda con datos

Requisito

Que quien arma un formulario pueda elegir el tipo de cada campo, y que ese tipo llegue identificado al storefront para que lo dibuje como corresponde: un teléfono con teclado numérico, una fecha con calendario, un paso que corta un formulario largo.

El plugin trae un conjunto de tipos, pero no todos los que trae están disponibles, y los que hacían falta para este sitio no estaban.

Cómo decide el plugin qué tipos ofrecer

Es la pieza que explica todo lo demás, y no se ve a simple vista. Hay dos objetos distintos:

  1. El catálogo de definiciones, con trece bloques: checkbox, country, date, email, message, number, payment, radio, select, state, text, textarea, upload.
  2. El mapa de habilitados, que trae once claves por defecto.

Y el armado recorre el segundo, no el primero. Recién dentro del recorrido busca la definición en el catálogo. De ahí salen tres estados, no dos:

Estado Qué significa Cuáles
true Habilitado Los nueve de siempre
false Apagado a propósito, y se nota la intención payment, upload
Ausente Nunca se lo mira. La definición existe pero, al no ser clave del mapa, el recorrido no pasa por ella date, radio

El tercero es el que confunde: se busca date: false esperando encontrarlo y no está en ningún lado. Tiene toda la pinta de un descuido del plugin —agregaron los bloques al catálogo y se olvidaron del mapa—, y la consecuencia práctica es que habilitar un tipo que el plugin ya trae es nombrarlo.

Lo que ofrece este CMS

Doce tipos, en este orden:

checkbox · country · email · message · number · select · state · text · textarea
date · pageBreak · phone
Tipo De dónde sale Nota
Los nueve primeros Del plugin, habilitados por defecto Sin cambios
date Del plugin, habilitado a mano La definición ya existía; solo faltaba nombrarla
pageBreak Propio No es un campo: no tiene name ni genera valor en el envío. Parte el formulario en pasos
phone Propio El plugin no tiene bloque de teléfono

Quedan fuera payment y upload, apagados por el plugin y sin caso que los pida, y radio, que está en la misma situación que estaba date: la definición existe y alcanzaría con nombrarla. No se habilitó porque nadie lo pidió; cuando haga falta, es una línea más el componente de render y su tabla, que lleva dos porque el bloque tiene arreglo de opciones.

Modelo de datos

Nombres de campo en inglés y etiquetas del panel en español, por ADR-0007. Las etiquetas de los bloques propios repiten las palabras que el plugin ya usa en español, para que no desentonen en el panel.

Bloque phone

Campo Tipo Regla
name texto, requerido La clave con la que el valor viaja en el envío
label texto Lo que se lee arriba del campo
width número Ancho en porcentaje
required checkbox Si se puede enviar el formulario sin completarlo
placeholder texto Se ve dentro del campo mientras está vacío y sirve para sugerir el formato: 0981 123 456

No lleva valor predeterminado, a diferencia del campo de texto del plugin: un teléfono precargado no tiene sentido. Para sugerir el formato está el texto de ejemplo.

Bloque date

Es el del plugin, sin modificar: name, label, width, required y defaultValue.

defaultValue se guarda como fecha con hora y zona, no como fecha suelta. Importa al dibujarlo: el selector del navegador solo acepta AAAA-MM-DD, así que hay que recortar. Sin eso el campo aparece vacío aunque tenga valor.

Bloque pageBreak

title y description. No genera valor en el envío.

Reglas

  1. El CMS no valida ni normaliza el teléfono. Quien arma el formulario no sabe de qué país va a llegar el visitante, y un formato impuesto acá rechazaría números legítimos. Se guarda lo que la persona escribió, tal cual. La validación de forma, si hace falta, es del storefront, que es quien conoce el público de cada formulario.
  2. Habilitar un tipo del plugin exige también su tabla. El panel lo ofrece apenas se lo nombra, pero sin migración la base no lo acepta y el formulario falla al guardar en producción.
  3. Un tipo habilitado que el storefront no conoce no rompe nada, pero se dibuja como caja de texto. Ver la sección siguiente.

Lo que el storefront tiene que dibujar

El contrato es corto: cada campo llega con su blockType y eso es lo único que lo distingue.

blockType Qué dibujar
phone type="tel", que abre el teclado numérico en el celular y habilita el autocompletado. El tipo generado es FormPhoneField
date Un selector de fecha. Recortar defaultValue a AAAA-MM-DD
pageBreak No es un campo: corta la lista en pasos y muestra title y description como encabezado del paso siguiente

Hoy el storefront no dibuja ninguno de los tres. Su renderizador de formularios resuelve text, email, textarea, select y checkbox, y todo lo demás cae en el caso por defecto, que es una caja de texto. No se rompe nada: el teléfono se completa igual y el valor llega bien. Lo que se pierde es el teclado numérico, el calendario y los pasos.

Limitaciones conocidas

  • El tipo se elige al armar el formulario y no se puede cambiar después sin volver a crear el campo, porque cada tipo es un bloque distinto con su propia tabla.
  • Un campo que cambia de name pierde la relación con los envíos anteriores, que guardan la clave como texto.
  • radio y upload siguen sin estar. El primero es una línea más su render; el segundo necesita además declarar de qué colección son las subidas.

Verificación

Criterio Prueba Comando
El teléfono figura entre los tipos disponibles y los que ya estaban siguen estando prueba de integración sobre la configuración npx vitest run --config ./vitest.config.mts -t "teléfono"
Un formulario con teléfono se guarda y vuelve con blockType: 'phone' prueba de integración ídem
El número se guarda tal cual, sin normalizar prueba de integración con tres formatos distintos ídem
Un formulario con fecha se guarda y se recupera prueba de integración -t "fecha"
Payload carga la configuración npm run generate:types pasa y escribe los tipos nuevos