feat: Zona de marca tipo Estilo/Brief + brandbooks desde ads/RRSS

UI con nav lateral numerada y panel editable; parse de brandbook JSON string;
enrich desde Meta/Google/IG/FB/web/CSS para que app.4ventures.es muestre el kit.

Co-authored-by: Cursor <cursoragent@cursor.com>
This commit is contained in:
4Ventures
2026-10-15 03:23:23 +02:00
parent 102c100427
commit 3cb3ad1db1
10 changed files with 3967 additions and 69 deletions

View File

@@ -0,0 +1,52 @@
/**
* Auto-fill Zona de marca for all tenants (or one slug) + ensure Drive folders.
*
* npx tsx scripts/enrich_brandbooks.ts
* npx tsx scripts/enrich_brandbooks.ts bps
* DRY_RUN=1 npx tsx scripts/enrich_brandbooks.ts
* FORCE_SEED=1 npx tsx scripts/enrich_brandbooks.ts
*/
import { config } from 'dotenv';
import { resolve } from 'path';
config({ path: resolve(process.cwd(), '.env.local') });
import { enrichAllTenantBrandbooks } from '../src/lib/brandbook-enrich';
import { ensureCreativesDriveFolders } from '../src/lib/creatives-drive';
async function main() {
const slugFilter = process.argv[2]?.trim();
const dryRun = process.env.DRY_RUN === '1';
const forceSeed = process.env.FORCE_SEED === '1';
console.log(
`Enrich brandbooks · dryRun=${dryRun} · forceSeed=${forceSeed} · filter=${slugFilter || '*'}`
);
const results = await enrichAllTenantBrandbooks({
dryRun,
forceSeed,
slugFilter,
});
for (const r of results) {
console.log(
`[${r.slug}] ${r.ok ? 'OK' : 'FAIL'} · ${r.created ? 'created' : 'updated'} · ` +
`score ${r.completenessBefore}→${r.completenessAfter} · ` +
`sources=${r.sources.join('+')} · filled=${r.filledFields.slice(0, 12).join(',')}` +
(r.warning ? ` · ${r.warning}` : '')
);
if (r.ok && !dryRun) {
const drive = await ensureCreativesDriveFolders(r.tenantId, r.slug);
console.log(
` drive folders: ${drive.ok ? 'ads+rrss ok' : drive.warning || 'skip'}`
);
}
}
console.log(`Done · ${results.length} tenants`);
}
main().catch((e) => {
console.error(e);
process.exit(1);
});