lkd-web-kit 0.10.2 → 0.10.3

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 (33) hide show
  1. package/.agents/skills/mantine-combobox/SKILL.md +73 -0
  2. package/.agents/skills/mantine-combobox/references/api.md +199 -0
  3. package/.agents/skills/mantine-combobox/references/patterns.md +279 -0
  4. package/.agents/skills/mantine-custom-components/SKILL.md +112 -0
  5. package/.agents/skills/mantine-custom-components/references/api.md +407 -0
  6. package/.agents/skills/mantine-custom-components/references/patterns.md +431 -0
  7. package/.agents/skills/publish-lkd-web-kit/SKILL.md +172 -0
  8. package/.agents/skills/publish-lkd-web-kit/agents/openai.yaml +4 -0
  9. package/.agents/skills/publish-lkd-web-kit/references/npm-trusted-publishing.md +82 -0
  10. package/.agents/skills/update-lkd-dependencies/SKILL.md +88 -0
  11. package/.agents/skills/update-lkd-dependencies/agents/openai.yaml +4 -0
  12. package/.agents/skills/update-lkd-dependencies/scripts/collect-npm-metadata.mjs +73 -0
  13. package/dist/index.cjs +2 -0
  14. package/dist/index.js +2 -1
  15. package/dist/mantine/breakpoints-with-px.cjs +3 -2
  16. package/dist/mantine/breakpoints-with-px.d.ts +2 -1
  17. package/dist/mantine/breakpoints-with-px.d.ts.map +1 -1
  18. package/dist/mantine/breakpoints-with-px.js +3 -2
  19. package/dist/mantine/create-lkd-theme.cjs +7 -0
  20. package/dist/mantine/create-lkd-theme.d.ts +3 -0
  21. package/dist/mantine/create-lkd-theme.d.ts.map +1 -0
  22. package/dist/mantine/create-lkd-theme.js +6 -0
  23. package/dist/mantine/index.d.ts +1 -0
  24. package/dist/mantine/index.d.ts.map +1 -1
  25. package/package.json +3 -3
  26. package/scripts/{install-codex-skills.mjs → install-agent-skills.mjs} +1 -1
  27. package/codex/skills/create-modal-component/SKILL.md +0 -168
  28. package/codex/skills/create-modal-component/agents/openai.yaml +0 -4
  29. package/codex/skills/create-svg-icon/SKILL.md +0 -41
  30. package/codex/skills/create-svg-icon/agents/openai.yaml +0 -3
  31. package/codex/skills/create-table-component/SKILL.md +0 -189
  32. package/codex/skills/create-table-component/agents/openai.yaml +0 -3
  33. package/codex/skills/rhf-lkd-forms/SKILL.md +0 -186
