create-kerf-component 5.0.0-beta.7 → 5.0.0-beta.70

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.
package/README.md CHANGED
@@ -11,6 +11,8 @@ npm create kerf-component@latest my-widgets
11
11
  cd my-widgets
12
12
  npm install
13
13
  npm run build
14
+ npm run catalog:check
15
+ npm run check:styles
14
16
  ```
15
17
 
16
18
  Run it with **no argument** (`npm create kerf-component`) and it prompts for the
@@ -20,7 +22,7 @@ directory's basename is used as the package name.
20
22
  ## What you get
21
23
 
22
24
  A ready-to-publish component package that encodes the rules from the kerf docs
23
- (*Building reusable component packages*):
25
+ (_Building reusable component packages_):
24
26
 
25
27
  - **`kerfjs` as a `peerDependency`, `external` in the tsup build** — never
26
28
  bundled, so `isSafeHtml` brand checks and signal identity stay intact across
@@ -35,6 +37,57 @@ A ready-to-publish component package that encodes the rules from the kerf docs
35
37
  component needs:
36
38
  - **per-instance state via a factory + props** (`createCounter` → `<Counter store={…} />`), and
37
39
  - **a `wire(root)` delegation disposer** (`wireCounter`) instead of inline event handlers.
40
+ - **A stylesheet that owns only its component** (`src/counter.css`, exported as
41
+ `./counter.css`): it styles `.kerf-counter` and its own internals, writes only
42
+ `--_kerf-counter-*` private variables (the context it gives its buttons is
43
+ named after Counter), exposes a typed `size` prop and one public token
44
+ (`--kerf-counter-gap`) as its configuration, and adapts itself inside a Kerf
45
+ UI Toolbar from its own stylesheet (`.kui-toolbar .kerf-counter`). `npm run
46
+ check:styles` runs `kerf-ui-analyze` (from the `@kerfjs/ui` dev dependency)
47
+ over `src/`, so a rule that restyles another package's component, touches
48
+ its private variables, overrides a token a typed prop sets, or uses a hook
49
+ class (`KUI-L019`–`KUI-L022`) fails before `prepublishOnly` publishes.
50
+ - **Author-owned AI metadata** in `kerf.components.json`, with explicit purpose,
51
+ exports, composition, geometry, public `rootClass`, tokens, accessibility,
52
+ and source links. Run
53
+ `npm run catalog:generate` to emit the package-qualified
54
+ `component-composition.json`; `npm run catalog:check` fails on drift, deleted
55
+ sources, renamed exports, duplicate ids, an omitted author decision, or any
56
+ source/output field that violates the shipped schemas. Export verification
57
+ uses the TypeScript/TSX syntax tree, so JSX text, nested scopes, comments, and
58
+ string/template/regular-expression literals cannot masquerade as public
59
+ exports. The scaffold already declares TypeScript; run `npm install` before
60
+ invoking its copied local checker in a fresh offline directory.
61
+ A component whose wiring helper writes runtime `data-*` state onto its DOM
62
+ can declare it under `composition.wiring.stateAttributes` — each item is
63
+ `{ name, on, helper, meaning }`, where `name` is a `data-*` name, `on` is the
64
+ element that carries it, and `helper` is one of `wiring.helpers`. Apps must
65
+ not render, remove, or treat those attributes as their own state. The field
66
+ is optional; names must be unique per component, and the checker rejects a
67
+ helper that is not listed in `wiring.helpers`.
68
+ `boundaries.placeableClasses` (optional) names the public classes an app may
69
+ write onto its own elements; every other public class is the component's
70
+ rendered anatomy, which `eslint-plugin-kerfjs` reports on an app-owned
71
+ element as `KUI-L103` with the component to render. `boundaries.rootElement`
72
+ names the element the component itself renders around its placeable classes,
73
+ so a plain element of that tag carrying them is reported too. Placeable
74
+ classes must be public; `rootElement` requires them.
75
+ A wrapper that renders a cataloged component declares it under
76
+ `composition.rendersAs` (for example
77
+ `["@kerfjs/ui:toolbar-control-group"]`), so the `ui-composition` lint treats
78
+ it as that root. Every key must resolve to an entry generated in the same run
79
+ or to an installed package's catalog.
80
+ Each `publicExports` item names a `package.json#exports` subpath that maps to
81
+ the `src/` file exporting it. A private, bundled application
82
+ (`package.json#private: true`) has no per-file `dist/` entries and is never
83
+ imported by package name, so its items may omit `subpath`
84
+ (`{ "name": "DemandSegmentsControl" }`); the checker then verifies the name
85
+ against the component's `source` file, which is how the UI lint resolves the
86
+ wrapper. A subpath it does declare is still checked against `exports`.
87
+ `private: true` is the only opt-in: a `.kerf-ui-profile.json` `scope` does
88
+ not change this. An application that is published to npm (an app shell), or
89
+ whose manifest omits `private`, either declares a real `subpath` for each
90
+ item or sets `"private": true`.
38
91
 
39
92
  ## Layout produced
40
93
 
@@ -43,13 +96,32 @@ my-widgets/
43
96
  ├── package.json # peerDependencies.kerfjs, exports map, publish files
44
97
  ├── tsconfig.json # jsxImportSource: "kerfjs"
45
98
  ├── tsup.config.ts # external: ['kerfjs'], format esm, dts
99
+ ├── kerf.components.json # explicit source metadata (never inferred from pixels)
100
+ ├── component-composition.json # deterministic generated AI catalog
101
+ ├── scripts/
102
+ │ ├── kerf-component-catalog.mjs # local generator + check mode
103
+ │ ├── component-metadata.schema.json # author-source schema used by the checker
104
+ │ └── component-composition.schema.json # emitted-catalog schema used by the checker
46
105
  ├── LICENSE # MIT license with the package contributor notice
47
106
  ├── .gitignore
48
107
  ├── README.md
49
108
  └── src/
50
109
  ├── index.ts # public barrel
51
- └── counter.tsx # factory + component + wire() disposer
110
+ ├── counter.tsx # factory + component + wire() disposer
111
+ └── counter.css # styles only Counter; configured by props and tokens
52
112
  ```
53
113
 
54
114
  This package is part of the kerf repository and releases in lockstep with
55
- `kerfjs`.
115
+ `kerfjs`. The 5.0.0 template targets `kerfjs` and `@kerfjs/ui` on the 5.x
116
+ line; the generated package keeps Kerf as a peer dependency and uses UI only
117
+ for its authoring checks.
118
+
119
+ The package also exposes `kerf-component-catalog`. It accepts `--write` (the
120
+ default), `--check`, and `--root <path>`. A root package with npm `workspaces`
121
+ generates every child package that declares `package.json#kerfComponentCatalog`,
122
+ in deterministic package and component order.
123
+
124
+ Application projects do not need this package scaffold. `npx kerfjs setup
125
+ --ui` creates an empty, schema-valid author metadata file, wires this catalog
126
+ command, and publishes the generated app catalog through the workspace UI
127
+ profile.