- Resumen de patrones de diseño recurrentes a partir de la experiencia de crear HTML tools que ejecutan HTML·JavaScript·CSS empaquetados en un solo archivo
- Explica con casos concretos cómo se construyen y mantienen en la práctica pequeñas herramientas, con más de 150 creadas en 2 años
- Una estructura sin etapa de build y el uso de CDN hacen que se forme de manera natural un flujo de desarrollo basado en copiar y pegar
- Amplía el alcance de lo posible usando solo funciones del navegador: URL,
localStorage, abrir archivos, descargas, Pyodide y WebAssembly
- Reforzamiento de una dinámica donde la propia colección de herramientas se convierte en la base del desarrollo mediante el registro de prompts y resultados, y la recombinación de herramientas existentes
Concepto y ejemplos de HTML tools
Estructura básica de una HTML tool
- Composición de un solo archivo HTML con JavaScript y CSS incluidos en línea
- Al no usar React, que requiere build de JSX, copiar y redistribuir se vuelve simple
- Las librerías necesarias se cargan directamente desde CDN como CDNjs o jsDelivr, y las dependencias se mantienen al mínimo
- El código se mantiene en unas cuantas centenas de líneas para reducir la carga de mantenimiento y conservar un estado que el LLM pueda leer y modificar rápidamente
Prototipado con Canvas y Artifacts
- Uso de ChatGPT Canvas, Claude Artifacts y Gemini Canvas para ejecutar de inmediato herramientas HTML y darles una forma inicial
- Se añade la condición “No React” para generar código que funcione de inmediato sin etapa de build
- Ejemplo que convierte JSON pegado en YAML
Cuando se vuelve más complejo, pasar a un agente de código
- Con Claude Code o Codex CLI se puede automatizar trabajo repetitivo, incluyendo pruebas en navegador con Playwright y similares
- En herramientas más complejas, como un visor de hilos de Bluesky, se usa la estrategia de “actualizar” hacia este tipo de agentes
- Se crean PR directamente en el repo simonw/tools para agregar o actualizar herramientas
- El proceso de trabajo usando un agente web puede verse en el video sobre Claude Code for web
Gestión de dependencias basada en CDN
- Cuando se usan librerías adicionales, se cargan desde un CDN
- Hay una allow-list de CDN permitida por Artifacts/Canvas de los LLM, así que instrucciones como “usar PDF.js” permiten construir la URL
- Si hace falta, se buscan las URL en cdnjs o jsDelivr y se pegan en el chat
- Todo funciona como un solo archivo HTML sin proceso de instalación con npm ni build
- npm + build step reduce la productividad para hackear rápidamente herramientas individuales y hacer self-hosting
- Las URL del CDN incluyen versiones, lo que ayuda a mantener la reproducibilidad a largo plazo
Hosting estático externo
- El hosting dentro de plataformas de LLM suele tener muchas restricciones de sandbox, por lo que a veces se bloquea la carga de datos o imágenes desde URLs externas, o los enlaces salientes
- Desde la experiencia de usuario, también puede haber problemas como mensajes de advertencia, cargas adicionales o promoción de la plataforma
- La combinación “No React + CDN” facilita subirlo a cualquier lugar sin build
- Si se sube el archivo HTML a GitHub Pages, se puede acceder de inmediato con una URL fija
- La mayoría de las herramientas se gestionan en el repo simonw/tools y se ofrecen desde tools.simonwillison.net
Entrada y salida centradas en copiar y pegar
- Muchas herramientas usan como mecanismo principal transformar una entrada pegada y luego hacer que se copie al portapapeles otra vez
- Como copiar y pegar en móvil es incómodo, a menudo se añade un botón “Copy to clipboard”
- El portapapeles del sistema puede contener varios formatos a la vez, y en el evento
paste de JavaScript también se puede acceder a esos datos “ricos”
- Herramientas representativas
Herramientas de depuración
- Creación de herramientas dedicadas para comprobar las estructuras reales de datos que se manejan en el navegador
- clipboard-viewer: muestra todos los datos del portapapeles, como texto, texto enriquecido, imágenes y archivos
- Herramientas adicionales
Guardar estado en la URL
- Incluso sin una base de datos del servidor, se puede guardar bastante estado en la URL
- Este patrón se prefiere en herramientas pensadas para marcadores y compartir
- icon-editor: conserva directamente en la URL el estado de edición de un ícono de 24×24
Uso de localStorage
localStorage es una API del navegador que guarda datos de forma persistente en el dispositivo del usuario sin exponerlos al servidor
- Se usa para estados grandes que no caben bien en una URL o para valores secretos como claves de API, evitando el riesgo de exponerlos en logs del servidor de un host estático
- word-counter: guarda automáticamente el texto en redacción
- render-markdown: mantiene el contenido mientras se escribe Markdown
- haiku: guarda la clave de API en
localStorage y genera haiku a partir de imágenes de webcam
Uso de APIs con CORS habilitado
- CORS (Cross-origin resource sharing) es el mecanismo que controla si el JavaScript del navegador puede llamar APIs de otros dominios
- Las APIs con encabezados CORS abiertos son recursos favorables para HTML tools, y con el tiempo vale la pena ir reuniendo una lista
- Se usan iNaturalist, PyPI, GitHub (contenido de repos públicos accesible de forma anónima vía raw.githubusercontent.com), Bluesky y Mastodon, entre otros
- Casos de herramientas
Llamadas directas a APIs de LLM
- Las APIs JSON de OpenAI, Anthropic y Gemini se pueden llamar directamente desde el navegador mediante CORS
- Como incrustar la clave de API en el HTML implica riesgo de robo y de cobros, se usa el “patrón de secretos” guardándola en
localStorage
- Desde la experiencia de usuario, el proceso de emitir y pegar la clave de API genera bastante fricción, pero funciona
- Herramientas de ejemplo
No tener miedo de abrir archivos
- Con
<input type="file"> es posible leer y usar archivos directamente en el navegador sin subirlos a un servidor
- ocr: usa PDF.js y Tesseract.js para convertir un PDF en imágenes por página y ejecutar OCR en el navegador
- social-media-cropper: permite abrir/pegar una imagen y recortarla con proporciones para redes sociales, por ejemplo Twitter/LinkedIn 2:1, Substack 1.4:1, etc.
- ffmpeg-crop: genera comandos de ffmpeg para recortar video
Ofrecer archivos para descarga
- Incluso sin servidor, el navegador puede generar archivos y ofrecerlos para descarga
- En el ecosistema JavaScript existen varias librerías para generar distintos formatos
- Herramientas de ejemplo
Pyodide y WebAssembly
- Pyodide es una distribución que compila Python a WebAssembly para ejecutarlo en el navegador
- Como se puede cargar limpiamente desde un CDN, no hay razón para no usarlo en HTML tools
- Mediante micropip se pueden cargar adicionalmente paquetes puros de Python desde PyPI usando CORS
- Casos de herramientas
Ampliar aún más con WebAssembly
- La base que hace posible Pyodide es WebAssembly, y gracias a eso también se puede cargar en el navegador software escrito en otros lenguajes
- Squoosh.app ofrece varias librerías de compresión de imágenes en el navegador
- Casos de herramientas
Recombinación de herramientas anteriores
- Tener una sola colección pública con más de 100 herramientas es otra ventaja porque permite que el LLM las recombine fácilmente
- A veces se copian herramientas anteriores dentro del contexto, y con agentes de código se las referencia por nombre o se les pide buscar ejemplos
- El código fuente de herramientas funcionales actúa como documentación, incluyendo patrones de uso de librerías de edición, y aumenta la probabilidad de éxito del LLM
- Registro completo del proceso de creación de pypi-changelog: transcripción del prompt
- Se construyó un prompt indicando que revisara la herramienta “pypi package explorer”, luego leyera el código de zip-wheel-explorer, obtuviera wheels desde la API de PyPI, renderizara el diff entre versiones y creara una nueva herramienta con botón Copy
- También vale la pena revisar ejecutar OCR en el navegador
Registro de prompts y transcripciones
- Adoptar el hábito de guardar y publicar registros del uso de LLM ayuda a mejorar la propia capacidad de aprovechamiento
- En herramientas hechas en plataformas de LLM tipo chat, la función share se usa como mecanismo de registro
- Al usar agentes como Claude Code o Codex CLI, se copia la transcripción completa de la terminal, se convierte el log a HTML con terminal-to-html y luego se comparte como Gist
- Al guardar una herramienta terminada en el repo, se incluye el enlace a la transcripción en el mensaje del commit - colección de registros: tools.simonwillison.net/colophon
Cierre
- Durante el último año y medio, explorar LLM y herramientas HTML de esta forma ha sido muy entretenido, y ha ayudado mucho a entender hasta dónde puede llegar HTML y cuáles son las capacidades de los LLM
- Para empezar una colección propia de herramientas basta con crear un repo en GitHub y activar GitHub Pages para comenzar simplemente copiando archivos
.html
- Como extra, se comparte un enlace a la transcripción usada para añadir capturas de pantalla a este artículo con Claude Code y shot-scraper
3 comentarios
Patrones de HTML
Se ve interesante.
Qué genial