create-lexy 0.6.1 → 0.6.2

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (2) hide show
  1. package/dist/index.js +528 -220
  2. package/package.json +1 -1
package/dist/index.js CHANGED
@@ -1,11 +1,11 @@
1
1
  #!/usr/bin/env node
2
- import{readFileSync as Po}from"fs";import tt from"path";import{fileURLToPath as jo}from"url";import{Command as Co}from"commander";import Io from"picocolors";import{spawn as ct}from"child_process";import Q from"fs/promises";import G from"path";import{confirm as dt,isCancel as pt,spinner as Te}from"@clack/prompts";import h from"picocolors";import te from"path";var ot=(e,t)=>t.architecture!=="feature"?e:e.replace(/from ["']@\/lib\/utils\/cn["']/g,'from "@/shared/lib/utils/cn"').replace(/from ["']@\/components\/base\//g,'from "@/shared/components/base/'),at=[["components/base/",e=>e.paths.components],["views/",e=>e.paths.views],["hooks/",e=>e.paths.hooks],["lib/",e=>e.paths.lib]],T=(e,t)=>e.files.filter(o=>typeof o.content=="string").map(o=>{let a=at.find(([r])=>o.path.startsWith(r)),n=a?te.posix.join(a[1](t),o.path.slice(a[0].length)):te.posix.join(t.paths.components,te.posix.basename(o.path));return o.encoding==="base64"?{relPath:n,content:o.content,encoding:"base64"}:{relPath:n,content:ot(o.content,t)}});import we from"fs/promises";import nt from"path";var Se=e=>nt.join(e,".lexy"),O=async e=>{let t;try{t=await we.readFile(Se(e),"utf-8")}catch{throw new Error("No se encontr\xF3 el archivo .lexy. \xBFEst\xE1s en la ra\xEDz de un proyecto Lexy? (cr\xE9alo con `npx create-lexy create`)")}let o=JSON.parse(t);if(!o.paths?.components)throw new Error("El .lexy no tiene paths.components \u2014 archivo corrupto o de una versi\xF3n incompatible.");return o.installed??={},o},ke=async(e,t)=>{await we.writeFile(Se(e),JSON.stringify(t,null,2)+`
3
- `)};import q from"fs/promises";import rt from"os";import R from"path";import{fileURLToPath as it}from"url";var Ee="@lexydesign/registry",F=`https://cdn.jsdelivr.net/npm/${Ee}`,st=8e3,J=R.resolve(R.dirname(it(import.meta.url)),"../assets"),lt=R.join(rt.homedir(),".cache","create-lexy","registry"),B=async e=>{let t=await fetch(e,{signal:AbortSignal.timeout(st)});if(!t.ok){let o=new Error(`HTTP ${t.status} al pedir ${e}`);throw o.status=t.status,o}return await t.json()},Pe=async e=>{try{return JSON.parse(await q.readFile(R.join(J,"r",e),"utf-8"))}catch{return null}},oe=async()=>{try{return(await q.readFile(R.join(J,"registry-version"),"utf-8")).trim()}catch{return"bundle"}},$=null,W=async()=>{if($)return $;try{$=(await B(`https://registry.npmjs.org/${Ee}/latest`)).version}catch{try{$=(await B(`${F}@latest/package.json`)).version}catch{$=await oe()}}return $},k=async(e,t)=>{let o=e.replace(/^@lexy\//,""),a=t??await W(),n=R.join(lt,a,`${o}.json`);try{return{item:JSON.parse(await q.readFile(n,"utf-8")),version:a,source:"cache"}}catch{}try{let r=await B(`${F}@${a}/r/${o}.json`);return await q.mkdir(R.dirname(n),{recursive:!0}),await q.writeFile(n,JSON.stringify(r)),{item:r,version:a,source:"cdn"}}catch(r){if(r.status===404)throw new Error(`El componente "${o}" no existe en el registry (versi\xF3n ${a}). Mira el cat\xE1logo con \`create-lexy view --list\`.`);let i=await Pe(`${o}.json`);if(i)return{item:i,version:await oe(),source:"bundle"};throw new Error(`No se pudo alcanzar el registry (\xBFsin red?) y "${o}" tampoco est\xE1 en el bundle local del CLI.`)}},je=async()=>{try{let e=await W();return{index:await B(`${F}@${e}/r/registry.json`),version:e,source:"cdn"}}catch{let e=await Pe("registry.json");if(e)return{index:e,version:await oe(),source:"bundle"};throw new Error("No se pudo alcanzar el registry ni leer el bundle local del CLI.")}},Ce=R.join(J,"theme/lexy-theme.css"),Ie=R.join(J,"fonts");var mt=(e,t)=>new Promise((o,a)=>{ct("pnpm",["add",...e],{cwd:t,stdio:"ignore",shell:!0}).on("close",r=>r===0?o():a(new Error(`pnpm add fall\xF3 con c\xF3digo ${r}`)))}),ut=async(e,t="utf-8")=>{try{return await Q.readFile(e,t)}catch{return null}},Re=async(e,t)=>{let o=process.cwd(),a=await O(o),n=Te();n.start("Resolviendo componentes en el registry...");let r=new Map,i=async p=>{let f=p.toLowerCase().replace(/^@lexy\//,"");if(r.has(f))return;let c=await k(f);r.set(f,c);for(let l of c.item.registryDependencies??[])await i(l)};try{for(let p of e)await i(p)}catch(p){throw n.stop(h.red("No se pudo resolver el pedido.")),p}let d=new Map;for(let[p,{item:f}]of r){let c=[];for(let l of T(f,a)){let g=await ut(G.join(o,l.relPath),l.encoding??"utf-8");c.push({...l,status:g===null?"new":g===l.content?"same":"differs"})}d.set(p,c)}let s=Array.from(d.values()).flat().filter(p=>p.status==="differs");if(n.stop(`Resueltos: ${Array.from(r.keys()).join(", ")}`),s.length>0&&!t.overwrite){let p=s.map(f=>` ${f.relPath}`).join(`
2
+ import{readFileSync as Po}from"fs";import tt from"path";import{fileURLToPath as jo}from"url";import{Command as Io}from"commander";import Co from"picocolors";import{spawn as ct}from"child_process";import Y from"fs/promises";import G from"path";import{confirm as dt,isCancel as pt,spinner as Te}from"@clack/prompts";import v from"picocolors";import te from"path";var ot=(e,t)=>t.architecture!=="feature"?e:e.replace(/from ["']@\/lib\/utils\/cn["']/g,'from "@/shared/lib/utils/cn"').replace(/from ["']@\/components\/base\//g,'from "@/shared/components/base/'),at=[["components/base/",e=>e.paths.components],["views/",e=>e.paths.views],["hooks/",e=>e.paths.hooks],["lib/",e=>e.paths.lib]],T=(e,t)=>e.files.filter(o=>typeof o.content=="string").map(o=>{let a=at.find(([r])=>o.path.startsWith(r)),n=a?te.posix.join(a[1](t),o.path.slice(a[0].length)):te.posix.join(t.paths.components,te.posix.basename(o.path));return o.encoding==="base64"?{relPath:n,content:o.content,encoding:"base64"}:{relPath:n,content:ot(o.content,t)}});import we from"fs/promises";import nt from"path";var Se=e=>nt.join(e,".lexy"),_=async e=>{let t;try{t=await we.readFile(Se(e),"utf-8")}catch{throw new Error("No se encontr\xF3 el archivo .lexy. \xBFEst\xE1s en la ra\xEDz de un proyecto Lexy? (cr\xE9alo con `npx create-lexy create`)")}let o=JSON.parse(t);if(!o.paths?.components)throw new Error("El .lexy no tiene paths.components \u2014 archivo corrupto o de una versi\xF3n incompatible.");return o.installed??={},o},ke=async(e,t)=>{await we.writeFile(Se(e),JSON.stringify(t,null,2)+`
3
+ `)};import q from"fs/promises";import rt from"os";import R from"path";import{fileURLToPath as it}from"url";var Ee="@lexydesign/registry",F=`https://cdn.jsdelivr.net/npm/${Ee}`,st=8e3,J=R.resolve(R.dirname(it(import.meta.url)),"../assets"),lt=R.join(rt.homedir(),".cache","create-lexy","registry"),B=async e=>{let t=await fetch(e,{signal:AbortSignal.timeout(st)});if(!t.ok){let o=new Error(`HTTP ${t.status} al pedir ${e}`);throw o.status=t.status,o}return await t.json()},Pe=async e=>{try{return JSON.parse(await q.readFile(R.join(J,"r",e),"utf-8"))}catch{return null}},oe=async()=>{try{return(await q.readFile(R.join(J,"registry-version"),"utf-8")).trim()}catch{return"bundle"}},$=null,W=async()=>{if($)return $;try{$=(await B(`https://registry.npmjs.org/${Ee}/latest`)).version}catch{try{$=(await B(`${F}@latest/package.json`)).version}catch{$=await oe()}}return $},k=async(e,t)=>{let o=e.replace(/^@lexy\//,""),a=t??await W(),n=R.join(lt,a,`${o}.json`);try{return{item:JSON.parse(await q.readFile(n,"utf-8")),version:a,source:"cache"}}catch{}try{let r=await B(`${F}@${a}/r/${o}.json`);return await q.mkdir(R.dirname(n),{recursive:!0}),await q.writeFile(n,JSON.stringify(r)),{item:r,version:a,source:"cdn"}}catch(r){if(r.status===404)throw new Error(`El componente "${o}" no existe en el registry (versi\xF3n ${a}). Mira el cat\xE1logo con \`create-lexy view --list\`.`);let i=await Pe(`${o}.json`);if(i)return{item:i,version:await oe(),source:"bundle"};throw new Error(`No se pudo alcanzar el registry (\xBFsin red?) y "${o}" tampoco est\xE1 en el bundle local del CLI.`)}},je=async()=>{try{let e=await W();return{index:await B(`${F}@${e}/r/registry.json`),version:e,source:"cdn"}}catch{let e=await Pe("registry.json");if(e)return{index:e,version:await oe(),source:"bundle"};throw new Error("No se pudo alcanzar el registry ni leer el bundle local del CLI.")}},Ie=R.join(J,"theme/lexy-theme.css"),Ce=R.join(J,"fonts");var mt=(e,t)=>new Promise((o,a)=>{ct("pnpm",["add",...e],{cwd:t,stdio:"ignore",shell:!0}).on("close",r=>r===0?o():a(new Error(`pnpm add fall\xF3 con c\xF3digo ${r}`)))}),ut=async(e,t="utf-8")=>{try{return await Y.readFile(e,t)}catch{return null}},Re=async(e,t)=>{let o=process.cwd(),a=await _(o),n=Te();n.start("Resolviendo componentes en el registry...");let r=new Map,i=async p=>{let f=p.toLowerCase().replace(/^@lexy\//,"");if(r.has(f))return;let c=await k(f);r.set(f,c);for(let l of c.item.registryDependencies??[])await i(l)};try{for(let p of e)await i(p)}catch(p){throw n.stop(v.red("No se pudo resolver el pedido.")),p}let d=new Map;for(let[p,{item:f}]of r){let c=[];for(let l of T(f,a)){let g=await ut(G.join(o,l.relPath),l.encoding??"utf-8");c.push({...l,status:g===null?"new":g===l.content?"same":"differs"})}d.set(p,c)}let s=Array.from(d.values()).flat().filter(p=>p.status==="differs");if(n.stop(`Resueltos: ${Array.from(r.keys()).join(", ")}`),s.length>0&&!t.overwrite){let p=s.map(f=>` ${f.relPath}`).join(`
4
4
  `);if(process.stdout.isTTY&&process.stdin.isTTY){let f=await dt({message:`Estos archivos existen con cambios locales y ser\xE1n sobrescritos:
5
5
  ${p}
6
- \xBFContinuar?`});if(pt(f)||f!==!0){console.log(h.yellow("Operaci\xF3n cancelada \u2014 nada fue modificado.")),process.exitCode=1;return}}else{console.error(h.red(`Estos archivos existen con cambios locales:
7
- `)+p+h.dim(`
8
- Usa --overwrite para sobrescribirlos.`)),process.exitCode=1;return}}for(let[p,f]of d){let{item:c,version:l,source:g}=r.get(p);for(let x of f){if(x.status==="same")continue;let A=G.join(o,x.relPath);await Q.mkdir(G.dirname(A),{recursive:!0}),await Q.writeFile(A,x.content,x.encoding??"utf-8")}a.installed[c.name]=l;let P=e.map(x=>x.toLowerCase()).includes(p)?"":h.dim(" (dependencia)"),U=g==="bundle"?h.yellow(" [bundle local \u2014 sin red]"):"";console.log(h.green(`${h.bold(c.title??c.name)} instalado`)+P+h.cyan(` \u2192 ${a.paths.components}/`)+U);for(let x of f){let A=x.status==="same"?h.dim(" (sin cambios)"):"";console.log(h.dim(` ${x.relPath}${A}`))}}await ke(o,a);let u=new Set;for(let{item:p}of r.values())for(let f of p.dependencies??[])u.add(f);let m=JSON.parse(await Q.readFile(G.join(o,"package.json"),"utf-8")),y={...m.dependencies,...m.devDependencies},z=p=>{let f=p.lastIndexOf("@");return f>0?p.slice(0,f):p},M=Array.from(u).filter(p=>!y[z(p)]);if(M.length>0)if(t.install===!1)console.log(h.yellow(`Dependencias pendientes (inst\xE1lalas t\xFA): ${M.join(", ")}`));else{let p=Te();p.start(`Instalando dependencias: ${M.join(", ")}...`),await mt(M,o),p.stop("Dependencias instaladas.")}};import{spawn as po}from"child_process";import{note as mo,outro as uo,spinner as yo}from"@clack/prompts";import j from"picocolors";import{cancel as yt,intro as ft,isCancel as gt,select as Oe,text as xt}from"@clack/prompts";import _e from"picocolors";var ae=[{value:"screen",label:"Una pantalla o flujo corto",hint:"landing, formulario, demo \u2014 sin navegaci\xF3n entre secciones",architecture:"layer"},{value:"app",label:"Una app con secciones y navegaci\xF3n",hint:"dashboard, listados, detalle \u2014 varias vistas con router",architecture:"feature"}],Ne=e=>ae.find(t=>t.value===e).architecture;var vt=`
6
+ \xBFContinuar?`});if(pt(f)||f!==!0){console.log(v.yellow("Operaci\xF3n cancelada \u2014 nada fue modificado.")),process.exitCode=1;return}}else{console.error(v.red(`Estos archivos existen con cambios locales:
7
+ `)+p+v.dim(`
8
+ Usa --overwrite para sobrescribirlos.`)),process.exitCode=1;return}}for(let[p,f]of d){let{item:c,version:l,source:g}=r.get(p);for(let x of f){if(x.status==="same")continue;let A=G.join(o,x.relPath);await Y.mkdir(G.dirname(A),{recursive:!0}),await Y.writeFile(A,x.content,x.encoding??"utf-8")}a.installed[c.name]=l;let P=e.map(x=>x.toLowerCase()).includes(p)?"":v.dim(" (dependencia)"),U=g==="bundle"?v.yellow(" [bundle local \u2014 sin red]"):"";console.log(v.green(`${v.bold(c.title??c.name)} instalado`)+P+v.cyan(` \u2192 ${a.paths.components}/`)+U);for(let x of f){let A=x.status==="same"?v.dim(" (sin cambios)"):"";console.log(v.dim(` ${x.relPath}${A}`))}}await ke(o,a);let u=new Set;for(let{item:p}of r.values())for(let f of p.dependencies??[])u.add(f);let m=JSON.parse(await Y.readFile(G.join(o,"package.json"),"utf-8")),y={...m.dependencies,...m.devDependencies},z=p=>{let f=p.lastIndexOf("@");return f>0?p.slice(0,f):p},M=Array.from(u).filter(p=>!y[z(p)]);if(M.length>0)if(t.install===!1)console.log(v.yellow(`Dependencias pendientes (inst\xE1lalas t\xFA): ${M.join(", ")}`));else{let p=Te();p.start(`Instalando dependencias: ${M.join(", ")}...`),await mt(M,o),p.stop("Dependencias instaladas.")}};import{spawn as po}from"child_process";import{note as mo,outro as uo,spinner as yo}from"@clack/prompts";import j from"picocolors";import{cancel as yt,intro as ft,isCancel as gt,select as _e,text as xt}from"@clack/prompts";import Oe from"picocolors";var ae=[{value:"screen",label:"Una pantalla o flujo corto",hint:"landing, formulario, demo \u2014 sin navegaci\xF3n entre secciones",architecture:"layer"},{value:"app",label:"Una app con secciones y navegaci\xF3n",hint:"dashboard, listados, detalle \u2014 varias vistas con router",architecture:"feature"}],Ne=e=>ae.find(t=>t.value===e).architecture;var ht=`
9
9
  ###### ######
10
10
  ##::+#### ####+::##
11
11
  #-..:+################+:..:#
@@ -20,8 +20,8 @@ Usa --overwrite para sobrescribirlos.`)),process.exitCode=1;return}}for(let[p,f]
20
20
  ...........:====:...........
21
21
  ......................
22
22
  ..............
23
- `,ne=e=>{gt(e)&&(yt("Operaci\xF3n cancelada por el usuario."),process.exit(0))},Ae=async e=>{console.clear(),ft(`${_e.cyan(vt)}
24
- ${_e.bold(" Bienvenido al generador de proyectos Lexy")}`);let t=e;if(!t){let n=await xt({message:"\xBFCu\xE1l es el nombre de tu proyecto?",placeholder:"lexy-app",validate:r=>{if(!r||r.trim()==="")return"El nombre es obligatorio.";if(!/^(?:@[a-z0-9-*~][a-z0-9-*._~]*\/)?[a-z0-9-~][a-z0-9-._~]*$/.test(r))return"El nombre debe estar en min\xFAsculas, sin espacios ni caracteres especiales."}});ne(n),t=n}let o=await Oe({message:"\xBFPara qui\xE9n es este proyecto?",options:[{label:"Clientes de Lexy",value:"cliente",hint:"Producto de cara al cliente final"},{label:"Equipo interno / CRM",value:"crm",hint:"Herramienta densa para el equipo Lexy"},{label:"Ambos o a\xFAn no lo s\xE9",value:"mixto",hint:"Se decide por pantalla m\xE1s adelante"}],initialValue:"mixto"});ne(o);let a=await Oe({message:"\xBFC\xF3mo es lo que vas a construir?",options:ae.map(n=>({label:n.label,value:n.value,hint:n.hint})),initialValue:"app"});return ne(a),{projectName:t,architecture:Ne(a),world:o}};import b from"fs/promises";import w from"path";import{format as qt,resolveConfig as Vt}from"prettier";import Le from"fs/promises";import De from"path";var re="src/prototype/data-contract/prototype-data-contract.ts",ht="src/prototype/data-contract/data-contract-schema.ts",bt="scripts/check-data-contract.ts",wt=String.raw`import { z } from "zod";
23
+ `,ne=e=>{gt(e)&&(yt("Operaci\xF3n cancelada por el usuario."),process.exit(0))},Ae=async e=>{console.clear(),ft(`${Oe.cyan(ht)}
24
+ ${Oe.bold(" Bienvenido al generador de proyectos Lexy")}`);let t=e;if(!t){let n=await xt({message:"\xBFCu\xE1l es el nombre de tu proyecto?",placeholder:"lexy-app",validate:r=>{if(!r||r.trim()==="")return"El nombre es obligatorio.";if(!/^(?:@[a-z0-9-*~][a-z0-9-*._~]*\/)?[a-z0-9-~][a-z0-9-._~]*$/.test(r))return"El nombre debe estar en min\xFAsculas, sin espacios ni caracteres especiales."}});ne(n),t=n}let o=await _e({message:"\xBFPara qui\xE9n es este proyecto?",options:[{label:"Clientes de Lexy",value:"cliente",hint:"Producto de cara al cliente final"},{label:"Equipo interno / CRM",value:"crm",hint:"Herramienta densa para el equipo Lexy"},{label:"Ambos o a\xFAn no lo s\xE9",value:"mixto",hint:"Se decide por pantalla m\xE1s adelante"}],initialValue:"mixto"});ne(o);let a=await _e({message:"\xBFC\xF3mo es lo que vas a construir?",options:ae.map(n=>({label:n.label,value:n.value,hint:n.hint})),initialValue:"app"});return ne(a),{projectName:t,architecture:Ne(a),world:o}};import b from"fs/promises";import w from"path";import{format as qt,resolveConfig as Vt}from"prettier";import Le from"fs/promises";import De from"path";var re="src/prototype/data-contract/prototype-data-contract.ts",vt="src/prototype/data-contract/data-contract-schema.ts",bt="scripts/check-data-contract.ts",wt=String.raw`import { z } from "zod";
25
25
 
26
26
  const camelCaseIdSchema = z
27
27
  .string()
@@ -509,9 +509,8 @@ export const prototypeDataContract = definePrototypeDataContract({
509
509
  relations: [],
510
510
  projections: {},
511
511
  });
512
- `,ze=async(e,t)=>{let o=async(a,n)=>{let r=De.join(e,a);await Le.mkdir(De.dirname(r),{recursive:!0}),await Le.writeFile(r,n)};await o(ht,wt),await o(re,kt(t)),await o(bt,St)};import Me from"fs/promises";import ie from"path";var se="src/prototype/designer-panel/designer-activity.ts",le="src/prototype/designer-panel/PrototypeDesignerPanel.tsx",Et=String.raw`export type DesignerActivityRecordInput = {
512
+ `,ze=async(e,t)=>{let o=async(a,n)=>{let r=De.join(e,a);await Le.mkdir(De.dirname(r),{recursive:!0}),await Le.writeFile(r,n)};await o(vt,wt),await o(re,kt(t)),await o(bt,St)};import Me from"fs/promises";import ie from"path";var se="src/prototype/designer-panel/designer-activity.ts",le="src/prototype/designer-panel/PrototypeDesignerPanel.tsx",Et=String.raw`export type DesignerActivityRecordInput = {
513
513
  kind: "load" | "event";
514
- label: string;
515
514
  technicalId?: string;
516
515
  triggerId?: string;
517
516
  input?: unknown;
@@ -521,7 +520,6 @@ export type DesignerActivityRecord = {
521
520
  id: string;
522
521
  occurredAt: string;
523
522
  kind: "load" | "event";
524
- label: string;
525
523
  technicalId?: string;
526
524
  triggerId?: string;
527
525
  inputPreview?: string;
@@ -604,7 +602,7 @@ export const createDesignerActivityStore = (maxItems = 80): DesignerActivityStor
604
602
  id: tabId + "_" + sequence,
605
603
  occurredAt: new Date().toISOString(),
606
604
  kind: input.kind,
607
- label: input.label,
605
+ label: input.technicalId ?? "evento",
608
606
  ...(input.technicalId ? { technicalId: input.technicalId } : {}),
609
607
  ...(input.triggerId ? { triggerId: input.triggerId } : {}),
610
608
  ...(preview(input.input) ? { inputPreview: preview(input.input) } : {}),
@@ -624,38 +622,70 @@ export const designerActivity = createDesignerActivityStore();
624
622
  `,Pt=`
625
623
  .lexy-dp {
626
624
  --dp-bg: #ffffff;
627
- --dp-fg: #242424;
628
- --dp-card: #fafafa;
625
+ --dp-fg: #0f172a;
626
+ --dp-card: #ffffff;
629
627
  --dp-popover: #ffffff;
630
- --dp-primary: #4648d4;
628
+ --dp-primary: #4f46e5;
631
629
  --dp-primary-fg: #ffffff;
632
- --dp-muted: #f5f5f5;
633
- --dp-muted-fg: #616161;
634
- --dp-accent: #ebf3fc;
635
- --dp-accent-fg: #4648d4;
636
- --dp-border: #d1d1d1;
637
- --dp-ring: #4648d4;
638
- --dp-destructive: #d13438;
639
- --dp-success: #107c10;
630
+ --dp-muted: #f8fafc;
631
+ --dp-muted-fg: #475569;
632
+ --dp-accent: #e0e7ff;
633
+ --dp-accent-fg: #4f46e5;
634
+ --dp-border: #e2e8f0;
635
+ --dp-ring: #c7d2fe;
636
+ --dp-destructive: #ef4444;
637
+ --dp-success: #10b981;
640
638
  --dp-success-fg: #ffffff;
641
- --dp-warning: #f7630c;
639
+ --dp-warning: #f59e0b;
642
640
  --dp-warning-fg: #ffffff;
643
- --dp-info: #0f6cbd;
644
- --dp-radius: 0.5rem;
645
- --dp-mono: ui-monospace, SFMono-Regular, Menlo, Consolas, "Liberation Mono", monospace;
646
- --dp-sans: system-ui, -apple-system, "Segoe UI", Roboto, "Helvetica Neue", Arial, sans-serif;
641
+ --dp-info: #0ea5e9;
642
+ --dp-radius: 8px;
643
+ --dp-mono: SFMono-Regular, Consolas, "Liberation Mono", Menlo, Courier, monospace;
644
+ --dp-sans: "Inter", system-ui, -apple-system, sans-serif;
647
645
  color: var(--dp-fg);
648
646
  font-family: var(--dp-sans);
649
- font-size: 14px;
650
- line-height: 1.4;
647
+ font-size: 13.5px;
648
+ line-height: 1.5;
651
649
  }
652
650
  .lexy-dp *, .lexy-dp *::before, .lexy-dp *::after { box-sizing: border-box; }
653
651
  .lexy-dp p, .lexy-dp h1, .lexy-dp pre, .lexy-dp ul { margin: 0; }
654
652
  .lexy-dp ul { list-style: none; padding: 0; }
655
- .lexy-dp button { font-family: inherit; color: inherit; }
653
+ .lexy-dp button { font-family: inherit; color: inherit; border: none; background: transparent; cursor: pointer; outline: none; }
656
654
  .lexy-dp code { font-family: var(--dp-mono); }
657
655
 
658
- /* \u2500\u2500 P\xE1gina completa \u2500\u2500 */
656
+ /* Custom Scrollbars */
657
+ .lexy-dp .lexy-dp-scroll::-webkit-scrollbar,
658
+ .lexy-dp .lexy-dp-split__list::-webkit-scrollbar,
659
+ .lexy-dp .lexy-dp-split__detail::-webkit-scrollbar,
660
+ .lexy-dp .lexy-dp-sheet__body::-webkit-scrollbar,
661
+ .lexy-dp .lexy-dp-snippet::-webkit-scrollbar {
662
+ width: 6px;
663
+ height: 6px;
664
+ }
665
+ .lexy-dp .lexy-dp-scroll::-webkit-scrollbar-track,
666
+ .lexy-dp .lexy-dp-split__list::-webkit-scrollbar-track,
667
+ .lexy-dp .lexy-dp-split__detail::-webkit-scrollbar-track,
668
+ .lexy-dp .lexy-dp-sheet__body::-webkit-scrollbar-track,
669
+ .lexy-dp .lexy-dp-snippet::-webkit-scrollbar-track {
670
+ background: transparent;
671
+ }
672
+ .lexy-dp .lexy-dp-scroll::-webkit-scrollbar-thumb,
673
+ .lexy-dp .lexy-dp-split__list::-webkit-scrollbar-thumb,
674
+ .lexy-dp .lexy-dp-split__detail::-webkit-scrollbar-thumb,
675
+ .lexy-dp .lexy-dp-sheet__body::-webkit-scrollbar-thumb,
676
+ .lexy-dp .lexy-dp-snippet::-webkit-scrollbar-thumb {
677
+ background: rgba(0, 0, 0, 0.12);
678
+ border-radius: 9999px;
679
+ }
680
+ .lexy-dp .lexy-dp-scroll::-webkit-scrollbar-thumb:hover,
681
+ .lexy-dp .lexy-dp-split__list::-webkit-scrollbar-thumb:hover,
682
+ .lexy-dp .lexy-dp-split__detail::-webkit-scrollbar-thumb:hover,
683
+ .lexy-dp .lexy-dp-sheet__body::-webkit-scrollbar-thumb:hover,
684
+ .lexy-dp .lexy-dp-snippet::-webkit-scrollbar-thumb:hover {
685
+ background: rgba(0, 0, 0, 0.24);
686
+ }
687
+
688
+ /* \u2500\u2500 Full Page \u2500\u2500 */
659
689
  .lexy-dp-page {
660
690
  display: flex;
661
691
  flex-direction: column;
@@ -668,73 +698,99 @@ export const designerActivity = createDesignerActivityStore();
668
698
  display: flex;
669
699
  align-items: stretch;
670
700
  border-bottom: 1px solid var(--dp-border);
671
- padding: 0 12px;
672
- background: var(--dp-bg);
701
+ padding: 0 16px;
702
+ background: #ffffff;
703
+ gap: 8px;
673
704
  }
674
705
  .lexy-dp-tab {
675
706
  display: inline-flex;
676
707
  align-items: center;
677
- gap: 6px;
678
- padding: 8px 12px;
679
- font-size: 12px;
680
- border: none;
708
+ gap: 8px;
709
+ padding: 12px 14px;
710
+ font-size: 13px;
681
711
  border-bottom: 2px solid transparent;
682
712
  margin-bottom: -1px;
683
- background: transparent;
684
713
  color: var(--dp-muted-fg);
685
- border-radius: 0;
686
- cursor: pointer;
714
+ font-weight: 500;
715
+ transition: all 0.2s ease;
687
716
  }
688
717
  .lexy-dp-tab:hover { color: var(--dp-fg); }
689
- .lexy-dp-tab.is-active { color: var(--dp-primary); font-weight: 500; border-bottom-color: var(--dp-primary); }
690
- .lexy-dp-tab svg { width: 14px; height: 14px; }
718
+ .lexy-dp-tab.is-active {
719
+ color: var(--dp-primary);
720
+ font-weight: 600;
721
+ border-bottom-color: var(--dp-primary);
722
+ }
723
+ .lexy-dp-tab svg { width: 15px; height: 15px; opacity: 0.8; }
724
+ .lexy-dp-tab.is-active svg { opacity: 1; color: var(--dp-primary); }
725
+
691
726
  .lexy-dp-tabbadge {
692
727
  margin-left: 4px;
693
728
  border-radius: 9999px;
694
729
  background: var(--dp-warning);
695
730
  color: var(--dp-warning-fg);
696
- padding: 0 6px;
731
+ padding: 1px 6px;
697
732
  font-size: 10px;
698
- font-weight: 500;
733
+ font-weight: 600;
699
734
  }
700
735
  .lexy-dp-body { flex: 1; min-height: 0; }
701
736
  .lexy-dp-panel { height: 100%; }
702
737
 
703
- /* \u2500\u2500 Scroll y padding \u2500\u2500 */
738
+ /* \u2500\u2500 Scroll & Padding \u2500\u2500 */
704
739
  .lexy-dp-scroll { height: 100%; overflow-y: auto; }
705
- .lexy-dp-pad { padding: 20px 24px; }
740
+ .lexy-dp-pad { padding: 24px; }
706
741
 
707
- /* \u2500\u2500 Columna y toolbar \u2500\u2500 */
742
+ /* \u2500\u2500 Column & Toolbar \u2500\u2500 */
708
743
  .lexy-dp-col { display: flex; flex-direction: column; height: 100%; }
709
744
  .lexy-dp-toolbar {
710
745
  display: flex;
711
746
  align-items: center;
712
- gap: 4px;
747
+ gap: 8px;
713
748
  border-bottom: 1px solid var(--dp-border);
714
- background: var(--dp-bg);
715
- padding: 4px 8px;
749
+ background: #f8fafc;
750
+ padding: 8px 16px;
716
751
  }
717
752
 
718
- /* \u2500\u2500 Botones \u2500\u2500 */
753
+ /* \u2500\u2500 Buttons \u2500\u2500 */
719
754
  .lexy-dp-btn {
720
755
  display: inline-flex;
721
756
  align-items: center;
722
757
  justify-content: center;
723
- gap: 6px;
724
- padding: 6px 12px;
758
+ gap: 8px;
759
+ padding: 8px 16px;
725
760
  font-size: 13px;
761
+ font-weight: 500;
726
762
  border-radius: var(--dp-radius);
727
763
  border: 1px solid transparent;
728
764
  background: var(--dp-primary);
729
765
  color: var(--dp-primary-fg);
730
- cursor: pointer;
766
+ box-shadow: 0 1px 2px rgba(79, 70, 229, 0.1);
767
+ transition: all 0.2s cubic-bezier(0.4, 0, 0.2, 1);
768
+ }
769
+ .lexy-dp-btn:hover {
770
+ opacity: 0.95;
771
+ transform: translateY(-1px);
772
+ box-shadow: 0 4px 8px rgba(79, 70, 229, 0.15);
773
+ }
774
+ .lexy-dp-btn:active { transform: translateY(0); }
775
+ .lexy-dp-btn:disabled {
776
+ opacity: 0.4;
777
+ cursor: not-allowed;
778
+ transform: none !important;
779
+ box-shadow: none !important;
780
+ }
781
+ .lexy-dp-btn--outline {
782
+ background: transparent;
783
+ border-color: var(--dp-border);
784
+ color: var(--dp-fg);
785
+ box-shadow: none;
786
+ }
787
+ .lexy-dp-btn--outline:hover {
788
+ background: var(--dp-muted);
789
+ border-color: var(--dp-border);
790
+ box-shadow: none;
731
791
  }
732
- .lexy-dp-btn:hover { opacity: 0.92; }
733
- .lexy-dp-btn:disabled { opacity: 0.5; cursor: not-allowed; }
734
- .lexy-dp-btn--outline { background: transparent; border-color: var(--dp-border); color: var(--dp-fg); }
735
- .lexy-dp-btn--outline:hover { background: var(--dp-muted); opacity: 1; }
736
792
  .lexy-dp-btn--outline:disabled:hover { background: transparent; }
737
- .lexy-dp-btn--sm { padding: 4px 10px; font-size: 12px; }
793
+ .lexy-dp-btn--sm { padding: 5px 12px; font-size: 12px; }
738
794
  .lexy-dp-btn svg { width: 14px; height: 14px; }
739
795
 
740
796
  /* \u2500\u2500 Badges \u2500\u2500 */
@@ -742,218 +798,376 @@ export const designerActivity = createDesignerActivityStore();
742
798
  display: inline-flex;
743
799
  align-items: center;
744
800
  border-radius: 9999px;
745
- padding: 1px 8px;
801
+ padding: 2px 10px;
746
802
  font-size: 11px;
747
- font-weight: 500;
803
+ font-weight: 600;
748
804
  border: 1px solid transparent;
749
- background: var(--dp-primary);
750
- color: var(--dp-primary-fg);
805
+ background: rgba(79, 70, 229, 0.08);
806
+ color: var(--dp-primary);
751
807
  white-space: nowrap;
752
808
  }
753
- .lexy-dp-badge--outline { background: var(--dp-muted); color: var(--dp-muted-fg); border-color: var(--dp-border); }
754
- .lexy-dp-badge--success { background: var(--dp-success); color: var(--dp-success-fg); }
755
- .lexy-dp-badge--warning { background: var(--dp-warning); color: var(--dp-warning-fg); }
809
+ .lexy-dp-badge--outline {
810
+ background: var(--dp-muted);
811
+ color: var(--dp-muted-fg);
812
+ border-color: var(--dp-border);
813
+ }
814
+ .lexy-dp-badge--success {
815
+ background: rgba(16, 185, 129, 0.1);
816
+ color: #047857;
817
+ }
818
+ .lexy-dp-badge--warning {
819
+ background: rgba(245, 158, 11, 0.1);
820
+ color: #b45309;
821
+ }
756
822
 
757
823
  /* \u2500\u2500 Cards \u2500\u2500 */
758
824
  .lexy-dp-card {
759
825
  border: 1px solid var(--dp-border);
760
826
  background: var(--dp-card);
761
827
  border-radius: var(--dp-radius);
762
- box-shadow: 0 1px 2px rgba(0, 0, 0, 0.05);
763
- padding: 12px 14px;
828
+ box-shadow: 0 1px 3px rgba(0, 0, 0, 0.05);
829
+ padding: 16px;
830
+ transition: all 0.2s ease;
831
+ }
832
+ .lexy-dp-card:hover {
833
+ border-color: rgba(79, 70, 229, 0.2);
834
+ box-shadow: 0 4px 12px rgba(0, 0, 0, 0.05);
764
835
  }
765
- .lexy-dp-card__title { font-size: 14px; font-weight: 600; }
766
- .lexy-dp-card__desc { font-size: 13px; color: var(--dp-muted-fg); margin-top: 2px; }
767
- .lexy-dp-card__content { margin-top: 10px; }
836
+ .lexy-dp-card__title { font-size: 14.5px; font-weight: 600; color: var(--dp-fg); }
837
+ .lexy-dp-card__desc { font-size: 12.5px; color: var(--dp-muted-fg); margin-top: 4px; line-height: 1.4; }
838
+ .lexy-dp-card__content { margin-top: 14px; }
768
839
  .lexy-dp-card__head-row { display: flex; align-items: flex-start; justify-content: space-between; gap: 12px; }
769
840
 
770
841
  /* \u2500\u2500 Searchbox \u2500\u2500 */
771
842
  .lexy-dp-search { position: relative; display: flex; align-items: center; flex: 1; }
772
843
  .lexy-dp-search input {
773
844
  width: 100%;
774
- padding: 3px 26px 3px 8px;
775
- font-size: 12px;
845
+ padding: 6px 30px 6px 12px;
846
+ font-size: 12.5px;
776
847
  font-family: inherit;
777
848
  border: 1px solid var(--dp-border);
778
- border-radius: 3px;
779
- background: var(--dp-bg);
849
+ border-radius: 6px;
850
+ background: #ffffff;
780
851
  color: var(--dp-fg);
852
+ transition: all 0.2s ease;
853
+ }
854
+ .lexy-dp-search input:focus {
855
+ outline: none;
856
+ border-color: var(--dp-primary);
857
+ box-shadow: 0 0 0 3px rgba(79, 70, 229, 0.15);
781
858
  }
782
- .lexy-dp-search input:focus { outline: 2px solid var(--dp-ring); outline-offset: -1px; }
783
859
  .lexy-dp-search__clear {
784
860
  position: absolute;
785
- right: 6px;
861
+ right: 10px;
786
862
  border: none;
787
863
  background: transparent;
788
864
  color: var(--dp-muted-fg);
789
865
  cursor: pointer;
790
866
  padding: 2px;
791
867
  display: inline-flex;
868
+ transition: color 0.15s ease;
792
869
  }
870
+ .lexy-dp-search__clear:hover { color: var(--dp-fg); }
793
871
  .lexy-dp-search__clear svg { width: 14px; height: 14px; }
794
872
 
795
- /* \u2500\u2500 Snippet / separador / etiquetas \u2500\u2500 */
873
+ /* \u2500\u2500 Snippet \u2500\u2500 */
796
874
  .lexy-dp-snippet {
797
875
  font-family: var(--dp-mono);
798
876
  font-size: 12px;
799
- background: var(--dp-muted);
877
+ background: #f8fafc;
800
878
  border: 1px solid var(--dp-border);
801
879
  border-radius: var(--dp-radius);
802
- padding: 10px 12px;
880
+ padding: 12px 14px;
803
881
  overflow: auto;
804
882
  white-space: pre;
805
- color: var(--dp-fg);
883
+ color: #334155;
806
884
  }
807
- .lexy-dp-sep { border: none; border-top: 1px solid var(--dp-border); height: 1px; }
885
+ .lexy-dp-sep { border: none; border-top: 1px solid var(--dp-border); height: 1px; margin: 20px 0; }
808
886
  .lexy-dp-section-label {
809
- font-size: 12px;
810
- font-weight: 500;
887
+ font-size: 11.5px;
888
+ font-weight: 600;
811
889
  text-transform: uppercase;
812
- letter-spacing: 0.04em;
813
- color: var(--dp-muted-fg);
890
+ letter-spacing: 0.05em;
891
+ color: #64748b;
892
+ margin-bottom: 8px;
814
893
  }
815
894
  .lexy-dp-muted { color: var(--dp-muted-fg); }
816
895
  .lexy-dp-mono { font-family: var(--dp-mono); }
817
- .lexy-dp-empty { padding: 16px 12px; color: var(--dp-muted-fg); font-size: 13px; }
896
+ .lexy-dp-empty { padding: 24px 16px; color: var(--dp-muted-fg); font-size: 13px; text-align: center; }
818
897
 
819
- .lexy-dp-log__event { color: var(--dp-fg); }
898
+ .lexy-dp-log__event { color: var(--dp-fg); font-weight: 600; }
820
899
 
821
- /* \u2500\u2500 Stacks y grids \u2500\u2500 */
822
- .lexy-dp-stack { display: flex; flex-direction: column; gap: 2px; }
823
- .lexy-dp-stack-sm { display: flex; flex-direction: column; gap: 6px; }
824
- .lexy-dp-stack-lg { display: flex; flex-direction: column; gap: 12px; }
825
- .lexy-dp-substack { display: flex; flex-direction: column; gap: 2px; padding-left: 16px; color: var(--dp-muted-fg); }
826
- .lexy-dp-grid2 { display: grid; grid-template-columns: 1fr 1fr; gap: 8px; }
900
+ /* \u2500\u2500 Stacks & Grids \u2500\u2500 */
901
+ .lexy-dp-stack { display: flex; flex-direction: column; gap: 4px; }
902
+ .lexy-dp-stack-sm { display: flex; flex-direction: column; gap: 8px; }
903
+ .lexy-dp-stack-lg { display: flex; flex-direction: column; gap: 16px; }
904
+ .lexy-dp-substack { display: flex; flex-direction: column; gap: 4px; padding-left: 18px; color: var(--dp-muted-fg); }
905
+ .lexy-dp-grid2 { display: grid; grid-template-columns: 1fr 1fr; gap: 12px; }
827
906
 
828
- /* \u2500\u2500 \xC1rbol JSON \u2500\u2500 */
829
- .lexy-dp-json-str { color: var(--dp-fg); }
830
- .lexy-dp-json-num { color: var(--dp-info); }
831
- .lexy-dp-json-row { display: flex; align-items: flex-start; gap: 4px; padding: 1px 0; }
907
+ /* \u2500\u2500 JSON Tree \u2500\u2500 */
908
+ .lexy-dp-json-str { color: #047857; } /* Emerald green */
909
+ .lexy-dp-json-num { color: #0284c7; } /* Sky blue */
910
+ .lexy-dp-json-row { display: flex; align-items: flex-start; gap: 6px; padding: 2px 0; }
832
911
  .lexy-dp-json-spacer { width: 14px; height: 14px; flex-shrink: 0; }
833
912
  .lexy-dp-json-leaf { min-width: 0; word-break: break-word; }
834
913
  .lexy-dp-json-toggle {
835
914
  display: flex;
836
915
  width: 100%;
837
916
  align-items: flex-start;
838
- gap: 4px;
839
- padding: 1px 0;
917
+ gap: 6px;
918
+ padding: 3px 6px;
840
919
  text-align: left;
841
920
  background: transparent;
842
- border: none;
843
- cursor: pointer;
921
+ border-radius: 4px;
922
+ transition: background 0.15s ease;
844
923
  }
845
- .lexy-dp-json-toggle:hover { background: var(--dp-muted); }
846
- .lexy-dp-chevron { width: 14px; height: 14px; flex-shrink: 0; color: var(--dp-muted-fg); margin-top: 1px; }
847
- .lexy-dp-chevron--sm { width: 12px; height: 12px; margin-top: 0; }
848
- .lexy-dp-chevron.is-open { transform: rotate(90deg); }
924
+ .lexy-dp-json-toggle:hover { background: rgba(0, 0, 0, 0.03); }
925
+ .lexy-dp-chevron { width: 14px; height: 14px; flex-shrink: 0; color: var(--dp-muted-fg); margin-top: 2px; transition: transform 0.2s cubic-bezier(0.4, 0, 0.2, 1); }
926
+ .lexy-dp-chevron--sm { width: 12px; height: 12px; margin-top: 1px; }
927
+ .lexy-dp-chevron.is-open { transform: rotate(90deg); color: var(--dp-fg); }
849
928
 
850
- /* \u2500\u2500 Log de actividad \u2500\u2500 */
929
+ /* \u2500\u2500 Activity Log \u2500\u2500 */
851
930
  .lexy-dp-activitylog {
852
931
  min-height: 100%;
853
932
  background: var(--dp-bg);
854
- padding: 4px 0;
933
+ padding: 8px 0;
855
934
  font-family: var(--dp-mono);
856
- font-size: 12px;
857
- line-height: 1.5;
935
+ font-size: 12.5px;
936
+ line-height: 1.6;
858
937
  color: var(--dp-fg);
859
938
  }
860
939
  .lexy-dp-activitylog--scroll { flex: 1; min-height: 0; overflow-y: auto; }
861
- .lexy-dp-log { border-bottom: 1px solid var(--dp-border); }
940
+ .lexy-dp-log {
941
+ border-bottom: 1px solid var(--dp-border);
942
+ transition: background 0.15s ease;
943
+ }
944
+ .lexy-dp-log:hover {
945
+ background: rgba(0, 0, 0, 0.005);
946
+ }
862
947
  .lexy-dp-log__head {
863
948
  display: flex;
864
949
  width: 100%;
865
950
  align-items: center;
866
- gap: 6px;
867
- padding: 4px 8px;
951
+ gap: 8px;
952
+ padding: 10px 16px;
868
953
  text-align: left;
869
954
  background: transparent;
870
- border: none;
871
955
  cursor: pointer;
956
+ transition: background 0.15s ease;
957
+ }
958
+ .lexy-dp-log__head:hover { background: rgba(0, 0, 0, 0.03); }
959
+ .lexy-dp-log__time { margin-left: auto; flex-shrink: 0; color: var(--dp-muted-fg); font-size: 11px; }
960
+ .lexy-dp-log__body {
961
+ padding: 8px 16px 12px 16px;
962
+ background: #f8fafc;
963
+ border-top: 1px solid rgba(0, 0, 0, 0.03);
872
964
  }
873
- .lexy-dp-log__head:hover { background: var(--dp-muted); }
874
- .lexy-dp-log__time { margin-left: auto; flex-shrink: 0; color: var(--dp-muted-fg); }
875
- .lexy-dp-log__body { padding-bottom: 6px; }
876
-
877
- /* \u2500\u2500 Detalle (event/entity detail) \u2500\u2500 */
878
- .lexy-dp-eventdetail { display: flex; flex-direction: column; font-size: 12px; line-height: 1.5; }
879
- .lexy-dp-detail-body { padding: 12px 14px; display: flex; flex-direction: column; gap: 6px; }
880
- .lexy-dp-detail-field { display: flex; gap: 4px; font-family: var(--dp-mono); font-size: 12px; }
881
- .lexy-dp-detail-label { color: var(--dp-muted-fg); flex-shrink: 0; }
882
- .lexy-dp-detail-label::after { content: ":"; }
883
-
884
- /* \u2500\u2500 Triggers list \u2500\u2500 */
885
- .lexy-dp-trigger-list { list-style: none; padding: 0; margin: 0; display: flex; flex-direction: column; gap: 4px; }
886
- .lexy-dp-trigger-item { display: flex; gap: 8px; align-items: baseline; }
887
- .lexy-dp-bullet { color: var(--dp-primary); font-weight: 700; flex-shrink: 0; }
888
-
889
965
 
890
- /* \u2500\u2500 Split (lista + detalle) \u2500\u2500 */
966
+ /* \u2500\u2500 Split (Master-Detail) \u2500\u2500 */
891
967
  .lexy-dp-split { display: flex; height: 100%; }
892
968
  .lexy-dp-split__list {
893
969
  width: 288px;
894
970
  flex-shrink: 0;
895
971
  overflow-y: auto;
896
972
  border-right: 1px solid var(--dp-border);
897
- padding: 8px 0;
973
+ padding: 12px 0;
898
974
  display: flex;
899
975
  flex-direction: column;
900
- gap: 1px;
976
+ background: #f8fafc; /* sidebar light gray background */
901
977
  }
902
978
  .lexy-dp-list-section {
903
979
  display: flex;
904
980
  align-items: center;
905
981
  justify-content: space-between;
906
982
  width: 100%;
907
- padding: 5px 10px;
908
- font-size: 12px;
909
- font-weight: 500;
910
- color: var(--dp-fg);
911
- background: var(--dp-muted);
983
+ padding: 10px 16px;
984
+ font-size: 11px;
985
+ font-weight: 700;
986
+ letter-spacing: 0.05em;
987
+ color: #475569;
988
+ text-transform: uppercase;
989
+ background: transparent;
912
990
  border: none;
913
- border-top: 1px solid var(--dp-border);
914
- border-bottom: 1px solid var(--dp-border);
915
991
  cursor: pointer;
916
992
  font-family: inherit;
917
993
  text-align: left;
994
+ margin-top: 8px;
918
995
  }
919
- .lexy-dp-list-section:hover { background: var(--dp-border); }
996
+ .lexy-dp-list-section:first-of-type { margin-top: 0; }
920
997
  .lexy-dp-listitem {
921
- width: 100%;
998
+ width: calc(100% - 16px);
999
+ margin: 2px 8px;
922
1000
  text-align: left;
923
1001
  border: none;
924
1002
  background: transparent;
925
- border-radius: 0;
926
- padding: 5px 12px;
1003
+ padding: 7px 12px;
927
1004
  font-family: var(--dp-mono);
928
1005
  font-size: 12px;
929
- color: var(--dp-fg);
1006
+ color: #334155;
930
1007
  cursor: pointer;
931
1008
  white-space: nowrap;
932
1009
  overflow: hidden;
933
1010
  text-overflow: ellipsis;
1011
+ border-radius: 6px;
1012
+ transition: all 0.15s ease;
1013
+ }
1014
+ .lexy-dp-listitem:hover { background: rgba(0, 0, 0, 0.03); color: var(--dp-fg); }
1015
+ .lexy-dp-listitem.is-active {
1016
+ background: rgba(79, 70, 229, 0.08);
1017
+ color: var(--dp-primary);
1018
+ font-weight: 600;
1019
+ }
1020
+ .lexy-dp-split__detail {
1021
+ flex: 1;
1022
+ min-width: 0;
1023
+ min-height: 0;
1024
+ overflow-y: auto;
1025
+ padding: 0;
1026
+ background: #ffffff; /* details pure white background */
934
1027
  }
935
- .lexy-dp-listitem:hover { background: var(--dp-muted); }
936
- .lexy-dp-listitem.is-active { background: var(--dp-accent); color: var(--dp-accent-fg); font-weight: 500; }
937
- .lexy-dp-split__detail { flex: 1; min-width: 0; min-height: 0; overflow-y: auto; padding: 0; }
938
1028
 
939
- /* \u2500\u2500 Tabla de campos (devtools) \u2500\u2500 */
940
- .lexy-dp-field-table { width: 100%; border-collapse: collapse; font-family: var(--dp-mono); font-size: 11px; table-layout: fixed; }
941
- .lexy-dp-field-table th { text-align: left; font-weight: 500; color: var(--dp-fg); padding: 3px 8px; background: var(--dp-muted); border-bottom: 1px solid var(--dp-border); border-right: 1px solid var(--dp-border); white-space: nowrap; overflow: hidden; text-overflow: ellipsis; }
1029
+ /* \u2500\u2500 Detalle (Event / Load / Entity Detail Layout) \u2500\u2500 */
1030
+ .lexy-dp-eventdetail { display: flex; flex-direction: column; font-size: 13.5px; line-height: 1.6; }
1031
+
1032
+ /* The first detail body acts as the HERO banner of the selected item */
1033
+ .lexy-dp-eventdetail .lexy-dp-detail-body:first-of-type {
1034
+ background: #f8fafc;
1035
+ border-bottom: 1px solid var(--dp-border);
1036
+ padding: 24px;
1037
+ display: flex;
1038
+ flex-direction: column;
1039
+ gap: 16px;
1040
+ margin-bottom: 12px;
1041
+ }
1042
+ /* Reorganize field rows inside the HERO banner */
1043
+ .lexy-dp-eventdetail .lexy-dp-detail-body:first-of-type .lexy-dp-detail-field {
1044
+ display: flex;
1045
+ flex-direction: column;
1046
+ align-items: flex-start;
1047
+ gap: 4px;
1048
+ }
1049
+ /* Hide default "Nombre" label since it's redundant */
1050
+ .lexy-dp-eventdetail .lexy-dp-detail-body:first-of-type .lexy-dp-detail-field:first-of-type .lexy-dp-detail-label {
1051
+ display: none;
1052
+ }
1053
+ /* Title of the hero banner (technical ID) */
1054
+ .lexy-dp-eventdetail .lexy-dp-detail-body:first-of-type .lexy-dp-detail-field:first-of-type span:not(.lexy-dp-detail-label) {
1055
+ font-size: 20px;
1056
+ font-weight: 700;
1057
+ color: #0f172a;
1058
+ font-family: var(--dp-sans);
1059
+ }
1060
+ /* Styling other hero banner labels as small headers */
1061
+ .lexy-dp-eventdetail .lexy-dp-detail-body:first-of-type .lexy-dp-detail-field:not(:first-of-type) .lexy-dp-detail-label {
1062
+ font-size: 11px;
1063
+ font-weight: 600;
1064
+ text-transform: uppercase;
1065
+ letter-spacing: 0.05em;
1066
+ color: #64748b;
1067
+ }
1068
+ .lexy-dp-eventdetail .lexy-dp-detail-body:first-of-type .lexy-dp-detail-field:not(:first-of-type) .lexy-dp-detail-label::after {
1069
+ content: "";
1070
+ }
1071
+ /* Text description in the hero banner */
1072
+ .lexy-dp-eventdetail .lexy-dp-detail-body:first-of-type .lexy-dp-detail-field:not(:first-of-type) span:not(.lexy-dp-detail-label) {
1073
+ font-size: 13.5px;
1074
+ color: #475569;
1075
+ font-family: var(--dp-sans);
1076
+ line-height: 1.6;
1077
+ }
1078
+
1079
+ /* Detail sub-bodies (e.g. content underneath sections) */
1080
+ .lexy-dp-eventdetail .lexy-dp-detail-body:not(:first-of-type) {
1081
+ padding: 12px 24px 24px 24px;
1082
+ display: flex;
1083
+ flex-direction: column;
1084
+ gap: 8px;
1085
+ }
1086
+ .lexy-dp-detail-field { display: flex; gap: 8px; font-family: var(--dp-mono); font-size: 12.5px; }
1087
+ .lexy-dp-detail-label { color: var(--dp-muted-fg); flex-shrink: 0; }
1088
+ .lexy-dp-detail-label::after { content: ":"; }
1089
+
1090
+ /* Section Header Buttons inside Detail Page */
1091
+ .lexy-dp-eventdetail > .lexy-dp-list-section {
1092
+ display: flex;
1093
+ align-items: center;
1094
+ justify-content: space-between;
1095
+ width: 100%;
1096
+ padding: 12px 24px;
1097
+ font-size: 13px;
1098
+ font-weight: 600;
1099
+ color: #0f172a;
1100
+ background: #ffffff;
1101
+ border-top: 1px solid var(--dp-border);
1102
+ border-bottom: none;
1103
+ cursor: pointer;
1104
+ font-family: inherit;
1105
+ text-align: left;
1106
+ margin-top: 8px;
1107
+ text-transform: none;
1108
+ letter-spacing: normal;
1109
+ }
1110
+ .lexy-dp-eventdetail > .lexy-dp-list-section:hover { background: #f8fafc; }
1111
+
1112
+ /* \u2500\u2500 Triggers List \u2500\u2500 */
1113
+ .lexy-dp-trigger-list { list-style: none; padding: 0; margin: 0; display: flex; flex-direction: column; gap: 6px; }
1114
+ .lexy-dp-trigger-item { display: flex; gap: 8px; align-items: baseline; }
1115
+ .lexy-dp-bullet { color: var(--dp-primary); font-weight: 700; flex-shrink: 0; }
1116
+
1117
+ /* \u2500\u2500 Fields Table (DevTools) \u2500\u2500 */
1118
+ .lexy-dp-field-table {
1119
+ width: 100%;
1120
+ border-collapse: collapse;
1121
+ font-family: var(--dp-mono);
1122
+ font-size: 12px;
1123
+ table-layout: fixed;
1124
+ }
1125
+ .lexy-dp-field-table th {
1126
+ text-align: left;
1127
+ font-weight: 600;
1128
+ color: #475569;
1129
+ padding: 8px 12px;
1130
+ background: #f8fafc;
1131
+ border-bottom: 1px solid var(--dp-border);
1132
+ border-right: 1px solid var(--dp-border);
1133
+ white-space: nowrap;
1134
+ overflow: hidden;
1135
+ text-overflow: ellipsis;
1136
+ font-size: 11px;
1137
+ text-transform: uppercase;
1138
+ letter-spacing: 0.05em;
1139
+ }
942
1140
  .lexy-dp-field-table th:last-child { border-right: none; }
943
- .lexy-dp-field-table td { padding: 2px 8px; border-bottom: 1px solid var(--dp-border); border-right: 1px solid var(--dp-border); white-space: nowrap; overflow: hidden; text-overflow: ellipsis; vertical-align: top; }
1141
+ .lexy-dp-field-table td {
1142
+ padding: 6px 12px;
1143
+ border-bottom: 1px solid var(--dp-border);
1144
+ border-right: 1px solid var(--dp-border);
1145
+ white-space: nowrap;
1146
+ overflow: hidden;
1147
+ text-overflow: ellipsis;
1148
+ vertical-align: middle;
1149
+ color: #334155;
1150
+ }
944
1151
  .lexy-dp-field-table td:last-child { border-right: none; }
945
- .lexy-dp-field-table tbody tr { cursor: pointer; }
946
- .lexy-dp-field-table tbody tr:hover { background: var(--dp-muted); }
947
- .lexy-dp-field-table tbody tr.is-selected { background: var(--dp-accent); color: var(--dp-accent-fg); }
948
- .lexy-dp-field-table tbody tr.is-selected td { color: var(--dp-accent-fg); }
1152
+ .lexy-dp-field-table tbody tr { cursor: pointer; transition: background 0.15s ease; }
1153
+ .lexy-dp-field-table tbody tr:hover { background: rgba(0, 0, 0, 0.015); }
1154
+ .lexy-dp-field-table tbody tr.is-selected { background: rgba(79, 70, 229, 0.04); }
1155
+ .lexy-dp-field-table tbody tr.is-selected td { color: var(--dp-primary); font-weight: 600; }
949
1156
  .lexy-dp-field-table tbody tr:last-child td { border-bottom: none; }
950
1157
 
951
- /* \u2500\u2500 Launcher flotante \u2500\u2500 */
1158
+ /* Wrapper to round table corners */
1159
+ .lexy-dp-eventdetail .lexy-dp-detail-body > div[style*="overflowX"] {
1160
+ border: 1px solid var(--dp-border);
1161
+ border-radius: 8px;
1162
+ overflow: hidden;
1163
+ }
1164
+
1165
+ /* \u2500\u2500 Floating Launcher \u2500\u2500 */
952
1166
  .lexy-dp-launcher {
953
1167
  position: fixed;
954
- bottom: 16px;
955
- right: 16px;
956
- z-index: 40;
1168
+ bottom: 20px;
1169
+ right: 20px;
1170
+ z-index: 50;
957
1171
  display: flex;
958
1172
  align-items: center;
959
1173
  justify-content: center;
@@ -961,86 +1175,112 @@ export const designerActivity = createDesignerActivityStore();
961
1175
  width: 48px;
962
1176
  gap: 0;
963
1177
  overflow: hidden;
964
- border: none;
1178
+ border: none !important;
965
1179
  border-radius: 9999px;
966
- background: var(--dp-fg);
967
- color: var(--dp-primary-fg);
968
- box-shadow: 0 4px 12px rgba(0, 0, 0, 0.18);
1180
+ background: #0f172a !important;
1181
+ color: #ffffff !important;
1182
+ box-shadow: 0 4px 14px rgba(0, 0, 0, 0.15) !important;
969
1183
  cursor: pointer;
970
- padding: 0 12px;
1184
+ padding: 0 14px;
1185
+ transition: all 0.3s cubic-bezier(0.16, 1, 0.3, 1);
971
1186
  }
972
- .lexy-dp-launcher:hover,
973
- .lexy-dp-launcher:focus-visible,
974
- .lexy-dp-launcher.is-open { width: 176px; gap: 8px; }
975
- .lexy-dp-launcher:focus-visible { outline: 2px solid var(--dp-ring); outline-offset: 2px; }
1187
+ .lexy-dp-launcher:hover {
1188
+ width: 176px;
1189
+ gap: 8px;
1190
+ background: #1e293b !important;
1191
+ transform: translateY(-2px);
1192
+ box-shadow: 0 6px 20px rgba(0, 0, 0, 0.2) !important;
1193
+ }
1194
+ .lexy-dp-launcher.is-open {
1195
+ width: 176px;
1196
+ gap: 8px;
1197
+ background: #0f172a !important;
1198
+ box-shadow: 0 6px 20px rgba(0, 0, 0, 0.2) !important;
1199
+ }
1200
+ .lexy-dp-launcher.is-open:hover {
1201
+ background: #1e293b !important;
1202
+ }
1203
+ .lexy-dp-launcher:focus-visible { outline: 2px solid var(--dp-primary); outline-offset: 2px; }
976
1204
  .lexy-dp-launcher__icon { width: 20px; height: 20px; flex-shrink: 0; }
977
1205
  .lexy-dp-launcher__label {
978
1206
  overflow: hidden;
979
1207
  white-space: nowrap;
980
1208
  font-size: 13px;
981
- font-weight: 500;
1209
+ font-weight: 600;
982
1210
  max-width: 0;
983
1211
  opacity: 0;
1212
+ transition: max-width 0.3s ease, opacity 0.2s ease;
984
1213
  }
985
1214
  .lexy-dp-launcher:hover .lexy-dp-launcher__label,
986
1215
  .lexy-dp-launcher:focus-visible .lexy-dp-launcher__label,
987
- .lexy-dp-launcher.is-open .lexy-dp-launcher__label { max-width: 160px; opacity: 1; }
1216
+ .lexy-dp-launcher.is-open .lexy-dp-launcher__label { max-width: 130px; opacity: 1; }
988
1217
 
989
- /* \u2500\u2500 Sheet flotante \u2500\u2500 */
1218
+ /* \u2500\u2500 Floating Sheet \u2500\u2500 */
990
1219
  .lexy-dp-sheet {
991
1220
  position: fixed;
992
- bottom: 80px;
993
- right: 16px;
994
- z-index: 40;
1221
+ bottom: 84px;
1222
+ right: 20px;
1223
+ z-index: 50;
995
1224
  display: flex;
996
1225
  flex-direction: column;
997
- height: 70vh;
998
- width: min(100vw - 2rem, 400px);
1226
+ height: 75vh;
1227
+ width: min(100vw - 2.5rem, 460px);
999
1228
  overflow: hidden;
1000
1229
  border: 1px solid var(--dp-border);
1001
1230
  border-radius: 12px;
1002
1231
  background: var(--dp-popover);
1003
1232
  color: var(--dp-fg);
1004
- box-shadow: 0 20px 40px rgba(0, 0, 0, 0.25);
1233
+ box-shadow: 0 12px 30px rgba(0, 0, 0, 0.1), 0 4px 10px rgba(0, 0, 0, 0.05);
1234
+ animation: lexy-sheet-slide 0.3s cubic-bezier(0.16, 1, 0.3, 1) forwards;
1235
+ }
1236
+
1237
+ @keyframes lexy-sheet-slide {
1238
+ from { opacity: 0; transform: translateY(12px) scale(0.98); }
1239
+ to { opacity: 1; transform: translateY(0) scale(1); }
1005
1240
  }
1241
+
1006
1242
  .lexy-dp-sheet__header {
1007
1243
  display: flex;
1008
1244
  align-items: center;
1009
1245
  justify-content: space-between;
1010
1246
  gap: 12px;
1011
- border-bottom: 1px solid var(--dp-border);
1012
- background: var(--dp-fg);
1013
- padding: 12px 16px;
1014
- color: var(--dp-primary-fg);
1247
+ border-bottom: 1px solid rgba(255, 255, 255, 0.1);
1248
+ background: #0f172a;
1249
+ padding: 14px 18px;
1250
+ color: #ffffff;
1015
1251
  }
1016
- .lexy-dp-sheet__title { font-size: 14px; font-weight: 500; }
1017
- .lexy-dp-sheet__actions { display: flex; align-items: center; gap: 4px; }
1252
+ .lexy-dp-sheet__title { font-size: 14.5px; font-weight: 700; letter-spacing: -0.01em; }
1253
+ .lexy-dp-sheet__actions { display: flex; align-items: center; gap: 6px; }
1018
1254
  .lexy-dp-iconbtn {
1019
1255
  display: flex;
1020
- height: 28px;
1021
- width: 28px;
1256
+ height: 30px;
1257
+ width: 30px;
1022
1258
  align-items: center;
1023
1259
  justify-content: center;
1024
1260
  border: none;
1025
1261
  background: transparent;
1026
1262
  border-radius: 6px;
1027
- opacity: 0.7;
1263
+ opacity: 0.6;
1264
+ color: #ffffff;
1028
1265
  cursor: pointer;
1266
+ transition: all 0.15s ease;
1029
1267
  }
1030
- .lexy-dp-iconbtn:hover { opacity: 1; }
1031
- .lexy-dp-iconbtn svg { width: 16px; height: 16px; }
1268
+ .lexy-dp-iconbtn:hover { opacity: 1; background: rgba(255, 255, 255, 0.1); color: #ffffff; }
1269
+ .lexy-dp-iconbtn svg { width: 15px; height: 15px; }
1032
1270
  .lexy-dp-sheet__body { flex: 1; min-height: 0; overflow-y: auto; background: var(--dp-bg); }
1033
1271
  `,jt=()=>String.raw`import {
1034
1272
  Activity,
1035
1273
  ArrowUpRight,
1036
1274
  ChevronRight,
1275
+ Eye,
1276
+ EyeOff,
1037
1277
  Maximize2,
1038
1278
  Settings,
1039
1279
  Trash2,
1040
1280
  X,
1041
1281
  Zap,
1042
1282
  } from "lucide-react";
1043
- import { useState, useSyncExternalStore } from "react";
1283
+ import { useState, useEffect, useSyncExternalStore } from "react";
1044
1284
 
1045
1285
  import { prototypeDataContract } from "../data-contract/prototype-data-contract";
1046
1286
  import {
@@ -1080,11 +1320,11 @@ const TREE_INDENT = 14;
1080
1320
  const TREE_BASE = 8;
1081
1321
 
1082
1322
  const renderPrimitive = (value: unknown) => {
1083
- if (typeof value === "string") return <span className="lexy-dp-json-str">"{value}"</span>;
1084
- if (typeof value === "number") return <span className="lexy-dp-json-num">{value}</span>;
1085
- if (typeof value === "boolean") return <span className="lexy-dp-json-num">{String(value)}</span>;
1323
+ if (typeof value === "string") return <span className="lexy-dp-json-row-str">"{value}"</span>;
1324
+ if (typeof value === "number") return <span className="lexy-dp-json-row-num">{value}</span>;
1325
+ if (typeof value === "boolean") return <span className="lexy-dp-json-row-num">{String(value)}</span>;
1086
1326
  if (value === null) return <span className="lexy-dp-muted">null</span>;
1087
- return <span className="lexy-dp-json-str">{String(value)}</span>;
1327
+ return <span className="lexy-dp-json-row-str">{String(value)}</span>;
1088
1328
  };
1089
1329
 
1090
1330
  function JsonNode({
@@ -1163,7 +1403,7 @@ function LogEntry({ item }: { item: DesignerActivityRecord }) {
1163
1403
  <span className="lexy-dp-json-spacer" aria-hidden />
1164
1404
  <span className="lexy-dp-json-leaf">
1165
1405
  <span className="lexy-dp-muted">fuente:</span>{" "}
1166
- <span className="lexy-dp-json-str">{trigger}</span>
1406
+ <span className="lexy-dp-json-row-str">{trigger}</span>
1167
1407
  </span>
1168
1408
  </div>
1169
1409
  {input !== undefined ? <JsonNode label={inputLabel} value={input} defaultOpen /> : null}
@@ -1357,8 +1597,8 @@ function EventDetail({ event }: { event: CatalogEvent }) {
1357
1597
  const observedTriggers = Array.from(
1358
1598
  new Set(
1359
1599
  activity
1360
- .filter((record) => record.technicalId === event.technicalId && record.triggerId)
1361
- .map((record) => record.triggerId as string),
1600
+ .filter((record) => record.technicalId === event.technicalId && record.triggerId)
1601
+ .map((record) => record.triggerId as string),
1362
1602
  ),
1363
1603
  );
1364
1604
  const payload = event.lastPayload;
@@ -1758,6 +1998,22 @@ type DesignerTab = "activity" | "events";
1758
1998
 
1759
1999
  export function DesignerPanelPage() {
1760
2000
  const [tab, setTab] = useState<DesignerTab>("activity");
2001
+ const [launcherVisible, setLauncherVisible] = useState(() => {
2002
+ if (typeof window !== "undefined") {
2003
+ return localStorage.getItem("lexy-dp-launcher-visible") !== "false";
2004
+ }
2005
+ return true;
2006
+ });
2007
+
2008
+ useEffect(() => {
2009
+ const handleStorage = (e: StorageEvent) => {
2010
+ if (e.key === "lexy-dp-launcher-visible") {
2011
+ setLauncherVisible(e.newValue !== "false");
2012
+ }
2013
+ };
2014
+ window.addEventListener("storage", handleStorage);
2015
+ return () => window.removeEventListener("storage", handleStorage);
2016
+ }, []);
1761
2017
 
1762
2018
  return (
1763
2019
  <div className="lexy-dp lexy-dp-page">
@@ -1783,6 +2039,24 @@ export function DesignerPanelPage() {
1783
2039
  <Zap />
1784
2040
  Eventos y Datos
1785
2041
  </button>
2042
+
2043
+ <div style={{ marginLeft: "auto", display: "flex", alignItems: "center", gap: "8px" }}>
2044
+ <span className="lexy-dp-muted" style={{ fontSize: "12px" }}>Burbuja de Asistencia:</span>
2045
+ <button
2046
+ type="button"
2047
+ className="lexy-dp-btn lexy-dp-btn--outline lexy-dp-btn--sm"
2048
+ style={{ display: "inline-flex", alignItems: "center", gap: "6px", cursor: "pointer" }}
2049
+ onClick={() => {
2050
+ const nextState = !launcherVisible;
2051
+ setLauncherVisible(nextState);
2052
+ localStorage.setItem("lexy-dp-launcher-visible", String(nextState));
2053
+ window.dispatchEvent(new Event("storage"));
2054
+ }}
2055
+ >
2056
+ {launcherVisible ? <EyeOff style={{ width: "12px", height: "12px" }} /> : <Eye style={{ width: "12px", height: "12px" }} />}
2057
+ {launcherVisible ? "Ocultar" : "Mostrar"}
2058
+ </button>
2059
+ </div>
1786
2060
  </div>
1787
2061
  <div className="lexy-dp-body">
1788
2062
  {tab === "activity" ? (
@@ -1802,6 +2076,25 @@ export function DesignerPanelPage() {
1802
2076
 
1803
2077
  export function PrototypeDesignerPanel() {
1804
2078
  const [open, setOpen] = useState(false);
2079
+ const [visible, setVisible] = useState(() => {
2080
+ if (typeof window !== "undefined") {
2081
+ return localStorage.getItem("lexy-dp-launcher-visible") !== "false";
2082
+ }
2083
+ return true;
2084
+ });
2085
+
2086
+ useEffect(() => {
2087
+ const handleStorage = (e: StorageEvent) => {
2088
+ if (e.key === "lexy-dp-launcher-visible") {
2089
+ setVisible(e.newValue !== "false");
2090
+ }
2091
+ };
2092
+ window.addEventListener("storage", handleStorage);
2093
+ return () => window.removeEventListener("storage", handleStorage);
2094
+ }, []);
2095
+
2096
+ if (!visible) return null;
2097
+
1805
2098
  return (
1806
2099
  <div className="lexy-dp">
1807
2100
  <PanelStyles />
@@ -1810,6 +2103,21 @@ export function PrototypeDesignerPanel() {
1810
2103
  <div className="lexy-dp-sheet__header">
1811
2104
  <p className="lexy-dp-sheet__title">Panel de Actividad</p>
1812
2105
  <div className="lexy-dp-sheet__actions">
2106
+ <button
2107
+ type="button"
2108
+ aria-label="Ocultar burbuja de asistencia"
2109
+ title="Ocultar burbuja de asistencia"
2110
+ className="lexy-dp-iconbtn"
2111
+ onClick={() => {
2112
+ if (confirm("¿Estás seguro de que quieres ocultar la burbuja de asistencia? Podrás volver a habilitarla desde la página del panel (/designer-panel).")) {
2113
+ localStorage.setItem("lexy-dp-launcher-visible", "false");
2114
+ setVisible(false);
2115
+ window.dispatchEvent(new Event("storage"));
2116
+ }
2117
+ }}
2118
+ >
2119
+ <EyeOff />
2120
+ </button>
1813
2121
  <button
1814
2122
  type="button"
1815
2123
  aria-label="Abrir panel completo"
@@ -1848,7 +2156,7 @@ export function PrototypeDesignerPanel() {
1848
2156
  </div>
1849
2157
  );
1850
2158
  }
1851
- `,$e=async(e,t)=>{let o=async(a,n)=>{await Me.mkdir(ie.dirname(ie.join(e,a)),{recursive:!0}),await Me.writeFile(ie.join(e,a),n)};await o(se,Et),await o(le,jt())};import Fe from"fs/promises";import qe from"path";var ce="src/prototype/mock-store/mock-store.ts",de="src/prototype/mock-store/fixtures.ts",Ct="src/prototype/ports/types.ts",It="src/prototype/ports/catalog.ts",Tt="src/prototype/ports/mock-read.ts",Rt="src/prototype/ports/mock-write.ts",Nt="src/prototype/ports/production.ts",pe="src/prototype/ports/index.ts",Ot=String.raw`import { fixtures } from "./fixtures";
2159
+ `,$e=async(e,t)=>{let o=async(a,n)=>{await Me.mkdir(ie.dirname(ie.join(e,a)),{recursive:!0}),await Me.writeFile(ie.join(e,a),n)};await o(se,Et),await o(le,jt())};import Fe from"fs/promises";import qe from"path";var ce="src/prototype/mock-store/mock-store.ts",de="src/prototype/mock-store/fixtures.ts",It="src/prototype/ports/types.ts",Ct="src/prototype/ports/catalog.ts",Tt="src/prototype/ports/mock-read.ts",Rt="src/prototype/ports/mock-write.ts",Nt="src/prototype/ports/production.ts",pe="src/prototype/ports/index.ts",_t=String.raw`import { fixtures } from "./fixtures";
1852
2160
 
1853
2161
  export type JsonPrimitive = string | number | boolean | null;
1854
2162
  export type JsonValue = JsonPrimitive | JsonValue[] | { [key: string]: JsonValue };
@@ -2008,7 +2316,7 @@ export const findRecordById = (
2008
2316
  fieldId: string,
2009
2317
  id: JsonPrimitive,
2010
2318
  ) => records.find((record) => record[fieldId] === id);
2011
- `,_t=String.raw`import type { MockEntityRecord } from "./mock-store";
2319
+ `,Ot=String.raw`import type { MockEntityRecord } from "./mock-store";
2012
2320
 
2013
2321
  export type Fixtures = {
2014
2322
  datasetVersion: number;
@@ -2304,7 +2612,7 @@ export type {
2304
2612
  ReadMeta,
2305
2613
  WriteMeta,
2306
2614
  } from "./types";
2307
- `,Ft=[[ce,Ot],[de,_t],[Ct,At],[It,Lt],[Tt,Dt],[Rt,zt],[Nt,Mt],[pe,$t]],Ve=async e=>{for(let[t,o]of Ft){let a=qe.join(e,t);await Fe.mkdir(qe.dirname(a),{recursive:!0}),await Fe.writeFile(a,o)}};var Kt={feature:["src/app","src/features","src/shared/assets","src/shared/components/base","src/shared/hooks","src/shared/services","src/shared/lib","src/shared/types"],layer:["src/assets","src/components/base","src/hooks","src/services","src/lib","src/types","src/views","src/stores"]},Ut="10.33.3",Ht=e=>{let t=e.architecture==="feature"?{"react-router":"^7.9.0"}:{};return JSON.stringify({name:e.projectName,private:!0,version:"0.0.0",type:"module",packageManager:`pnpm@${Ut}`,scripts:{dev:"vite","check:data-contract":"tsx scripts/check-data-contract.ts","check:prototype":"pnpm check:data-contract","build:app":"tsc -b && vite build",build:"pnpm check:prototype && pnpm build:app",preview:"vite preview",lint:"eslint .",format:"prettier --write ."},dependencies:{clsx:"^2.1.1","lucide-react":"^0.460.0",react:"^19.2.6","react-dom":"^19.2.6",...t,"tailwind-merge":"^3.3.1",zod:"^4.1.0"},devDependencies:{"@babel/core":"^7.29.7","@eslint/js":"^10.0.1","@rolldown/plugin-babel":"^0.2.3","@tailwindcss/vite":"^4.3.0","@types/babel__core":"^7.20.5","@types/node":"^24.12.3","@types/react":"^19.2.14","@types/react-dom":"^19.2.3","@vitejs/plugin-react":"^6.0.1","babel-plugin-react-compiler":"^1.0.0",eslint:"^10.4.1","eslint-plugin-jsx-a11y":"^6.10.2","eslint-plugin-react-hooks":"^7.1.1","eslint-plugin-simple-import-sort":"^13.0.0",globals:"^17.6.0",prettier:"^3.8.4",tailwindcss:"^4.3.0",terser:"^5.48.0",tsx:"^4.19.0",typescript:"~5.9.3","typescript-eslint":"^8.61.0",vite:"^8.0.12"}},null,2)+`
2615
+ `,Ft=[[ce,_t],[de,Ot],[It,At],[Ct,Lt],[Tt,Dt],[Rt,zt],[Nt,Mt],[pe,$t]],Ve=async e=>{for(let[t,o]of Ft){let a=qe.join(e,t);await Fe.mkdir(qe.dirname(a),{recursive:!0}),await Fe.writeFile(a,o)}};var Kt={feature:["src/app","src/features","src/shared/assets","src/shared/components/base","src/shared/hooks","src/shared/services","src/shared/lib","src/shared/types"],layer:["src/assets","src/components/base","src/hooks","src/services","src/lib","src/types","src/views","src/stores"]},Ut="10.33.3",Ht=e=>{let t=e.architecture==="feature"?{"react-router":"^7.9.0"}:{};return JSON.stringify({name:e.projectName,private:!0,version:"0.0.0",type:"module",packageManager:`pnpm@${Ut}`,scripts:{dev:"vite","check:data-contract":"tsx scripts/check-data-contract.ts","check:prototype":"pnpm check:data-contract","build:app":"tsc -b && vite build",build:"pnpm check:prototype && pnpm build:app",preview:"vite preview",lint:"eslint .",format:"prettier --write ."},dependencies:{clsx:"^2.1.1","lucide-react":"^0.460.0",react:"^19.2.6","react-dom":"^19.2.6",...t,"tailwind-merge":"^3.3.1",zod:"^4.1.0"},devDependencies:{"@babel/core":"^7.29.7","@eslint/js":"^10.0.1","@rolldown/plugin-babel":"^0.2.3","@tailwindcss/vite":"^4.3.0","@types/babel__core":"^7.20.5","@types/node":"^24.12.3","@types/react":"^19.2.14","@types/react-dom":"^19.2.3","@vitejs/plugin-react":"^6.0.1","babel-plugin-react-compiler":"^1.0.0",eslint:"^10.4.1","eslint-plugin-jsx-a11y":"^6.10.2","eslint-plugin-react-hooks":"^7.1.1","eslint-plugin-simple-import-sort":"^13.0.0",globals:"^17.6.0",prettier:"^3.8.4",tailwindcss:"^4.3.0",terser:"^5.48.0",tsx:"^4.19.0",typescript:"~5.9.3","typescript-eslint":"^8.61.0",vite:"^8.0.12"}},null,2)+`
2308
2616
  `},Bt=`import path from "node:path";
2309
2617
 
2310
2618
  import babel from "@rolldown/plugin-babel";
@@ -2392,7 +2700,7 @@ export default tseslint.config(
2392
2700
  src/lexy-theme.css
2393
2701
  public/fonts/
2394
2702
  dist/
2395
- `,Qt=`name: CI
2703
+ `,Yt=`name: CI
2396
2704
 
2397
2705
  on:
2398
2706
  push:
@@ -2415,7 +2723,7 @@ jobs:
2415
2723
  - run: pnpm check:data-contract
2416
2724
  - run: pnpm build:app
2417
2725
  - run: pnpm audit --audit-level high
2418
- `,Yt=`{
2726
+ `,Qt=`{
2419
2727
  "files": [],
2420
2728
  "references": [{ "path": "./tsconfig.app.json" }, { "path": "./tsconfig.node.json" }],
2421
2729
  "compilerOptions": {
@@ -2568,26 +2876,26 @@ npx create-lexy add button # instalarlo (local y editable)
2568
2876
  npx create-lexy doctor # divergencia con el registry
2569
2877
  \`\`\`
2570
2878
  `,so=e=>{let o=e.architecture==="feature"?"@/shared":"@";return JSON.stringify({$schema:"https://ui.shadcn.com/schema.json",style:"new-york",rsc:!1,tsx:!0,tailwind:{config:"",css:"src/index.css",baseColor:"neutral",cssVariables:!0},aliases:{components:`${o}/components`,ui:`${o}/components/base`,utils:`${o}/lib/utils/cn`,lib:`${o}/lib`,hooks:`${o}/hooks`},registries:{"@lexy":`${F}@latest/r/{name}.json`}},null,2)+`
2571
- `},lo=e=>{let t=e.architecture==="feature";return{version:"2.0.0",generatedAt:new Date().toISOString(),architecture:e.architecture,world:e.world,registry:{package:"@lexydesign/registry",cdn:F},componentImportPattern:t?"@/shared/components/base/{Component}":"@/components/base/{Component}",paths:{components:t?"src/shared/components/base":"src/components/base",hooks:t?"src/shared/hooks":"src/hooks",services:t?"src/shared/services":"src/services",lib:t?"src/shared/lib":"src/lib",views:t?"src/features":"src/views"},prototype:{dataContractVersion:"1",dataContractPath:re,runtimeVersion:"1",mockStorePath:ce,fixturesPath:de,portsPath:pe,designerPanelVersion:"1",designerPanelPath:le,designerActivityStorePath:se},installed:{}}},Ue=async(e,t)=>{let o=["package.json","src","index.html",".lexy"],a=[];for(let s of o)try{await b.access(w.join(t,s)),a.push(s)}catch{}if(a.length>0)throw new Error(`El directorio actual ya contiene archivos de un proyecto (${a.join(", ")}). Ejecuta el comando dentro de una carpeta vac\xEDa.`);for(let s of Kt[e.architecture])await b.mkdir(w.join(t,s),{recursive:!0});let n=(s,u)=>b.writeFile(w.join(t,s),u);await n("package.json",Ht(e)),await n("vite.config.ts",Bt),await n("tsconfig.json",Yt),await n("tsconfig.app.json",Xt),await n("tsconfig.node.json",Zt),await n("eslint.config.js",Jt),await n(".prettierrc",Wt),await n(".prettierignore",Gt),await b.mkdir(w.join(t,".github/workflows"),{recursive:!0}),await n(".github/workflows/ci.yml",Qt),await n("index.html",eo(e)),await n(".gitignore",ro),await n("README.md",io(e)),await n("src/index.css",to),await n("src/main.tsx",oo(e)),await ze(t,e.projectName),await Ve(t);let r=lo(e);await $e(t,r);let i=e.architecture==="feature"?"src/app":"src/views";await n(`${i}/App.tsx`,ao(e)),await n(".lexy",JSON.stringify(r,null,2)+`
2572
- `),await n("components.json",so(e)),await b.copyFile(Ce,w.join(t,"src/lexy-theme.css")),await b.mkdir(w.join(t,"public/fonts"),{recursive:!0}),await b.cp(Ie,w.join(t,"public/fonts"),{recursive:!0});let d=w.join(t,r.paths.lib,"utils");await b.mkdir(d,{recursive:!0}),await b.writeFile(w.join(d,"cn.ts"),no),await co(t)},co=async e=>{let t=[],o=async a=>{let n;try{n=await b.readdir(a,{withFileTypes:!0})}catch{return}for(let r of n){let i=w.join(a,r.name);r.isDirectory()?await o(i):/\.(ts|tsx)$/.test(r.name)&&t.push(i)}};await o(w.join(e,"src")),await o(w.join(e,"scripts"));for(let a of t){let n=await b.readFile(a,"utf-8"),r=await Vt(a)??{},i=await qt(n,{...r,filepath:a});i!==n&&await b.writeFile(a,i)}};var fo=["feature","layer"],go=["cliente","crm","mixto"],xo=e=>new Promise((t,o)=>{po("pnpm",["install"],{cwd:e,stdio:"ignore",shell:!0}).on("close",n=>n===0?t():o(new Error(`pnpm install fall\xF3 con c\xF3digo ${n}`)))}),He=async(e,t)=>{let o;!!(e&&t.type)?(fo.includes(t.type)||(console.error(j.red(`Error: la arquitectura "${t.type}" no es v\xE1lida. Usa "feature" o "layer".`)),process.exit(1)),t.world&&!go.includes(t.world)&&(console.error(j.red(`Error: el mundo "${t.world}" no es v\xE1lido. Usa "cliente", "crm" o "mixto".`)),process.exit(1)),t.world||console.warn(j.yellow('Aviso: sin --world; se asume "mixto". ')+j.dim("Pasa --world cliente|crm para fijar densidad y voz desde el inicio.")),o={projectName:e,architecture:t.type,world:t.world??"mixto"},console.log(j.blue("Modo automatizado detectado. Saltando interfaz interactiva..."))):o=await Ae(e),mo(`Nombre: ${o.projectName}
2879
+ `},lo=e=>{let t=e.architecture==="feature";return{version:"2.0.0",generatedAt:new Date().toISOString(),architecture:e.architecture,world:e.world,registry:{package:"@lexydesign/registry",cdn:F},componentImportPattern:t?"@/shared/components/base/{Component}":"@/components/base/{Component}",paths:{components:t?"src/shared/components/base":"src/components/base",hooks:t?"src/shared/hooks":"src/hooks",services:t?"src/shared/services":"src/services",lib:t?"src/shared/lib":"src/lib",views:t?"src/features":"src/views"},prototype:{dataContractVersion:"1",dataContractPath:re,runtimeVersion:"1",mockStorePath:ce,fixturesPath:de,portsPath:pe,designerPanelVersion:"1",designerPanelPath:le,designerActivityStorePath:se},installed:{}}},Ue=async(e,t)=>{let o=["package.json","src","index.html",".lexy"],a=[];for(let s of o)try{await b.access(w.join(t,s)),a.push(s)}catch{}if(a.length>0)throw new Error(`El directorio actual ya contiene archivos de un proyecto (${a.join(", ")}). Ejecuta el comando dentro de una carpeta vac\xEDa.`);for(let s of Kt[e.architecture])await b.mkdir(w.join(t,s),{recursive:!0});let n=(s,u)=>b.writeFile(w.join(t,s),u);await n("package.json",Ht(e)),await n("vite.config.ts",Bt),await n("tsconfig.json",Qt),await n("tsconfig.app.json",Xt),await n("tsconfig.node.json",Zt),await n("eslint.config.js",Jt),await n(".prettierrc",Wt),await n(".prettierignore",Gt),await b.mkdir(w.join(t,".github/workflows"),{recursive:!0}),await n(".github/workflows/ci.yml",Yt),await n("index.html",eo(e)),await n(".gitignore",ro),await n("README.md",io(e)),await n("src/index.css",to),await n("src/main.tsx",oo(e)),await ze(t,e.projectName),await Ve(t);let r=lo(e);await $e(t,r);let i=e.architecture==="feature"?"src/app":"src/views";await n(`${i}/App.tsx`,ao(e)),await n(".lexy",JSON.stringify(r,null,2)+`
2880
+ `),await n("components.json",so(e)),await b.copyFile(Ie,w.join(t,"src/lexy-theme.css")),await b.mkdir(w.join(t,"public/fonts"),{recursive:!0}),await b.cp(Ce,w.join(t,"public/fonts"),{recursive:!0});let d=w.join(t,r.paths.lib,"utils");await b.mkdir(d,{recursive:!0}),await b.writeFile(w.join(d,"cn.ts"),no),await co(t)},co=async e=>{let t=[],o=async a=>{let n;try{n=await b.readdir(a,{withFileTypes:!0})}catch{return}for(let r of n){let i=w.join(a,r.name);r.isDirectory()?await o(i):/\.(ts|tsx)$/.test(r.name)&&t.push(i)}};await o(w.join(e,"src")),await o(w.join(e,"scripts"));for(let a of t){let n=await b.readFile(a,"utf-8"),r=await Vt(a)??{},i=await qt(n,{...r,filepath:a});i!==n&&await b.writeFile(a,i)}};var fo=["feature","layer"],go=["cliente","crm","mixto"],xo=e=>new Promise((t,o)=>{po("pnpm",["install"],{cwd:e,stdio:"ignore",shell:!0}).on("close",n=>n===0?t():o(new Error(`pnpm install fall\xF3 con c\xF3digo ${n}`)))}),He=async(e,t)=>{let o;!!(e&&t.type)?(fo.includes(t.type)||(console.error(j.red(`Error: la arquitectura "${t.type}" no es v\xE1lida. Usa "feature" o "layer".`)),process.exit(1)),t.world&&!go.includes(t.world)&&(console.error(j.red(`Error: el mundo "${t.world}" no es v\xE1lido. Usa "cliente", "crm" o "mixto".`)),process.exit(1)),t.world||console.warn(j.yellow('Aviso: sin --world; se asume "mixto". ')+j.dim("Pasa --world cliente|crm para fijar densidad y voz desde el inicio.")),o={projectName:e,architecture:t.type,world:t.world??"mixto"},console.log(j.blue("Modo automatizado detectado. Saltando interfaz interactiva..."))):o=await Ae(e),mo(`Nombre: ${o.projectName}
2573
2881
  Arquitectura: ${o.architecture}
2574
2882
  Mundo: ${o.world}`,"Configuraci\xF3n de Proyecto");let n=yo();n.start("Construyendo tu proyecto...");let r=process.cwd();try{await Ue(o,r)}catch(i){throw n.stop(j.red("No se pudo crear el proyecto.")),i}t.install!==!1&&(n.message("Instalando dependencias base..."),await xo(r)),n.stop("\xA1Proyecto construido con \xE9xito!"),uo(j.green(`Todo listo en el directorio actual
2575
2883
 
2576
2884
  `)+j.dim(`Siguientes pasos:
2577
2885
  `)+j.cyan(` pnpm dev
2578
- `)+j.cyan(" npx create-lexy add button"))};import vo from"fs/promises";import ho from"path";import S from"picocolors";import me from"picocolors";var V=(e,t)=>{let o=e.split(`
2886
+ `)+j.cyan(" npx create-lexy add button"))};import ho from"fs/promises";import vo from"path";import S from"picocolors";import me from"picocolors";var V=(e,t)=>{let o=e.split(`
2579
2887
  `),a=t.split(`
2580
- `),n=o.length,r=a.length,i=Array.from({length:n+1},()=>new Array(r+1).fill(0));for(let m=n-1;m>=0;m--)for(let y=r-1;y>=0;y--)i[m][y]=o[m]===a[y]?i[m+1][y+1]+1:Math.max(i[m+1][y],i[m][y+1]);let d=[],s=0,u=0;for(;s<n&&u<r;)o[s]===a[u]?(d.push({type:"same",text:o[s]}),s++,u++):i[s+1][u]>=i[s][u+1]?d.push({type:"del",text:o[s++]}):d.push({type:"add",text:a[u++]});for(;s<n;)d.push({type:"del",text:o[s++]});for(;u<r;)d.push({type:"add",text:a[u++]});return d},Y=e=>e.some(t=>t.type!=="same"),Be=(e,t=3)=>{if(!Y(e))return null;let o=new Array(e.length).fill(!1);e.forEach((r,i)=>{if(r.type!=="same")for(let d=Math.max(0,i-t);d<=Math.min(e.length-1,i+t);d++)o[d]=!0});let a=[],n=!1;for(let r=0;r<e.length;r++){if(!o[r]){n||(a.push(me.dim(" \u22EF")),n=!0);continue}n=!1;let i=e[r];i.type==="same"?a.push(` ${i.text}`):i.type==="del"?a.push(me.red(`- ${i.text}`)):a.push(me.green(`+ ${i.text}`))}return a.join(`
2581
- `)};var Je=async e=>{let t=process.cwd(),o=await O(t),a=e.toLowerCase(),{item:n,version:r}=await k(a),i=o.installed[a];console.log(S.bold(`
2888
+ `),n=o.length,r=a.length,i=Array.from({length:n+1},()=>new Array(r+1).fill(0));for(let m=n-1;m>=0;m--)for(let y=r-1;y>=0;y--)i[m][y]=o[m]===a[y]?i[m+1][y+1]+1:Math.max(i[m+1][y],i[m][y+1]);let d=[],s=0,u=0;for(;s<n&&u<r;)o[s]===a[u]?(d.push({type:"same",text:o[s]}),s++,u++):i[s+1][u]>=i[s][u+1]?d.push({type:"del",text:o[s++]}):d.push({type:"add",text:a[u++]});for(;s<n;)d.push({type:"del",text:o[s++]});for(;u<r;)d.push({type:"add",text:a[u++]});return d},Q=e=>e.some(t=>t.type!=="same"),Be=(e,t=3)=>{if(!Q(e))return null;let o=new Array(e.length).fill(!1);e.forEach((r,i)=>{if(r.type!=="same")for(let d=Math.max(0,i-t);d<=Math.min(e.length-1,i+t);d++)o[d]=!0});let a=[],n=!1;for(let r=0;r<e.length;r++){if(!o[r]){n||(a.push(me.dim(" \u22EF")),n=!0);continue}n=!1;let i=e[r];i.type==="same"?a.push(` ${i.text}`):i.type==="del"?a.push(me.red(`- ${i.text}`)):a.push(me.green(`+ ${i.text}`))}return a.join(`
2889
+ `)};var Je=async e=>{let t=process.cwd(),o=await _(t),a=e.toLowerCase(),{item:n,version:r}=await k(a),i=o.installed[a];console.log(S.bold(`
2582
2890
  ${n.title??a}`)+S.dim(` \xB7 instalado con registry@${i??"?"} \xB7 vigente registry@${r}
2583
- `));let d=!1;for(let s of T(n,o)){let u=await vo.readFile(ho.join(t,s.relPath),s.encoding??"utf-8").catch(()=>null);if(u===null){console.log(S.red(`\u2717 ${s.relPath} no existe localmente`)+S.dim(` \u2014 cr\xE9alo con \`create-lexy add ${a}\``)),d=!0;continue}if(s.encoding==="base64"){u===s.content?console.log(S.green(`\u2713 ${s.relPath}`)+S.dim(" sin diferencias")):(d=!0,console.log(S.yellow(`\xB1 ${s.relPath}`)+S.dim(" (binario difiere del registry)")));continue}let m=Be(V(u,s.content));m===null?console.log(S.green(`\u2713 ${s.relPath}`)+S.dim(" sin diferencias")):(d=!0,console.log(S.yellow(`\xB1 ${s.relPath}`)+S.dim(" (\u2212 local \xB7 + registry)")),console.log(m))}d&&(process.exitCode=1)};import _ from"fs/promises";import v from"path";import C from"picocolors";var We=async e=>{let t=process.cwd(),o=0,a=c=>console.log(C.green(" \u2713 ")+c),n=c=>console.log(C.yellow(" \u2022 ")+c),r=(c,l)=>{o=1,console.log(C.red(" \u2717 ")+c),l&&console.log(C.dim(` \u2192 ${l}`))};console.log(C.bold(`
2891
+ `));let d=!1;for(let s of T(n,o)){let u=await ho.readFile(vo.join(t,s.relPath),s.encoding??"utf-8").catch(()=>null);if(u===null){console.log(S.red(`\u2717 ${s.relPath} no existe localmente`)+S.dim(` \u2014 cr\xE9alo con \`create-lexy add ${a}\``)),d=!0;continue}if(s.encoding==="base64"){u===s.content?console.log(S.green(`\u2713 ${s.relPath}`)+S.dim(" sin diferencias")):(d=!0,console.log(S.yellow(`\xB1 ${s.relPath}`)+S.dim(" (binario difiere del registry)")));continue}let m=Be(V(u,s.content));m===null?console.log(S.green(`\u2713 ${s.relPath}`)+S.dim(" sin diferencias")):(d=!0,console.log(S.yellow(`\xB1 ${s.relPath}`)+S.dim(" (\u2212 local \xB7 + registry)")),console.log(m))}d&&(process.exitCode=1)};import O from"fs/promises";import h from"path";import I from"picocolors";var We=async e=>{let t=process.cwd(),o=0,a=c=>console.log(I.green(" \u2713 ")+c),n=c=>console.log(I.yellow(" \u2022 ")+c),r=(c,l)=>{o=1,console.log(I.red(" \u2717 ")+c),l&&console.log(I.dim(` \u2192 ${l}`))};console.log(I.bold(`
2584
2892
  Diagn\xF3stico del proyecto Lexy
2585
- `));let i;try{i=await O(t),a(`.lexy v\xE1lido (arquitectura ${i.architecture}${i.world?`, mundo ${i.world}`:""})`)}catch(c){return r(c.message),1}await _.access(v.join(t,"src/lexy-theme.css")).then(()=>!0,()=>!1)?a("theme presente (src/lexy-theme.css)"):r("falta src/lexy-theme.css","re-cr\xE9alo desde un proyecto nuevo o copia el theme del registry");let s=v.join(i.paths.lib,"utils/cn.ts");await _.access(v.join(t,s)).then(()=>!0,()=>!1)?a(`helper cn presente (${s})`):r(`falta el helper cn (${s})`);let m=await _.readFile(v.join(t,"package.json"),"utf-8").then(c=>JSON.parse(c)).catch(()=>null),y=async(c,l)=>{await _.access(v.join(t,c)).then(()=>!0,()=>!1)?a(`${l} presente (${c})`):r(`falta ${l} (${c})`)},z=(c,l)=>{if(!m){r("package.json no se pudo leer para validar scripts del prototipo");return}let g=m.scripts?.[c];if(!g){r(`falta el script ${c} en package.json`,l?`agrega \`${l}\``:void 0);return}if(l&&!g.includes(l)){r(`el script ${c} no ejecuta ${l}`);return}a(`script ${c} configurado`)};if(!i.prototype)n("prototipo funcional no habilitado \u2014 proyecto anterior al runtime de datos y ports");else{let c=i.prototype.dataContractPath;if(!c)n("contrato de datos no configurado \u2014 proyecto anterior a la Spec 1");else{await y(c,"contrato de datos");let l=v.join(v.dirname(c),"data-contract-schema.ts");await y(l,"schema del contrato"),await y("scripts/check-data-contract.ts","validador del contrato"),z("check:data-contract","tsx scripts/check-data-contract.ts")}i.prototype.runtimeVersion?(i.prototype.mockStorePath?(await y(i.prototype.mockStorePath,"mock-store del prototipo"),await y(v.join(v.dirname(i.prototype.mockStorePath),"fixtures.ts"),"fixtures del prototipo")):r("mockStorePath no est\xE1 configurado en .lexy"),i.prototype.portsPath?await y(i.prototype.portsPath,"ports del prototipo"):r("portsPath no est\xE1 configurado en .lexy")):n("runtime del prototipo no habilitado \u2014 proyecto anterior a la Spec 2"),i.prototype.designerPanelVersion?(i.prototype.designerPanelPath?await y(i.prototype.designerPanelPath,"panel de asistencia al Designer"):r("designerPanelPath no est\xE1 configurado en .lexy"),i.prototype.designerActivityStorePath?await y(i.prototype.designerActivityStorePath,"store de actividad del Designer"):r("designerActivityStorePath no est\xE1 configurado en .lexy")):n("panel de asistencia al Designer no habilitado \u2014 proyecto anterior a la Spec 4")}let M=v.join(t,"ai/lexy-ai-manifest.json"),p=await _.readFile(M,"utf-8").catch(()=>null);if(p===null)console.log(C.dim(" \xB7 capa de IA no instalada (npx @lexydesign/ai install) \u2014 opcional"));else try{let c=JSON.parse(p),l=c.files??[],g=[];for(let P of l)await _.access(v.join(t,P)).then(()=>!0,()=>!1)||g.push(P);g.length>0?r(`capa de IA ${c.aiVersion??"?"} incompleta \u2014 faltan ${g.length} archivo(s) (${g.slice(0,3).join(", ")}${g.length>3?", \u2026":""})`,"npx @lexydesign/ai install"):a(`capa de IA ${c.aiVersion??"?"} completa (${l.length} archivos)`)}catch{r("ai/lexy-ai-manifest.json no es JSON v\xE1lido","regenera con `npx @lexydesign/ai install`")}let f=Object.entries(i.installed);if(f.length===0)console.log(C.dim(`
2586
- Sin componentes instalados a\xFAn (create-lexy add <nombre>).`));else{let c=await W();console.log(C.bold(`
2893
+ `));let i;try{i=await _(t),a(`.lexy v\xE1lido (arquitectura ${i.architecture}${i.world?`, mundo ${i.world}`:""})`)}catch(c){return r(c.message),1}await O.access(h.join(t,"src/lexy-theme.css")).then(()=>!0,()=>!1)?a("theme presente (src/lexy-theme.css)"):r("falta src/lexy-theme.css","re-cr\xE9alo desde un proyecto nuevo o copia el theme del registry");let s=h.join(i.paths.lib,"utils/cn.ts");await O.access(h.join(t,s)).then(()=>!0,()=>!1)?a(`helper cn presente (${s})`):r(`falta el helper cn (${s})`);let m=await O.readFile(h.join(t,"package.json"),"utf-8").then(c=>JSON.parse(c)).catch(()=>null),y=async(c,l)=>{await O.access(h.join(t,c)).then(()=>!0,()=>!1)?a(`${l} presente (${c})`):r(`falta ${l} (${c})`)},z=(c,l)=>{if(!m){r("package.json no se pudo leer para validar scripts del prototipo");return}let g=m.scripts?.[c];if(!g){r(`falta el script ${c} en package.json`,l?`agrega \`${l}\``:void 0);return}if(l&&!g.includes(l)){r(`el script ${c} no ejecuta ${l}`);return}a(`script ${c} configurado`)};if(!i.prototype)n("prototipo funcional no habilitado \u2014 proyecto anterior al runtime de datos y ports");else{let c=i.prototype.dataContractPath;if(!c)n("contrato de datos no configurado \u2014 proyecto anterior a la Spec 1");else{await y(c,"contrato de datos");let l=h.join(h.dirname(c),"data-contract-schema.ts");await y(l,"schema del contrato"),await y("scripts/check-data-contract.ts","validador del contrato"),z("check:data-contract","tsx scripts/check-data-contract.ts")}i.prototype.runtimeVersion?(i.prototype.mockStorePath?(await y(i.prototype.mockStorePath,"mock-store del prototipo"),await y(h.join(h.dirname(i.prototype.mockStorePath),"fixtures.ts"),"fixtures del prototipo")):r("mockStorePath no est\xE1 configurado en .lexy"),i.prototype.portsPath?await y(i.prototype.portsPath,"ports del prototipo"):r("portsPath no est\xE1 configurado en .lexy")):n("runtime del prototipo no habilitado \u2014 proyecto anterior a la Spec 2"),i.prototype.designerPanelVersion?(i.prototype.designerPanelPath?await y(i.prototype.designerPanelPath,"panel de asistencia al Designer"):r("designerPanelPath no est\xE1 configurado en .lexy"),i.prototype.designerActivityStorePath?await y(i.prototype.designerActivityStorePath,"store de actividad del Designer"):r("designerActivityStorePath no est\xE1 configurado en .lexy")):n("panel de asistencia al Designer no habilitado \u2014 proyecto anterior a la Spec 4")}let M=h.join(t,"ai/lexy-ai-manifest.json"),p=await O.readFile(M,"utf-8").catch(()=>null);if(p===null)console.log(I.dim(" \xB7 capa de IA no instalada (npx @lexydesign/ai install) \u2014 opcional"));else try{let c=JSON.parse(p),l=c.files??[],g=[];for(let P of l)await O.access(h.join(t,P)).then(()=>!0,()=>!1)||g.push(P);g.length>0?r(`capa de IA ${c.aiVersion??"?"} incompleta \u2014 faltan ${g.length} archivo(s) (${g.slice(0,3).join(", ")}${g.length>3?", \u2026":""})`,"npx @lexydesign/ai install"):a(`capa de IA ${c.aiVersion??"?"} completa (${l.length} archivos)`)}catch{r("ai/lexy-ai-manifest.json no es JSON v\xE1lido","regenera con `npx @lexydesign/ai install`")}let f=Object.entries(i.installed);if(f.length===0)console.log(I.dim(`
2894
+ Sin componentes instalados a\xFAn (create-lexy add <nombre>).`));else{let c=await W();console.log(I.bold(`
2587
2895
  Componentes instalados (registry vigente: ${c})
2588
- `));for(let[l,g]of f){let P;try{P=await k(l)}catch(L){r(`${l}: ${L.message}`);continue}let U=T(P.item,i),x=[],A=!1;for(let L of U){let H=await _.readFile(v.join(t,L.relPath),"utf-8").catch(()=>null);H===null?x.push(L.relPath):Y(V(H,L.content))&&(A=!0)}if(x.length>0){r(`${l}: archivos faltantes (${x.join(", ")})`,`create-lexy add ${l}`);continue}if(!A){a(`${l} al d\xEDa (${P.version})`);continue}let ee=!0;if(g&&g!==P.version)try{let L=await k(l,g),H=T(L.item,i);ee=!1;for(let he of H){let be=await _.readFile(v.join(t,he.relPath),"utf-8").catch(()=>null);(be===null||Y(V(be,he.content)))&&(ee=!0)}}catch{}ee?e.strict?r(`${l}: editado localmente (difiere del registry vigente)`,`create-lexy diff ${l}`):n(`${l}: editado localmente \u2014 divergencia deliberada (m\xEDrala con \`create-lexy diff ${l}\`)`):r(`${l}: desactualizado (instalado con ${g}, vigente ${P.version})`,`create-lexy diff ${l} \xB7 create-lexy add ${l} --overwrite`)}}return console.log(o===0?C.green(`
2896
+ `));for(let[l,g]of f){let P;try{P=await k(l)}catch(L){r(`${l}: ${L.message}`);continue}let U=T(P.item,i),x=[],A=!1;for(let L of U){let H=await O.readFile(h.join(t,L.relPath),"utf-8").catch(()=>null);H===null?x.push(L.relPath):Q(V(H,L.content))&&(A=!0)}if(x.length>0){r(`${l}: archivos faltantes (${x.join(", ")})`,`create-lexy add ${l}`);continue}if(!A){a(`${l} al d\xEDa (${P.version})`);continue}let ee=!0;if(g&&g!==P.version)try{let L=await k(l,g),H=T(L.item,i);ee=!1;for(let ve of H){let be=await O.readFile(h.join(t,ve.relPath),"utf-8").catch(()=>null);(be===null||Q(V(be,ve.content)))&&(ee=!0)}}catch{}ee?e.strict?r(`${l}: editado localmente (difiere del registry vigente)`,`create-lexy diff ${l}`):n(`${l}: editado localmente \u2014 divergencia deliberada (m\xEDrala con \`create-lexy diff ${l}\`)`):r(`${l}: desactualizado (instalado con ${g}, vigente ${P.version})`,`create-lexy diff ${l} \xB7 create-lexy add ${l} --overwrite`)}}return console.log(o===0?I.green(`
2589
2897
  Todo en orden.
2590
- `):C.red(`
2898
+ `):I.red(`
2591
2899
  Hay problemas que atender (exit 1).
2592
2900
  `)),o};import ue from"fs/promises";import Ge from"path";import{note as bo,outro as wo}from"@clack/prompts";import ye from"picocolors";var X="LEXY-KICKOFF.md",So=`# Kickoff de proyecto Lexy \u2014 protocolo de entrevista
2593
2901
 
@@ -2679,16 +2987,16 @@ producci\xF3n; el panel registra cargas y publicaciones para inspecci\xF3n.
2679
2987
  Borra este archivo (\`${X}\`): su trabajo termin\xF3. Conf\xEDrmale a la
2680
2988
  persona que su proyecto est\xE1 listo y prop\xF3n el primer paso concreto
2681
2989
  (p. ej. "\xBFDise\xF1amos la pantalla de inicio?").
2682
- `,Qe=async e=>{let t=process.cwd();for(let n of["package.json",".lexy"])if(await ue.access(Ge.join(t,n)).then(()=>!0,()=>!1))throw new Error(`El directorio actual ya contiene un proyecto (${n}). \`kickoff\` es para empezar de cero en una carpeta vac\xEDa.`);let o=Ge.join(t,X);if(await ue.access(o).then(()=>!0,()=>!1)&&!e.force)throw new Error(`${X} ya existe. Usa --force para regenerarlo.`);await ue.writeFile(o,So),bo(`Se cre\xF3 ${ye.cyan(X)} en esta carpeta.
2990
+ `,Ye=async e=>{let t=process.cwd();for(let n of["package.json",".lexy"])if(await ue.access(Ge.join(t,n)).then(()=>!0,()=>!1))throw new Error(`El directorio actual ya contiene un proyecto (${n}). \`kickoff\` es para empezar de cero en una carpeta vac\xEDa.`);let o=Ge.join(t,X);if(await ue.access(o).then(()=>!0,()=>!1)&&!e.force)throw new Error(`${X} ya existe. Usa --force para regenerarlo.`);await ue.writeFile(o,So),bo(`Se cre\xF3 ${ye.cyan(X)} en esta carpeta.
2683
2991
 
2684
2992
  Abre la carpeta con Claude Code y di: `+ye.bold("\xABay\xFAdame a arrancar mi proyecto Lexy\xBB")+`.
2685
- El agente te entrevistar\xE1 y montar\xE1 el proyecto por ti.`,"Kickoff listo"),wo(ye.green("Sin flags, sin prompts t\xE9cnicos \u2014 solo conversa con el agente."))};import fe from"fs/promises";import Z from"path";import I from"picocolors";var xe="@lexydesign/kit",Ye=`https://cdn.jsdelivr.net/npm/${xe}`,Xe=8e3,ge=async e=>{let t=await fetch(e,{signal:AbortSignal.timeout(Xe)});if(!t.ok){let o=new Error(`HTTP ${t.status} al pedir ${e}`);throw o.status=t.status,o}return Buffer.from(await t.arrayBuffer())},ko=async()=>{try{let t=await fetch(`https://registry.npmjs.org/${xe}/latest`,{signal:AbortSignal.timeout(Xe)});if(t.ok)return(await t.json()).version}catch{}return JSON.parse((await ge(`${Ye}@latest/package.json`)).toString("utf-8")).version},Ze=async e=>{let t=process.cwd(),o=Z.resolve(t,e.dir??"lexy-kit"),a=Z.relative(t,o)||".";if(await fe.access(o).then(()=>!0).catch(()=>!1)&&!e.force)throw new Error(`Ya existe ${I.bold(a)}. Usa ${I.cyan("--force")} para sobrescribir o ${I.cyan("--dir <ruta>")} para otra carpeta.`);let r=await ko();console.log(I.dim(`
2993
+ El agente te entrevistar\xE1 y montar\xE1 el proyecto por ti.`,"Kickoff listo"),wo(ye.green("Sin flags, sin prompts t\xE9cnicos \u2014 solo conversa con el agente."))};import fe from"fs/promises";import Z from"path";import C from"picocolors";var xe="@lexydesign/kit",Qe=`https://cdn.jsdelivr.net/npm/${xe}`,Xe=8e3,ge=async e=>{let t=await fetch(e,{signal:AbortSignal.timeout(Xe)});if(!t.ok){let o=new Error(`HTTP ${t.status} al pedir ${e}`);throw o.status=t.status,o}return Buffer.from(await t.arrayBuffer())},ko=async()=>{try{let t=await fetch(`https://registry.npmjs.org/${xe}/latest`,{signal:AbortSignal.timeout(Xe)});if(t.ok)return(await t.json()).version}catch{}return JSON.parse((await ge(`${Qe}@latest/package.json`)).toString("utf-8")).version},Ze=async e=>{let t=process.cwd(),o=Z.resolve(t,e.dir??"lexy-kit"),a=Z.relative(t,o)||".";if(await fe.access(o).then(()=>!0).catch(()=>!1)&&!e.force)throw new Error(`Ya existe ${C.bold(a)}. Usa ${C.cyan("--force")} para sobrescribir o ${C.cyan("--dir <ruta>")} para otra carpeta.`);let r=await ko();console.log(C.dim(`
2686
2994
  Trayendo ${xe}@${r} \u2192 ${a}/
2687
- `));let i=`${Ye}@${r}/kit`,d=JSON.parse((await ge(`${i}/manifest.json`)).toString("utf-8")),s=["index.html","kit.css","kit.js","manifest.json","README.md","AGENTS.md","llms.txt","llms-full.txt","fonts/noto-sans-latin.woff2","fonts/OFL-NotoSans.txt",...d.guides?.pautas??[],...d.components.map(m=>m.file),...d.blocks.map(m=>m.file)],u=0;for(let m of s)try{let y=await ge(`${i}/${m}`),z=Z.join(o,m);await fe.mkdir(Z.dirname(z),{recursive:!0}),await fe.writeFile(z,y),u+=1}catch(y){console.warn(I.yellow(`\u26A0 no se pudo traer ${m}`)+I.dim(` (${y.message})`))}console.log(I.green("\u2713 Kit listo")+I.dim(` \u2014 ${u} archivo(s), ${d.components.length} componente(s) + ${d.blocks.length} block(s)
2688
- `)),console.log(` Abre ${I.bold(`${a}/index.html`)} en el navegador.`),console.log(I.dim(` El cat\xE1logo m\xE1quina-legible est\xE1 en ${a}/manifest.json.
2689
- `))};import Eo from"fs/promises";import ve from"path";import E from"picocolors";var K=e=>console.log(E.bold(E.cyan(`
2995
+ `));let i=`${Qe}@${r}/kit`,d=JSON.parse((await ge(`${i}/manifest.json`)).toString("utf-8")),s=["index.html","kit.css","kit.js","manifest.json","README.md","AGENTS.md","llms.txt","llms-full.txt","fonts/noto-sans-latin.woff2","fonts/OFL-NotoSans.txt",...d.guides?.pautas??[],...d.components.map(m=>m.file),...d.blocks.map(m=>m.file)],u=0;for(let m of s)try{let y=await ge(`${i}/${m}`),z=Z.join(o,m);await fe.mkdir(Z.dirname(z),{recursive:!0}),await fe.writeFile(z,y),u+=1}catch(y){console.warn(C.yellow(`\u26A0 no se pudo traer ${m}`)+C.dim(` (${y.message})`))}console.log(C.green("\u2713 Kit listo")+C.dim(` \u2014 ${u} archivo(s), ${d.components.length} componente(s) + ${d.blocks.length} block(s)
2996
+ `)),console.log(` Abre ${C.bold(`${a}/index.html`)} en el navegador.`),console.log(C.dim(` El cat\xE1logo m\xE1quina-legible est\xE1 en ${a}/manifest.json.
2997
+ `))};import Eo from"fs/promises";import he from"path";import E from"picocolors";var K=e=>console.log(E.bold(E.cyan(`
2690
2998
  \u2500\u2500 ${e} \u2500\u2500
2691
2999
  `))),et=async(e,t)=>{if(t.list||!e){let{index:i,version:d,source:s}=await je();K(`Cat\xE1logo Lexy \xB7 @lexydesign/registry@${d}${s==="bundle"?" (bundle local)":""}`);for(let u of i.items)console.log(` ${E.bold(u.name.padEnd(20))} ${E.dim(u.description??"")}`);console.log(E.dim(`
2692
- ${i.items.length} componente(s). Instala con: create-lexy add <nombre>`));return}let o=e.toLowerCase();if(t.installed){let i=process.cwd(),d=await O(i),s=d.installed[o];if(!s){console.error(E.red(`"${o}" no figura como instalado en .lexy. Inst\xE1lalo con \`create-lexy add ${o}\`.`)),process.exitCode=1;return}let{item:u}=await k(o,s).catch(()=>k(o));K(`${u.title??o} \xB7 copia local (instalado con registry@${s})`);for(let m of T(u,d)){let y=await Eo.readFile(ve.join(i,m.relPath),"utf-8").catch(()=>null);K(y===null?`${m.relPath} (FALTANTE)`:m.relPath),y!==null&&console.log(y)}return}let{item:a,version:n,source:r}=await k(o);K(`${a.title??a.name} \xB7 @lexydesign/registry@${n}${r==="bundle"?" (bundle local)":""}`),a.description&&console.log(a.description+`
2693
- `),console.log(E.dim("tipo: ")+a.type),console.log(E.dim("deps npm: ")+((a.dependencies??[]).join(", ")||"\u2014")),console.log(E.dim("deps registry: ")+((a.registryDependencies??[]).join(", ")||"\u2014")),console.log(E.dim("archivos: ")+a.files.map(i=>ve.posix.basename(i.path)).join(", ")),console.log(E.dim("instalar: ")+`create-lexy add ${a.name}`);for(let i of a.files)typeof i.content=="string"&&(K(ve.posix.basename(i.path)),console.log(i.content))};var To=tt.dirname(jo(import.meta.url)),Ro=JSON.parse(Po(tt.join(To,"../package.json"),"utf-8")),N=new Co,D=e=>async()=>{try{await e()}catch(t){console.error(Io.red(`
2694
- Error: `)+t.message),process.exit(1)}};N.name("create-lexy").description("CLI del Lexy Design System: crea proyectos y trae componentes a demanda.\nLos componentes viven en tu proyecto \u2014 m\xEDralos con `view`, inst\xE1lalos con `add`, ed\xEDtalos con libertad.").version(Ro.version);N.command("create",{isDefault:!0}).alias("init").description("Crea un proyecto Lexy vac\xEDo (React + Vite + TS + theme); los componentes llegan con `add`").argument("[project-name]","Nombre del proyecto").option("-t, --type <architecture>","Arquitectura (feature o layer) \u2014 activa el modo no interactivo").option("-w, --world <world>","Mundo de dise\xF1o (cliente, crm o mixto)").option("--no-install","No correr pnpm install al final").action((e,t)=>D(()=>He(e,t))());N.command("kickoff").description("Deja un .md de entrevista para que el agente conduzca el arranque de un dise\xF1ador (carpeta vac\xEDa)").option("--force","Regenerar el .md de kickoff si ya existe").action(e=>D(()=>Qe(e))());N.command("add").description("Instala componentes del registry en tu proyecto (local y editable), con sus dependencias").argument("<components...>","Nombres en el registry (ej: button card)").option("--overwrite","Sobrescribir copias locales con cambios sin preguntar").option("--no-install","No instalar dependencias npm").action((e,t)=>D(()=>Re(e,t))());N.command("view").description("Muestra c\xF3digo + doc + metadata de un componente antes de instalarlo").argument("[component]","Nombre en el registry (sin nombre: lista el cat\xE1logo)").option("--installed","Mostrar la copia local instalada en vez de la del registry").option("--list","Listar el cat\xE1logo completo").action((e,t)=>D(()=>et(e,t))());N.command("kit").description("Trae el kit HTML/low-fi (mismos componentes y blocks en HTML plano) a una carpeta").option("--dir <path>","Carpeta destino (por defecto: lexy-kit)").option("--force","Sobrescribir la carpeta si ya existe").action(e=>D(()=>Ze(e))());N.command("diff").description("Copia local vs versi\xF3n vigente del registry (exit 1 si hay diferencias)").argument("<component>","Nombre en el registry").action(e=>D(()=>Je(e))());N.command("doctor").description("Drift de todo lo instalado contra el registry (solo lectura; exit 1 con problemas)").option("--strict","Las ediciones locales tambi\xE9n hacen fallar").action(e=>D(async()=>{process.exitCode=await We(e)})());N.parse(process.argv);
3000
+ ${i.items.length} componente(s). Instala con: create-lexy add <nombre>`));return}let o=e.toLowerCase();if(t.installed){let i=process.cwd(),d=await _(i),s=d.installed[o];if(!s){console.error(E.red(`"${o}" no figura como instalado en .lexy. Inst\xE1lalo con \`create-lexy add ${o}\`.`)),process.exitCode=1;return}let{item:u}=await k(o,s).catch(()=>k(o));K(`${u.title??o} \xB7 copia local (instalado con registry@${s})`);for(let m of T(u,d)){let y=await Eo.readFile(he.join(i,m.relPath),"utf-8").catch(()=>null);K(y===null?`${m.relPath} (FALTANTE)`:m.relPath),y!==null&&console.log(y)}return}let{item:a,version:n,source:r}=await k(o);K(`${a.title??a.name} \xB7 @lexydesign/registry@${n}${r==="bundle"?" (bundle local)":""}`),a.description&&console.log(a.description+`
3001
+ `),console.log(E.dim("tipo: ")+a.type),console.log(E.dim("deps npm: ")+((a.dependencies??[]).join(", ")||"\u2014")),console.log(E.dim("deps registry: ")+((a.registryDependencies??[]).join(", ")||"\u2014")),console.log(E.dim("archivos: ")+a.files.map(i=>he.posix.basename(i.path)).join(", ")),console.log(E.dim("instalar: ")+`create-lexy add ${a.name}`);for(let i of a.files)typeof i.content=="string"&&(K(he.posix.basename(i.path)),console.log(i.content))};var To=tt.dirname(jo(import.meta.url)),Ro=JSON.parse(Po(tt.join(To,"../package.json"),"utf-8")),N=new Io,D=e=>async()=>{try{await e()}catch(t){console.error(Co.red(`
3002
+ Error: `)+t.message),process.exit(1)}};N.name("create-lexy").description("CLI del Lexy Design System: crea proyectos y trae componentes a demanda.\nLos componentes viven en tu proyecto \u2014 m\xEDralos con `view`, inst\xE1lalos con `add`, ed\xEDtalos con libertad.").version(Ro.version);N.command("create",{isDefault:!0}).alias("init").description("Crea un proyecto Lexy vac\xEDo (React + Vite + TS + theme); los componentes llegan con `add`").argument("[project-name]","Nombre del proyecto").option("-t, --type <architecture>","Arquitectura (feature o layer) \u2014 activa el modo no interactivo").option("-w, --world <world>","Mundo de dise\xF1o (cliente, crm o mixto)").option("--no-install","No correr pnpm install al final").action((e,t)=>D(()=>He(e,t))());N.command("kickoff").description("Deja un .md de entrevista para que el agente conduzca el arranque de un dise\xF1ador (carpeta vac\xEDa)").option("--force","Regenerar el .md de kickoff si ya existe").action(e=>D(()=>Ye(e))());N.command("add").description("Instala componentes del registry en tu proyecto (local y editable), con sus dependencias").argument("<components...>","Nombres en el registry (ej: button card)").option("--overwrite","Sobrescribir copias locales con cambios sin preguntar").option("--no-install","No instalar dependencias npm").action((e,t)=>D(()=>Re(e,t))());N.command("view").description("Muestra c\xF3digo + doc + metadata de un componente antes de instalarlo").argument("[component]","Nombre en el registry (sin nombre: lista el cat\xE1logo)").option("--installed","Mostrar la copia local instalada en vez de la del registry").option("--list","Listar el cat\xE1logo completo").action((e,t)=>D(()=>et(e,t))());N.command("kit").description("Trae el kit HTML/low-fi (mismos componentes y blocks en HTML plano) a una carpeta").option("--dir <path>","Carpeta destino (por defecto: lexy-kit)").option("--force","Sobrescribir la carpeta si ya existe").action(e=>D(()=>Ze(e))());N.command("diff").description("Copia local vs versi\xF3n vigente del registry (exit 1 si hay diferencias)").argument("<component>","Nombre en el registry").action(e=>D(()=>Je(e))());N.command("doctor").description("Drift de todo lo instalado contra el registry (solo lectura; exit 1 con problemas)").option("--strict","Las ediciones locales tambi\xE9n hacen fallar").action(e=>D(async()=>{process.exitCode=await We(e)})());N.parse(process.argv);
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "create-lexy",
3
- "version": "0.6.1",
3
+ "version": "0.6.2",
4
4
  "description": "CLI del Lexy Design System — crea proyectos y trae componentes a demanda desde el registry",
5
5
  "type": "module",
6
6
  "bin": {