@@ -0,0 +1,88 @@
1
+ ---
2
+ name: update-lkd-dependencies
3
+ description: Audita y actualiza con cautela solo las peerDependencies de lkd-web-kit. Usar cuando el usuario pida revisar versiones disponibles, actualizar peers del paquete, evaluar breaking changes de React/Mantine/Next/Zod/React Hook Form/TanStack/Ky, sincronizar package-lock o preparar una recomendacion SemVer sin publicar.
4
+ ---
5
+
6
+ # Actualizar dependencias LKD
7
+
8
+ ## Principio
9
+
10
+ Trabaja como auditor de compatibilidad de una libreria React corporativa. No actualices a ciegas: primero descubre versiones, peers, engines y riesgos; despues edita de forma acotada y valida el paquete.
11
+
12
+ Esta skill no sube la version de `lkd-web-kit`, no crea tags y no publica en npm. Para publicar usa `$publish-lkd-web-kit`.
13
+
14
+ Esta skill es solo para `peerDependencies`. No actualices `devDependencies`, `dependencies` ni tooling interno salvo que sea estrictamente necesario para que el lockfile resuelva los peers actualizados y el usuario lo haya pedido.
15
+
16
+ ## Contexto obligatorio
17
+
18
+ Antes de proponer o editar dependencias, lee:
19
+
20
+ - `AGENTS.md`
21
+ - `package.json`
22
+ - `package-lock.json`
23
+ - `docs/generated/lkd-web-kit.md`
24
+
25
+ Usa `docs/generated/lkd-web-kit.md` como fuente de verdad del catalogo publico de componentes. Si un cambio de dependencia puede afectar props, wrappers Mantine, formularios o hooks publicos, tratalo como riesgo de compatibilidad.
26
+
27
+ ## Auditoria de versiones
28
+
29
+ 1. Identifica todas las entradas de `peerDependencies`.
30
+ 2. Consulta metadata de npm para cada paquete relevante:
31
+
32
+ ```bash
33
+ npm view <pkg> version peerDependencies dependencies engines --json
34
+ ```
35
+
36
+ 3. Para un reporte inicial no mutante, puedes ejecutar:
37
+
38
+ ```bash
39
+ node .agents/skills/update-lkd-dependencies/scripts/collect-npm-metadata.mjs
40
+ ```
41
+
42
+ 4. Actualiza solo a versiones estables publicadas. Evita prereleases, canary, alpha, beta, rc y next salvo instruccion explicita.
43
+ 5. Mantiene alineadas familias peer que deben avanzar juntas: `react`/`react-dom`, paquetes `@mantine/*` y paquetes `@tanstack/*` cuando compartan contrato.
44
+
45
+ ## Politica de riesgo
46
+
47
+ Detente y reporta antes de aplicar si encuentras:
48
+
49
+ - Cambio major en React, Mantine, Next, Zod, React Hook Form, TanStack Query o Ky.
50
+ - Cambio de `engines.node` que exceda el `>=22.12.0` actual o reduzca compatibilidad razonable.
51
+ - Peer ranges incompatibles entre dependencias del kit.
52
+ - Migraciones que obliguen a cambiar APIs publicas, props exportadas, tipos o comportamiento de componentes.
53
+
54
+ Puedes aplicar patch/minor compatibles cuando las pruebas y peers lo respalden. Para majors, aplica solo si el usuario pidio explicitamente aceptar el breaking change o si el analisis demuestra que el rango actual ya era incompatible.
55
+
56
+ Si por un breaking change tuviste que modificar props, componentes, formularios, hooks exportados o utilidades documentadas, regenera `docs/generated/lkd-web-kit.md` siguiendo estrictamente `docs/generate-lkd-web-kit-docs.md`. No edites el documento generado a mano salvo correcciones mecanicas posteriores al diff.
57
+
58
+ ## Edicion y validacion
59
+
60
+ Cuando edites:
61
+
62
+ - Actualiza solo `peerDependencies` en `package.json` y sincroniza `package-lock.json`.
63
+ - Corrige drift de version entre `package.json` y `package-lock.json`; en este repo se ha visto `package.json` en `0.8.4` y lockfile en `0.8.3`.
64
+ - No cambies `version` del paquete salvo que el usuario lo pida explicitamente fuera de esta skill.
65
+ - No ejecutes `npm publish`, no crees tags y no automatices login.
66
+
67
+ Validacion minima:
68
+
69
+ ```bash
70
+ npm install --package-lock-only
71
+ npm run lint
72
+ npm run test
73
+ npm run build
74
+ npm pack --dry-run
75
+ ```
76
+
77
+ Si una validacion falla, arregla solo lo necesario para la actualizacion o reporta el bloqueo con el paquete responsable.
78
+
79
+ ## Reporte final
80
+
81
+ Termina siempre con un resumen en espanol:
82
+
83
+ - Peer dependencies actualizadas.
84
+ - Peer dependencies retenidas y motivo.
85
+ - Breaking changes o riesgos detectados.
86
+ - Si se regenero `docs/generated/lkd-web-kit.md`, indica por que cambio la superficie publica.
87
+ - Validaciones ejecutadas y resultado.
88
+ - Recomendacion SemVer para una futura publicacion: `major`, `minor` o `patch`, con una frase de justificacion.
@@ -0,0 +1,4 @@
1
+ interface:
2
+ display_name: "Actualizar dependencias LKD"
3
+ short_description: "Audita y actualiza peer deps del kit"
4
+ default_prompt: "Usa $update-lkd-dependencies para auditar y actualizar solo las peerDependencies de lkd-web-kit con cautela."
@@ -0,0 +1,73 @@
1
+ #!/usr/bin/env node
2
+ import { execFile } from 'node:child_process'
3
+ import { readFile } from 'node:fs/promises'
4
+ import { promisify } from 'node:util'
5
+
6
+ const execFileAsync = promisify(execFile)
7
+ const packageJsonPath = new URL('../../../../package.json', import.meta.url)
8
+ const npmCommand = process.platform === 'win32' ? 'npm.cmd' : 'npm'
9
+
10
+ function parseMaybeJson(value) {
11
+ try {
12
+ return JSON.parse(value)
13
+ } catch {
14
+ return value.trim()
15
+ }
16
+ }
17
+
18
+ async function npmView(packageName) {
19
+ const { stdout } = await execFileAsync(
20
+ npmCommand,
21
+ ['view', packageName, 'version', 'peerDependencies', 'dependencies', 'engines', '--json'],
22
+ { shell: process.platform === 'win32', windowsHide: true },
23
+ )
24
+
25
+ return parseMaybeJson(stdout)
26
+ }
27
+
28
+ async function main() {
29
+ const packageJson = JSON.parse(await readFile(packageJsonPath, 'utf8'))
30
+ const names = Object.keys(packageJson.peerDependencies ?? {}).sort()
31
+ const results = []
32
+
33
+ for (const name of names) {
34
+ const currentRange = packageJson.peerDependencies?.[name] ?? null
35
+
36
+ try {
37
+ results.push({
38
+ name,
39
+ section: 'peerDependencies',
40
+ currentRange,
41
+ npm: await npmView(name),
42
+ })
43
+ } catch (error) {
44
+ results.push({
45
+ name,
46
+ section: 'peerDependencies',
47
+ currentRange,
48
+ error: error instanceof Error ? error.message : String(error),
49
+ })
50
+ }
51
+ }
52
+
53
+ console.log(
54
+ JSON.stringify(
55
+ {
56
+ package: {
57
+ name: packageJson.name,
58
+ version: packageJson.version,
59
+ engines: packageJson.engines ?? {},
60
+ },
61
+ generatedAt: new Date().toISOString(),
62
+ dependencies: results,
63
+ },
64
+ null,
65
+ 2,
66
+ ),
67
+ )
68
+ }
69
+
70
+ main().catch((error) => {
71
+ console.error(error instanceof Error ? error.message : String(error))
72
+ process.exitCode = 1
73
+ })
package/dist/index.cjs CHANGED
@@ -58,6 +58,7 @@ const require_useFetchNextPageOnScroll = require("./hooks/useFetchNextPageOnScro
58
58
  const require_useUpdateSearchParams = require("./hooks/useUpdateSearchParams.cjs");
59
59
  const require_useZodConfig = require("./hooks/useZodConfig.cjs");
60
60
  const require_my_default_theme = require("./mantine/my-default-theme.cjs");
61
+ const require_create_lkd_theme = require("./mantine/create-lkd-theme.cjs");
61
62
  const require_to_tailwind_colors = require("./mantine/to-tailwind-colors.cjs");
62
63
  const require_groupBy = require("./utils/array/groupBy.cjs");
63
64
  const require_shuffleArray = require("./utils/array/shuffleArray.cjs");
@@ -115,6 +116,7 @@ exports.TableWrapperPagination = require_TableWrapperPagination;
115
116
  exports.TableWrapperTitle = require_TableWrapperTitle;
116
117
  exports.addBodyJsonHook = require_addBodyJsonHook.addBodyJsonHook;
117
118
  exports.breakpointsWithPx = require_breakpoints_with_px.breakpointsWithPx;
119
+ exports.createLkdTheme = require_create_lkd_theme.createLkdTheme;
118
120
  exports.createNewRoute = require_new_route.createNewRoute;
119
121
  exports.formatBytes = require_formatBytes.formatBytes;
120
122
  exports.getVirtualContainerProps = require_virtual_styles.getVirtualContainerProps;
package/dist/index.js CHANGED
@@ -57,6 +57,7 @@ import { useFetchNextPageOnScroll } from "./hooks/useFetchNextPageOnScroll.js";
57
57
  import { useUpdateSearchParams } from "./hooks/useUpdateSearchParams.js";
58
58
  import { useZodConfig } from "./hooks/useZodConfig.js";
59
59
  import { myDefaultTheme } from "./mantine/my-default-theme.js";
60
+ import { createLkdTheme } from "./mantine/create-lkd-theme.js";
60
61
  import { toTailwindColors } from "./mantine/to-tailwind-colors.js";
61
62
  import { groupBy, indexBy } from "./utils/array/groupBy.js";
62
63
  import { shuffleArray } from "./utils/array/shuffleArray.js";
@@ -66,4 +67,4 @@ import { addBodyJsonHook } from "./utils/ky/addBodyJsonHook.js";
66
67
  import { parseJSON } from "./utils/ky/parseJson.js";
67
68
  import { queryStringify } from "./utils/query-stringify.js";
68
69
  import { createNewRoute, newRoute } from "./utils/new-route.js";
69
- export { EmptyState, Form, FormCheckbox, FormCheckboxGroup, FormDateInput, FormDatePickerInput, FormDateTimePicker, FormInfinitySelect, FormMonthPickerInput, FormMultiSelect, FormNumberInput, FormRadioGroup, FormSelect, FormSubmitButton, FormTextInput, FormTextarea, FormTimeInput, HttpStatus, Icon, InfinityLoadMoreButton, InfinitySelect, ModalManagerProvider, MyCheckboxGroup, MyDateInput, MyDatePickerInput, MyDateTimePicker, MyMonthPickerInput, MyMultiSelect, MyNotifications, MyNumberInput, MyRadioGroup, MySelect, MyTable, MyTextInput, MyTextarea, MyTimeInput, NavItems, NavigationHistoryProvider, PageDataProvider, QP_BACK_URL_NAME, Revalidate, TableWrapper, TableWrapperFooter, TableWrapperHeader, TableWrapperPagination, TableWrapperTitle, addBodyJsonHook, breakpointsWithPx, createNewRoute, formatBytes, getVirtualContainerProps, getVirtualItemProps, groupBy, indexBy, isInfinityEmpty, myDefaultTheme, newRoute, nullableButRequired, numberToTimeInput, optionalButRequired, parseJSON, queryStringify, shuffleArray, timeInputToNumber, toTailwindColors, useBreakpoint, useFetchNextPageOnScroll, useModalManager, useNavigationHistory, useOnScrollProgress, usePageData, useUpdateSearchParams, useZodConfig, withController, withModalManager, zodValidator };
70
+ export { EmptyState, Form, FormCheckbox, FormCheckboxGroup, FormDateInput, FormDatePickerInput, FormDateTimePicker, FormInfinitySelect, FormMonthPickerInput, FormMultiSelect, FormNumberInput, FormRadioGroup, FormSelect, FormSubmitButton, FormTextInput, FormTextarea, FormTimeInput, HttpStatus, Icon, InfinityLoadMoreButton, InfinitySelect, ModalManagerProvider, MyCheckboxGroup, MyDateInput, MyDatePickerInput, MyDateTimePicker, MyMonthPickerInput, MyMultiSelect, MyNotifications, MyNumberInput, MyRadioGroup, MySelect, MyTable, MyTextInput, MyTextarea, MyTimeInput, NavItems, NavigationHistoryProvider, PageDataProvider, QP_BACK_URL_NAME, Revalidate, TableWrapper, TableWrapperFooter, TableWrapperHeader, TableWrapperPagination, TableWrapperTitle, addBodyJsonHook, breakpointsWithPx, createLkdTheme, createNewRoute, formatBytes, getVirtualContainerProps, getVirtualItemProps, groupBy, indexBy, isInfinityEmpty, myDefaultTheme, newRoute, nullableButRequired, numberToTimeInput, optionalButRequired, parseJSON, queryStringify, shuffleArray, timeInputToNumber, toTailwindColors, useBreakpoint, useFetchNextPageOnScroll, useModalManager, useNavigationHistory, useOnScrollProgress, usePageData, useUpdateSearchParams, useZodConfig, withController, withModalManager, zodValidator };
@@ -1,11 +1,12 @@
1
1
  //#region src/mantine/breakpoints-with-px.ts
2
2
  var breakpointsWithPx = {
3
- xs: "576px",
3
+ xs: "540px",
4
4
  sm: "640px",
5
5
  md: "768px",
6
6
  lg: "1024px",
7
7
  xl: "1280px",
8
- ["2xl"]: "1536px"
8
+ "2xl": "1536px",
9
+ "3xl": "1680px"
9
10
  };
10
11
  //#endregion
11
12
  exports.breakpointsWithPx = breakpointsWithPx;
@@ -4,6 +4,7 @@ export declare const breakpointsWithPx: {
4
4
  md: string;
5
5
  lg: string;
6
6
  xl: string;
7
- "2xl": string;
7
+ '2xl': string;
8
+ '3xl': string;
8
9
  };
9
10
  //# sourceMappingURL=breakpoints-with-px.d.ts.map
@@ -1 +1 @@
1
- {"version":3,"file":"breakpoints-with-px.d.ts","sourceRoot":"","sources":["../../src/mantine/breakpoints-with-px.ts"],"names":[],"mappings":"AAAA,eAAO,MAAM,iBAAiB;;;;;;;CAO7B,CAAA"}
1
+ {"version":3,"file":"breakpoints-with-px.d.ts","sourceRoot":"","sources":["../../src/mantine/breakpoints-with-px.ts"],"names":[],"mappings":"AAAA,eAAO,MAAM,iBAAiB;;;;;;;;CAQ7B,CAAA"}
@@ -1,11 +1,12 @@
1
1
  //#region src/mantine/breakpoints-with-px.ts
2
2
  var breakpointsWithPx = {
3
- xs: "576px",
3
+ xs: "540px",
4
4
  sm: "640px",
5
5
  md: "768px",
6
6
  lg: "1024px",
7
7
  xl: "1280px",
8
- ["2xl"]: "1536px"
8
+ "2xl": "1536px",
9
+ "3xl": "1680px"
9
10
  };
10
11
  //#endregion
11
12
  export { breakpointsWithPx };
@@ -0,0 +1,7 @@
1
+ require("../_virtual/_rolldown/runtime.cjs");
2
+ const require_my_default_theme = require("./my-default-theme.cjs");
3
+ let _mantine_core = require("@mantine/core");
4
+ //#region src/mantine/create-lkd-theme.ts
5
+ var createLkdTheme = (theme) => (0, _mantine_core.createTheme)((0, _mantine_core.mergeThemeOverrides)(require_my_default_theme.myDefaultTheme, theme));
6
+ //#endregion
7
+ exports.createLkdTheme = createLkdTheme;
@@ -0,0 +1,3 @@
1
+ import { MantineThemeOverride } from '@mantine/core';
2
+ export declare const createLkdTheme: (theme: MantineThemeOverride) => MantineThemeOverride;
3
+ //# sourceMappingURL=create-lkd-theme.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"create-lkd-theme.d.ts","sourceRoot":"","sources":["../../src/mantine/create-lkd-theme.ts"],"names":[],"mappings":"AAAA,OAAO,EAAe,KAAK,oBAAoB,EAAuB,MAAM,eAAe,CAAA;AAG3F,eAAO,MAAM,cAAc,GAAI,OAAO,oBAAoB,KAAG,oBACJ,CAAA"}
@@ -0,0 +1,6 @@
1
+ import { myDefaultTheme } from "./my-default-theme.js";
2
+ import { createTheme, mergeThemeOverrides } from "@mantine/core";
3
+ //#region src/mantine/create-lkd-theme.ts
4
+ var createLkdTheme = (theme) => createTheme(mergeThemeOverrides(myDefaultTheme, theme));
5
+ //#endregion
6
+ export { createLkdTheme };
@@ -1,4 +1,5 @@
1
1
  export * from './breakpoints-with-px';
2
+ export * from './create-lkd-theme';
2
3
  export * from './my-default-theme';
3
4
  export * from './to-tailwind-colors';
4
5
  //# sourceMappingURL=index.d.ts.map
@@ -1 +1 @@
1
- {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../src/mantine/index.ts"],"names":[],"mappings":"AAAA,cAAc,uBAAuB,CAAA;AACrC,cAAc,oBAAoB,CAAA;AAClC,cAAc,sBAAsB,CAAA"}
1
+ {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../src/mantine/index.ts"],"names":[],"mappings":"AAAA,cAAc,uBAAuB,CAAA;AACrC,cAAc,oBAAoB,CAAA;AAClC,cAAc,oBAAoB,CAAA;AAClC,cAAc,sBAAsB,CAAA"}
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "lkd-web-kit",
3
- "version": "0.10.2",
3
+ "version": "0.10.3",
4
4
  "description": "A template for creating React component libraries with Vite.",
5
5
  "author": "LKD",
6
6
  "license": "MIT",
@@ -20,13 +20,13 @@
20
20
  }
21
21
  },
22
22
  "bin": {
23
- "lkd-install-codex-skills": "./scripts/install-codex-skills.mjs"
23
+ "lkd-install-agent-skills": "./scripts/install-agent-skills.mjs"
24
24
  },
25
25
  "sideEffects": false,
26
26
  "engines": {
27
27
  "node": ">=22.12.0"
28
28
  },
29
- "files": ["dist", "codex/skills", "scripts/install-codex-skills.mjs"],
29
+ "files": ["dist", ".agents/skills", "scripts/install-agent-skills.mjs"],
30
30
  "scripts": {
31
31
  "test": "vitest run --passWithNoTests",
32
32
  "test:watch": "vitest",
@@ -4,7 +4,7 @@ import { dirname, join } from 'node:path'
4
4
  import { fileURLToPath } from 'node:url'
5
5
 
6
6
  const scriptDir = dirname(fileURLToPath(import.meta.url))
7
- const source = join(scriptDir, '..', 'codex', 'skills')
7
+ const source = join(scriptDir, '..', '.agents', 'skills')
8
8
  const target = join(process.cwd(), '.agents', 'skills')
9
9
 
10
10
  if (!existsSync(source)) {
@@ -1,168 +0,0 @@
1
- ---
2
- name: create-modal-component
3
- description: Crear modales en proyectos internos con el modal manager global de lkd-web-kit. Usar cuando Codex deba agregar, modificar o registrar modales bajo src/components/modals, envolverlos con withModalManager, elegir entre un modal interno del proyecto o Modal de Mantine, organizar el modal en carpeta propia, tipar props para showModal, actualizar dynamicModals, MyModalManagerProvider, module augmentation o loadModals.
4
- ---
5
-
6
- # Crear Modal Component
7
-
8
- Usar este flujo para modales abiertos con `useModalManager().showModal(...)`.
9
-
10
- ## Lectura Obligatoria
11
-
12
- 1. Leer `docs/lkd-web-kit.md` y `docs/local-components.md`.
13
- 2. Leer `src/components/modals/index.ts`.
14
- 3. Leer `src/contexts/MyModalManagerContext/index.tsx`.
15
- 4. Leer `src/types/lkd-web-kit.d.ts`.
16
- 5. Buscar si existe un modal interno en `src/components/ui` o componentes compartidos antes de importar `Modal` de Mantine.
17
- 6. Leer un modal existente del mismo dominio en `src/components/modals/{dominio}`.
18
- 7. Si se toca `next/dynamic` o lazy loading, leer `node_modules/next/dist/docs/01-app/02-guides/lazy-loading.md`.
19
-
20
- ## Arquitectura Actual
21
-
22
- - `lkd-web-kit` exporta `ModalManagerProvider`, `useModalManager`, `withModalManager`, `ModalRegistryItem`, `ModalKey` y tipos relacionados.
23
- - El proyecto no usa `src/contexts/ModalManagerContext`; no recrearlo.
24
- - `src/contexts/MyModalManagerContext/index.tsx` adapta el provider del kit y le pasa `dynamicModals`.
25
- - `src/types/lkd-web-kit.d.ts` hace module augmentation para que `showModal` infiera keys y props desde `dynamicModals`.
26
- - `src/app/PageProviders.tsx` envuelve la app con `MyModalManagerProvider` y propaga `loadModals`.
27
-
28
- ## Estructura
29
-
30
- - Crear modales en `src/components/modals/{dominio}/{NombreModal}/index.tsx` cuando tengan formulario, schema, hooks internos, assets o subcomponentes.
31
- - Usar archivo plano `src/components/modals/{dominio}/{NombreModal}.tsx` solo para modales triviales de una pieza, siguiendo el patron existente.
32
- - Colocar piezas privadas junto al modal: `schema.ts`, `helpers.ts`, subcomponentes o assets dentro de la misma carpeta.
33
- - No mover logica compartida a `src/components/ui` salvo que ya exista mas de un consumidor real.
34
-
35
- ## Implementacion
36
-
37
- 1. Definir props exportadas si el modal recibe datos desde `showModal`:
38
-
39
- ```tsx
40
- export interface MyModalProps {
41
- itemId: string;
42
- onSuccess?: () => void;
43
- }
44
- ```
45
-
46
- 2. Envolver el componente con `withModalManager<Props>`.
47
- 3. Recibir `modalProps` desde el wrapper y pasarlo al modal raiz.
48
- 4. Antes de usar `Modal` de `@mantine/core`, corroborar si el proyecto tiene un modal interno que ya envuelve Mantine y usarlo si cubre el caso.
49
- 5. Usar clases Tailwind para spacing, radius, shadow, margin y padding; evitar props Mantine equivalentes si `className` resuelve el caso.
50
- 6. Usar wrappers locales del proyecto o `lkd-web-kit` antes que primitivas Mantine directas.
51
- 7. No usar `any`.
52
-
53
- Modal base con modal interno:
54
-
55
- ```tsx
56
- import { withModalManager } from "lkd-web-kit";
57
- import ButtonAE from "src/components/ui/ButtonAE";
58
- import InternalModal from "src/components/ui/InternalModal";
59
-
60
- export interface MyModalProps {
61
- onConfirm?: () => void;
62
- }
63
-
64
- const MyModal = withModalManager<MyModalProps>(
65
- ({ onConfirm, modalProps }) => {
66
- return (
67
- <InternalModal {...modalProps} size="lg">
68
- <InternalModal.Header>Titulo</InternalModal.Header>
69
- <InternalModal.Body className="grid gap-4">Contenido</InternalModal.Body>
70
- <InternalModal.Footer>
71
- <ButtonAE
72
- onClick={() => {
73
- onConfirm?.();
74
- modalProps.onClose?.();
75
- }}
76
- >
77
- Guardar
78
- </ButtonAE>
79
- </InternalModal.Footer>
80
- </InternalModal>
81
- );
82
- },
83
- );
84
-
85
- export default MyModal;
86
- ```
87
-
88
- Fallback con Mantine, solo si no hay modal interno aplicable:
89
-
90
- ```tsx
91
- import { Modal } from "@mantine/core";
92
- import { withModalManager } from "lkd-web-kit";
93
-
94
- const MyModal = withModalManager(({ modalProps }) => (
95
- <Modal {...modalProps} title="Titulo">
96
- Contenido
97
- </Modal>
98
- ));
99
-
100
- export default MyModal;
101
- ```
102
-
103
- ## Registro
104
-
105
- 1. Exportar las props publicas desde el modal.
106
- 2. Importar el tipo de props en `src/components/modals/index.ts`:
107
-
108
- ```ts
109
- import type { MyModalProps } from "./domain/MyModal";
110
- ```
111
-
112
- 3. Registrar con `dynamicModal<Props>("domain/MyModal")`:
113
-
114
- ```ts
115
- "domain.myModal": dynamicModal<MyModalProps>("domain/MyModal"),
116
- ```
117
-
118
- 4. Usar una key estable con formato `{dominio}.{accion}`.
119
- 5. No tocar `src/types/lkd-web-kit.d.ts` si `dynamicModals` sigue siendo la fuente unica. La augmentacion ya apunta a `typeof dynamicModals`.
120
- 6. Si se cambia la forma del registro, mantener `ModalRegistryItem<T>` y que cada item tenga `component`, `load` y `path`.
121
-
122
- ## Contexto y Precarga
123
-
124
- - Para rutas que ya usan `PageProviders`, pasar `loadModals` ahi:
125
-
126
- ```tsx
127
- <PageProviders loadModals={["domain.myModal"]}>{children}</PageProviders>
128
- ```
129
-
130
- - `loadModals` acepta una key exacta o un prefijo, por ejemplo `"development"` para precargar todos los modales cuyo key empieza con ese prefijo.
131
- - Para layouts que no usan `PageProviders`, envolver el arbol con `MyModalManagerProvider`:
132
-
133
- ```tsx
134
- import { MyModalManagerProvider } from "src/contexts/MyModalManagerContext";
135
-
136
- <MyModalManagerProvider loadModals={["domain.myModal"]}>
137
- {children}
138
- </MyModalManagerProvider>
139
- ```
140
-
141
- - Evitar providers anidados salvo que haya una razon real: un provider interno aisla estado y puede cerrar o reemplazar modales inesperadamente.
142
- - Invocar siempre con `useModalManager` desde `lkd-web-kit`, nunca importando el modal directo desde una vista:
143
-
144
- ```tsx
145
- import { useModalManager } from "lkd-web-kit";
146
-
147
- const { showModal, closeModal } = useModalManager();
148
- showModal("domain.myModal", { itemId: "123" });
149
- closeModal("domain.myModal");
150
- ```
151
-
152
- ## Formularios Dentro de Modales
153
-
154
- - Usar la skill `rhf-lkd-forms` si el modal contiene formulario.
155
- - Pasar `onSuccess={modalProps.onClose}` o cerrar en el submit exitoso.
156
- - En errores de API, mostrar la alerta esperada y luego hacer `throw error`.
157
- - No poner mensajes textuales en reglas base de Zod.
158
-
159
- ## Checklist
160
-
161
- - El modal exporta default envuelto con `withModalManager`.
162
- - Las props publicas estan exportadas y registradas en `dynamicModals`.
163
- - `showModal("key", props)` queda tipado sin `any`.
164
- - `useModalManager` se importa desde `lkd-web-kit`.
165
- - La ruta esta bajo `PageProviders` o `MyModalManagerProvider`.
166
- - `loadModals` se agrega solo cuando conviene precargar.
167
- - Se reutiliza el modal interno del proyecto salvo necesidad concreta de Mantine directo.
168
- - Se ejecuta una verificacion focalizada si el cambio no es trivial.
@@ -1,4 +0,0 @@
1
- interface:
2
- display_name: "Create Modal Component"
3
- short_description: "Create project modals with manager registration."
4
- default_prompt: "Use $create-modal-component to create a modal following this project's modal manager pattern."
@@ -1,41 +0,0 @@
1
- ---
2
- name: create-svg-icon
3
- description: Create SVG icon files in projects that expose SVGs from src/icons. Use when Codex must add a new icon under src/icons from user-provided SVG markup, normalize SVG colors to currentColor for Tailwind text-* styling, and export the icon alias from src/icons/index.ts.
4
- ---
5
-
6
- # Create SVG Icon
7
-
8
- Use this skill when the user provides SVG markup and the desired icon name, usually in the form `Icon{Name}`.
9
-
10
- ## Required Workflow
11
-
12
- 1. Read `src/icons/index.ts` before editing.
13
- 2. Determine the component export name from the user input.
14
- - Expected format: `Icon{Name}`.
15
- - Keep the export alias with the `Icon` prefix.
16
- 3. Verify the icon does not already exist.
17
- - Check for the exact alias in `src/icons/index.ts`.
18
- - Check for the target SVG filename in `src/icons/`.
19
- - If either exists, cancel the operation and notify the user.
20
- 4. Build the SVG filename.
21
- - Remove the leading `Icon` prefix.
22
- - Convert the remaining name to kebab-case.
23
- - Save it as `src/icons/{name}.svg`.
24
- - Example: `IconBuildingTower` -> `src/icons/building-tower.svg`.
25
- 5. Normalize the provided SVG.
26
- - Replace every explicit visual color value with `currentColor`.
27
- - Include colors expressed as hex, rgb(), rgba(), hsl(), hsla(), named colors, or inline style values.
28
- - Apply this to attributes such as `fill`, `stroke`, `color`, `stop-color`, and CSS declarations inside `style`.
29
- - Preserve `fill="none"`, `stroke="none"`, `currentColor`, `transparent`, masks, clipping, sizing, viewBox, paths, and structural SVG attributes.
30
- - Do not convert opacity values to `currentColor`.
31
- 6. Create the SVG file in `src/icons/`.
32
- 7. Add the alias in `src/icons/index.ts` following the existing export style in that file.
33
- 8. Report the created SVG path and the added export alias.
34
-
35
- ## Guardrails
36
-
37
- - Do not use `any`.
38
- - Do not create React wrapper components for the icon unless the existing icon system requires it.
39
- - Do not overwrite an existing icon file or alias.
40
- - Do not invent SVG path data; use the SVG supplied by the user.
41
- - Keep edits scoped to `src/icons/{name}.svg` and `src/icons/index.ts` unless the user asks for something else.
@@ -1,3 +0,0 @@
1
- display_name: Create SVG Icon
2
- short_description: Create project SVG icons with currentColor and index exports.
3
- default_prompt: Create an SVG icon for this project from the SVG markup and icon name I provide.