Open-Source Cold Email & Warmup Platform
Warmbly 是開源的冷郵件平台:溫暖您的收件箱、發送活動、並對每個回覆進行分流。可在我們的雲端運行或自行託管整個系統。
AI 翻譯
尚未偵測到更新。GitHub 發布版本後會顯示在這裡。
個人 GitHub 帳號下公開儲存庫的擁有者可以登入並驗證所有權,自行管理介紹,無需管理員核准。
登入並產生驗證檔案,在 30 分鐘內將其提交至此儲存庫的預設分支。其他分支或分叉儲存庫中的檔案無效。然後在下方檢查檔案,即可無需管理員核准直接管理專案。請保留檔案以維持管理權限。
如需登入,將前往登入頁面。登入後請回到此處,再次點擊所選的驗證按鈕。
在專案資料夾中執行 /nomorevibe verify,即可驗證所有權並自行管理介紹。
一分鐘完成驗證製作者的介紹僅有上面的一句話。 更多詳情請閱讀儲存庫 README。 儲存庫 README ↗
正在載入完整 README。
檢視完整 README ↗Plataforma web que conecta anunciantes con medios hiperlocales de Colombia para contratar, ejecutar, medir y liquidar pauta digital de forma estandarizada. Este repositorio contiene el front-end (Next.js) y el esquema de la base de datos (Supabase).
Si vas a desarrollar con un agente de IA, empieza por
AGENTS.md.
supabase login) para regenerar tipos y aplicar migracionespnpm install
cp .env.example .env.local # completa las variables (cada una está documentada en el archivo)
pnpm dev # http://localhost:3000
| Variable | Uso |
|---|---|
NEXT_PUBLIC_SUPABASE_URL, NEXT_PUBLIC_SUPABASE_PUBLISHABLE_KEY | Conexión pública a Supabase |
SUPABASE_SECRET_KEY | Clave secreta (solo servidor): gestión de usuarios y procedimientos privilegiados |
NEXT_PUBLIC_MAPBOX_TOKEN, NEXT_PUBLIC_MAPBOX_STYLE | Mapas (restringe el token por URL) |
NEXT_PUBLIC_SITE_URL | URL pública del sitio (enlaces de invitación y recuperación) |
AMO_SERVIDOR_SECRET | Secreto compartido servidor ↔ base de datos (también guardado en Supabase Vault) |
AMO_CIFRADO_KEY | Clave de cifrado de datos sensibles (k1:<base64 de 32 bytes>) |
SUPERADMIN_EMAIL | Correo del primer superadministrador |
AMO_SMTP_CONFIGURADO | true cuando Supabase Auth tenga SMTP propio |
AMO_CSP_MODO | enforce (por defecto) o report |
El build falla con un mensaje claro si falta una variable obligatoria.
| Entorno | Supabase | Variables | Datos |
|---|---|---|---|
| Producción | oriuuuaczpncmtglfgpv (ca-central-1) | .env.produccion | Solo los reales (nació vacío) |
| Develop | depbmnlpfnrcsbqlwxxd (us-east-1) | .env.develop, .env.db.develop | Banco de pruebas antes de producción |
| Local | supabase start (Docker) | .env.local | 15 meses de demo y cuentas de prueba (pnpm db:local) |
.env.produccion (ignorado por git; Next no lo carga en local) contiene las variables que se importan
en Vercel. Los scripts de arranque apuntan a otro entorno con AMO_ARCHIVO_ENTORNO, p. ej.
AMO_ARCHIVO_ENTORNO=.env.produccion pnpm bootstrap:superadmin. Lo que crea datos de prueba (E2E,
cuentas de pista, demo, carrera de cupos) se niega a correr contra producción.
Las migraciones están en supabase/migrations/ y son inmutables. Para un proyecto nuevo (así se
montó producción):
postgres.<ref>, puerto 5432;
contraseña alfanumérica o codificada) en un archivo .env.db (git lo ignora). Con --linked no sirve: el CLI entra como
cli_login_* y las migraciones de roles y tarifas exigen session_user = 'postgres'.supabase db push --db-url "$SUPABASE_DB_URL" --skip-vault — las 45 migraciones, con catálogos,
permisos, geografía, buckets y procesos programados. Sin --include-seed: supabase/seed/demo
nunca va a producción.amo_servidor_secret con el mismo valor que AMO_SERVIDOR_SECRET (como
postgres: select vault.create_secret('<valor>', 'amo_servidor_secret')).supabase/tests/*.sql (todas en begin … rollback) antes de la purga: algunas usan el
anunciante de pruebas. humo_roles_permisos_aplicables exige un superadministrador activo y se corre
tras el primer ingreso; en una base recién montada, a02 de humo_bitacora_indice falla por
volumen, no por esquema (ver su cabecera).negocio_actores crea el anunciante de pruebas e2e00000-0000-4000-8000-00000000a001
(lo usan las suites SQL y E2E). En producción se purga como postgres en una transacción:
set local amo.modo_carga='on'; set local amo.purga='on'; select private.purgar_demo(); y se borra
su fila de la bitácora (entidad='anunciantes', entidad_id = ese id).pnpm db:types (o MCP generate_typescript_types).Un proyecto nuevo nace con registro abierto, enlaces de 1 h y Site URL en localhost: hazlos antes
de desplegar. Ruta base: https://supabase.com/dashboard/project/<ref>/….
<sitio>/auth/callback, <sitio>/auth/confirm y <sitio>/**.private.acceso_valido()).vercel.app como https://front-*-<equipo>.vercel.app
(el de las vistas previas de Vercel): cualquiera puede crear en Vercel un proyecto cuyo dominio
encaje con el patrón y recibir allí los enlaces de sesión. Las vistas previas no usan producción.AMO_ARCHIVO_ENTORNO=.env.produccion pnpm bootstrap:superadmin # en desarrollo, sin la variable
Imprime un enlace de un solo uso (vigente lo que diga «Email OTP Expiration»; vuelve a ejecutarlo si venció). Al abrirlo defines tu contraseña y configuras la verificación en dos pasos con una app autenticadora. Desde Administración → Usuarios se invita al resto de superadministradores.
Un superadministrador puede restablecer la verificación en dos pasos de cualquier persona desde Administración → Usuarios. Si quien la perdió es el único superadministrador, quien administra el servidor ejecuta:
AMO_ARCHIVO_ENTORNO=.env.produccion pnpm bootstrap:restablecer-mfa [correo] # en desarrollo, sin la variable
Sin correo usa SUPERADMIN_EMAIL. Antes de usar el enlace, comprueba que la primera línea nombre el
proyecto oriuuuaczpncmtglfgpv (producción). Borra los factores de esa cuenta, lo registra en la
bitácora e imprime un enlace de un solo uso para definir una contraseña nueva y configurar el nuevo
dispositivo.
La base incluye 15 meses de operación simulada (40 anunciantes, 300 medios, 5.396 asignaciones,
liquidaciones, facturas y accesos desde 15 países), toda marcada como es_demo, y una cuenta por rol
(demo.admin, demo.operaciones, demo.finanzas, demo.anunciante, demo.medio, todas
@amo.test; credenciales DEMO_* en .env.local).
Se genera en dos partes porque los interruptores de carga solo funcionan como propietario de la base
de datos: las cuentas con pnpm demo:generar usuarios y los datos ejecutando en orden los SQL de
supabase/seed/demo/. El detalle, y cómo purgarlos con pnpm demo:purgar, está en
supabase/seed/demo/README.md.
| Comando | Qué hace |
|---|---|
pnpm dev / pnpm build / pnpm start | Desarrollo, compilación y servidor de producción |
pnpm typecheck · pnpm lint · pnpm format | Tipos, ESLint y Prettier |
pnpm test · pnpm test:e2e | Pruebas unitarias (Vitest) y de extremo a extremo (Playwright) |
pnpm geo:build | Regenera GeoJSON optimizados, diccionarios y semilla geográfica |
pnpm brand:build | Regenera logos e iconos |
pnpm db:types · pnpm db:permisos | Tipos de la base de datos · semilla del catálogo de permisos |
pnpm bootstrap:superadmin · pnpm bootstrap:e2e | Superadministrador · cuentas de prueba |
pnpm test:e2e:navegadores | Matriz de navegadores: Firefox, Safari, Safari iOS y Chrome Android |
pnpm db:local · pnpm db:suites local | Base local (Docker) reconstruida con demo y cuentas E2E · suites SQL |
pnpm db:push <entorno> · pnpm db:respaldo <entorno> | Aplica migraciones (develop, luego producción) · respaldo previo |
pnpm prod:config-pruebas · pnpm prod:limpiar-pruebas | Configuración de prueba del cliente · limpieza final (simula por defecto; ejecutar solo por orden expresa) |
pnpm pruebas:rendimiento-geo local | p95 del explorador geográfico (< 300 ms) |
src/app/ Rutas: (auth) acceso · (app) secciones privadas · api
src/components/ ui (shadcn/Base UI), layout, data-table, charts, kpi, maps, brand, motion, feedback
src/features/ Un directorio por dominio: acciones, consultas, esquemas, componentes y pruebas
src/lib/ auth (DAL, permisos, navegación), supabase, geo, export, utilidades
scripts/ geo, brand, db, bootstrap, demo, pruebas
supabase/ migrations, seed, tests
e2e/ Playwright
docs/ Guía de desarrollo, modelo de datos, KPIs, geodatos, marca
public/data/geo/ GeoJSON optimizados (países, departamentos y municipios por departamento)
docs/guia-desarrollo.md — convenciones, stack y flujo de trabajodocs/chuleta-apis.md — patrones verificados del códigodocs/modelo-datos.md — tablas, seguridad, funciones, estados y permisosdocs/kpis.md — indicadores e insightsdocs/geodatos.md — mapas y diccionarios geográficosdocs/marca.md — identidad visualcontext/ (documentos del cliente) y .env.local no se versionan..env.produccion, solo para Production (marca como sensibles las secretas).
ENABLE_EXPERIMENTAL_COREPACK=1 hace que el build use [email protected] (packageManager). En
Preview no publiques la SUPABASE_SECRET_KEY de producción: o sin variables o con las de
desarrollo.vercel.json fija la región yul1 (Montreal), junto a la base de datos (ca-central-1).https://front-amo.vercel.app (sin quitar
http://localhost:3000). Sin esto el explorador del mapa recibe 403 en producción.https://front-amo.vercel.app. Si Vercel asigna otro, cámbialo en
NEXT_PUBLIC_SITE_URL (y vuelve a desplegar: se incrusta al compilar), en la Site URL y las
Redirect URLs de Supabase y en las restricciones del token de Mapbox.main despliega (a producción): las vistas previas están apagadas en el proyecto
(previewDeploymentsDisabled, Settings → Git). Sin los secretos de producción el build de
develop o feature/* fallaría a propósito en la validación de variables. Si un merge a main
no genera despliegue, créalo desde Deployments → Create Deployment con la rama main.AMO_SMTP_CONFIGURADO=true.AMO_CIFRADO_KEY y AMO_SERVIDOR_SECRET de producción en un gestor de contraseñas: sin
la clave de cifrado, los datos bancarios cifrados no se recuperan.Hecho al montar producción: base sin datos demo ni cuentas de prueba, secretos propios (distintos de los de desarrollo) y región junto a la base. Mientras siga en plan gratuito: el proyecto se pausa tras 7 días sin uso (se reactiva desde el panel) y no hay copias descargables.