purity-mcp 0.0.0-stage → 2.0.0

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 (66) hide show
  1. package/README.md +252 -2
  2. package/dist/data/component-catalog.d.ts +3 -0
  3. package/dist/data/component-catalog.d.ts.map +1 -0
  4. package/dist/data/component-catalog.js +330 -0
  5. package/dist/data/component-catalog.js.map +1 -0
  6. package/dist/data/documentation.d.ts +10 -0
  7. package/dist/data/documentation.d.ts.map +1 -0
  8. package/dist/data/documentation.js +617 -0
  9. package/dist/data/documentation.js.map +1 -0
  10. package/dist/data/templates.d.ts +11 -0
  11. package/dist/data/templates.d.ts.map +1 -0
  12. package/dist/data/templates.js +633 -0
  13. package/dist/data/templates.js.map +1 -0
  14. package/dist/index.d.ts +7 -0
  15. package/dist/index.d.ts.map +1 -0
  16. package/dist/index.js +62 -0
  17. package/dist/index.js.map +1 -0
  18. package/dist/prompts/index.d.ts +3 -0
  19. package/dist/prompts/index.d.ts.map +1 -0
  20. package/dist/prompts/index.js +153 -0
  21. package/dist/prompts/index.js.map +1 -0
  22. package/dist/resources/index.d.ts +3 -0
  23. package/dist/resources/index.d.ts.map +1 -0
  24. package/dist/resources/index.js +177 -0
  25. package/dist/resources/index.js.map +1 -0
  26. package/dist/server.d.ts +3 -0
  27. package/dist/server.d.ts.map +1 -0
  28. package/dist/server.js +108 -0
  29. package/dist/server.js.map +1 -0
  30. package/dist/tools/components.tool.d.ts +34 -0
  31. package/dist/tools/components.tool.d.ts.map +1 -0
  32. package/dist/tools/components.tool.js +41 -0
  33. package/dist/tools/components.tool.js.map +1 -0
  34. package/dist/tools/docs.tool.d.ts +44 -0
  35. package/dist/tools/docs.tool.d.ts.map +1 -0
  36. package/dist/tools/docs.tool.js +60 -0
  37. package/dist/tools/docs.tool.js.map +1 -0
  38. package/dist/tools/inspect.tool.d.ts +9 -0
  39. package/dist/tools/inspect.tool.d.ts.map +1 -0
  40. package/dist/tools/inspect.tool.js +204 -0
  41. package/dist/tools/inspect.tool.js.map +1 -0
  42. package/dist/tools/scaffold.tool.d.ts +28 -0
  43. package/dist/tools/scaffold.tool.d.ts.map +1 -0
  44. package/dist/tools/scaffold.tool.js +56 -0
  45. package/dist/tools/scaffold.tool.js.map +1 -0
  46. package/dist/tools/transform.tool.d.ts +9 -0
  47. package/dist/tools/transform.tool.d.ts.map +1 -0
  48. package/dist/tools/transform.tool.js +9 -0
  49. package/dist/tools/transform.tool.js.map +1 -0
  50. package/dist/tools/validate.tool.d.ts +13 -0
  51. package/dist/tools/validate.tool.d.ts.map +1 -0
  52. package/dist/tools/validate.tool.js +53 -0
  53. package/dist/tools/validate.tool.js.map +1 -0
  54. package/dist/types.d.ts +105 -0
  55. package/dist/types.d.ts.map +1 -0
  56. package/dist/types.js +5 -0
  57. package/dist/types.js.map +1 -0
  58. package/dist/utils/code-analyzer.d.ts +3 -0
  59. package/dist/utils/code-analyzer.d.ts.map +1 -0
  60. package/dist/utils/code-analyzer.js +282 -0
  61. package/dist/utils/code-analyzer.js.map +1 -0
  62. package/dist/utils/template-converter.d.ts +12 -0
  63. package/dist/utils/template-converter.d.ts.map +1 -0
  64. package/dist/utils/template-converter.js +158 -0
  65. package/dist/utils/template-converter.js.map +1 -0
  66. package/package.json +45 -4
@@ -0,0 +1,617 @@
1
+ export const DOCUMENTATION = {
2
+ overview: {
3
+ topic: 'overview',
4
+ title: 'Purity Framework Overview',
5
+ summary: 'Lightweight native TypeScript frontend framework built on Custom Elements v1 and fine-grained synchronous signals.',
6
+ content: `# Purity Framework
7
+
8
+ Purity is a zero-dependency, native TypeScript framework designed for sub-microsecond reactive performance, clean modular architecture, and modern Web standards.
9
+
10
+ ## Key Pillars
11
+ 1. **Synchronous Fine-Grained Signals**: Built-in \`signal()\`, \`computed()\`, \`effect()\`, and \`untrack()\` with automatic dependency tracking.
12
+ 2. **Native Custom Elements v1**: Decorated with \`@Component\`, compiling external templates synchronously at build time via Vite (\`?raw\`).
13
+ 3. **Structural Directives**: \`for="let item of items"\`, \`virtual-for="let item, index of items; itemHeight: 48; buffer: 8; height: 420px; scrollIndex: jumpSignal"\`, \`if="expr"\`, \`else-if="expr"\`, \`else\`.
14
+ 4. **Dependency Injection**: First-class container with \`@Injectable('ServiceName')\` and \`inject(Token)\`.
15
+ 5. **KDE Plasma Breeze Vector Cursors**: 91 vector cursors with ref-counted animated progress state during network requests.
16
+ 6. **Adwaita Glassmorphism**: Translucent surfaces, refined corner radii hierarchy, and modular SCSS (\`@use '@styles' as *;\`).`,
17
+ examples: [
18
+ `import { bootstrapApplication } from '@purity/core';
19
+ import { AppComponent } from './app/app.component';
20
+
21
+ bootstrapApplication({
22
+ rootComponent: AppComponent,
23
+ providers: []
24
+ });`
25
+ ]
26
+ },
27
+ signals: {
28
+ topic: 'signals',
29
+ title: 'Fine-Grained Reactive Signals',
30
+ summary: 'Synchronous signal primitives with getter read syntax and atomic updates.',
31
+ content: `# Reactive Signals in Purity
32
+
33
+ Signals are the reactive core of Purity. They execute synchronously without Virtual DOM diffing, triggering atomic mutations directly on targeted DOM Text nodes or element attributes.
34
+
35
+ ## Core Functions
36
+ - \`signal<T>(initialValue: T): Signal<T>\`: Mutable state container. Read via \`mySignal()\`, mutate via \`mySignal.set(val)\` or \`mySignal.update(prev => next)\`.
37
+ - \`computed<T>(fn: () => T): ReadonlySignal<T>\`: Derived memoized signal. Recalculates only when dependencies change.
38
+ - \`effect(fn: () => void): void\`: Side-effect runner. Captures all accessed signals and re-executes synchronously on change.
39
+ - \`untrack<T>(fn: () => T): T\`: Runs code without subscribing the current effect to any signal reads inside it.
40
+
41
+ ## Critical Rules
42
+ - NEVER assign directly: \`count = 5\` or \`count.value = 5\` (wrong!). Use \`count.set(5)\`.
43
+ - ALWAYS invoke the getter in templates and functions: \`count()\` (or \`{{ count() }}\`).
44
+ - NEVER import RxJS, Redux, or external state libraries.`,
45
+ examples: [
46
+ `import { signal, computed, effect, untrack } from '@purity/core';
47
+
48
+ const count = signal(0);
49
+ const doubled = computed(() => count() * 2);
50
+
51
+ effect(() => {
52
+ console.log('Count changed:', count());
53
+ untrack(() => {
54
+ // Reads here do not become dependencies
55
+ });
56
+ });
57
+
58
+ count.set(5); // Logs: Count changed: 5
59
+ count.update(n => n + 1); // Logs: Count changed: 6`
60
+ ]
61
+ },
62
+ components: {
63
+ topic: 'components',
64
+ title: 'Native Custom Elements (@Component)',
65
+ summary: 'Transform plain classes into custom elements with template inlining and lifecycle management.',
66
+ content: `# Purity Components
67
+
68
+ Components in Purity are standard TypeScript classes decorated with \`@Component\`.
69
+
70
+ ## Decorator Options
71
+ - \`selector?: string\`: Custom element tag (kebab-case, e.g. \`user-card\`). If omitted, inferred from class name.
72
+ - \`templateUrl?: string\`: Path to HTML template. Inlined at build time by Vite (\`?raw\`).
73
+ - \`template?: string\`: Inline template string.
74
+
75
+ ## Lifecycle Hooks
76
+ - \`protected onInit(): void\`: Invoked after DOM mounting and template bindings are initialized.
77
+ - \`protected onDestroy(): void\`: Invoked when element is removed from DOM.
78
+ - \`disconnectedCallback(): void\`: Native custom element cleanup.
79
+
80
+ ## Queries
81
+ - \`@ViewChild(selector?: string)\`: Injects reference to child custom element or DOM element. Inferred from property name if selector is omitted.`,
82
+ examples: [
83
+ `import { Component, signal, ViewChild } from '@purity/core';
84
+ import { SwitchButtonComponent } from '@components/switch-button/switch-button.component';
85
+
86
+ @Component({
87
+ selector: 'user-profile',
88
+ templateUrl: './user-profile.component.html'
89
+ })
90
+ export class UserProfileComponent {
91
+ @ViewChild()
92
+ switchButton?: SwitchButtonComponent;
93
+
94
+ username = signal('Ada');
95
+
96
+ protected onInit() {
97
+ console.log('Mounted:', this.username());
98
+ }
99
+
100
+ protected onDestroy() {
101
+ console.log('Destroyed');
102
+ }
103
+ }`
104
+ ]
105
+ },
106
+ templates: {
107
+ topic: 'templates',
108
+ title: 'Template Bindings and Expressions',
109
+ summary: 'Handlebars interpolations, dynamic attributes, and event handlers.',
110
+ content: `# Template Bindings
111
+
112
+ Purity compiles templates into fine-grained reactive bindings.
113
+
114
+ ## Syntax
115
+ - Interpolation: \`{{ expression }}\`
116
+ - Pipes: \`{{ value | pipeName: arg1 : arg2 }}\`
117
+ - Attribute Bindings: \`checked="{{ isActive() }}"\` or \`title="{{ user.name }}"\`
118
+ - Event Listeners: \`onclick="handleClick()"\`, \`oninput="handleInput($event)"\` (methods evaluate on component instance)
119
+ - Dynamic code blocks: Standalone \`<code>\` and \`<pre>\` evaluate bindings unless marked with \`[data-no-bind]\`.`,
120
+ examples: [
121
+ `<div class="card">
122
+ <h3>{{ title() }}</h3>
123
+ <p>{{ balance() | currency: 'USD' }}</p>
124
+ <button class="button-primary" onclick="deposit(100)">Add Funds</button>
125
+ </div>`
126
+ ]
127
+ },
128
+ repeaters: {
129
+ topic: 'repeaters',
130
+ title: 'Structural Repeater (for="let item of items")',
131
+ summary: 'Fine-grained array iteration with seamless custom element interoperability.',
132
+ content: `# Structural Repeater
133
+
134
+ The \`for\` directive allows iterating over arrays and array signals.
135
+
136
+ ## Syntax
137
+ - \`for="let item of items"\`
138
+ - \`for="let item, index of items"\` (index starts at 0)
139
+
140
+ ## Custom Component Interoperability
141
+ - Structural repeaters fully interoperate with nested custom Web Components (\`<switch-button>\`, \`<expander>\`, etc.).
142
+ - Context proxy chaining (\`createComponentContext\`) allows access to row variables (\`item\`, \`index\`, \`$first\`, \`$last\`) inside custom element templates and slots.
143
+ - Safe signal attribute synchronization ensures child signals are updated via \`.set()\` rather than overwritten.
144
+ - Untracked attribute side-effects prevent circular re-render loops.`,
145
+ examples: [
146
+ `<!-- Standard array repeater -->
147
+ <div for="let user, index of users" class="user-row">
148
+ <span>#{{ index + 1 }} {{ user.name }}</span>
149
+ <switch-button checked="{{ user.isActive }}"></switch-button>
150
+ </div>
151
+
152
+ <!-- Direct repeater on custom element -->
153
+ <expander for="let faq of faqList" title="{{ faq.question }}">
154
+ <p>{{ faq.answer }}</p>
155
+ </expander>`
156
+ ]
157
+ },
158
+ 'virtual-for': {
159
+ topic: 'virtual-for',
160
+ title: 'Virtualized Repeater (virtual-for)',
161
+ summary: 'High-performance virtual scrolling for 1,000 to 100,000+ items.',
162
+ content: `# High-Performance Virtual Scrolling
163
+
164
+ Purity includes a GPU-accelerated virtual scrolling engine for massive datasets.
165
+
166
+ ## Syntax
167
+ \`virtual-for="let item, index of items; itemHeight: 48; buffer: 8; height: 420px; scrollIndex: jumpSignal"\`
168
+
169
+ ## Attributes & Parameters
170
+ - \`itemHeight\`: Height of each item in pixels (numeric).
171
+ - \`buffer\`: Overscan items above and below the viewport (default: 5).
172
+ - \`height\`: Viewport container height (e.g. \`420px\`, \`100%\`).
173
+ - \`scrollIndex\`: Optional reactive signal. Setting this signal jumps the viewport to the target index smoothly.`,
174
+ examples: [
175
+ `<div class="virtual-list-container">
176
+ <div
177
+ virtual-for="let txn, index of transactions; itemHeight: 52; buffer: 6; height: 440px; scrollIndex: jumpTarget"
178
+ class="txn-row"
179
+ >
180
+ <span>#{{ index + 1 }} - {{ txn.title }}</span>
181
+ <strong>{{ txn.amount | currency }}</strong>
182
+ </div>
183
+ </div>`
184
+ ]
185
+ },
186
+ conditionals: {
187
+ topic: 'conditionals',
188
+ title: 'Structural Conditionals (if, else-if, else)',
189
+ summary: 'Declarative multi-branch conditional rendering with deferred compilation.',
190
+ content: `# Structural Conditionals
191
+
192
+ Purity provides lazy, multi-branch conditional rendering:
193
+ - \`if="expr"\`
194
+ - \`else-if="expr"\`
195
+ - \`else\`
196
+
197
+ ## Deferred Compilation Guard
198
+ Falsy branches are completely excluded from the live DOM and will **not build, compile, or execute bindings or child component lifecycles** until their condition evaluates to truthy.`,
199
+ examples: [
200
+ `<div if="role() === 'admin'" class="admin-panel">
201
+ <admin-dashboard></admin-dashboard>
202
+ </div>
203
+ <div else-if="role() === 'editor'" class="editor-panel">
204
+ <editor-tools></editor-tools>
205
+ </div>
206
+ <div else class="guest-panel">
207
+ <p>Please log in to continue.</p>
208
+ </div>`
209
+ ]
210
+ },
211
+ slots: {
212
+ topic: 'slots',
213
+ title: 'Content Projection (<slot>)',
214
+ summary: 'Declarative content projection with default and named slots.',
215
+ content: `# Content Projection with Slots
216
+
217
+ Purity components support native \`<slot>\` projection.
218
+
219
+ ## Rules
220
+ - Default slot: \`<slot></slot>\` or \`<slot>Default fallback</slot>\`
221
+ - Named slots: \`<slot name="header"></slot>\`, \`<slot name="footer"></slot>\`
222
+ - Slotted content retains reactive bindings to its parent context.`,
223
+ examples: [
224
+ `<!-- Component template -->
225
+ <div class="card">
226
+ <header><slot name="header"></slot></header>
227
+ <main><slot>Default body</slot></main>
228
+ </div>
229
+
230
+ <!-- Usage -->
231
+ <user-card>
232
+ <h2 slot="header">Ada Lovelace</h2>
233
+ <p>Computer Programmer</p>
234
+ </user-card>`
235
+ ]
236
+ },
237
+ di: {
238
+ topic: 'di',
239
+ title: 'Dependency Injection (@Injectable & inject)',
240
+ summary: 'Container-managed singleton services and token resolution.',
241
+ content: `# Dependency Injection
242
+
243
+ Purity includes a built-in DI container.
244
+
245
+ ## Decorators & Resolution
246
+ - \`@Injectable('ServiceName')\` or \`@Service('ServiceName')\`
247
+ - Resolve with \`inject(ServiceName)\` or \`inject<Type>('TokenName')\`
248
+ - Services can hold reactive state (\`signal\`) and methods.`,
249
+ examples: [
250
+ `import { Injectable, signal, inject } from '@purity/core';
251
+
252
+ @Injectable('UserService')
253
+ export class UserService {
254
+ currentUser = signal({ name: 'Ada', role: 'admin' });
255
+
256
+ updateName(name: string) {
257
+ this.currentUser.update(u => ({ ...u, name }));
258
+ }
259
+ }
260
+
261
+ // In component:
262
+ export class ProfileComponent {
263
+ userService = inject(UserService);
264
+ }`
265
+ ]
266
+ },
267
+ http: {
268
+ topic: 'http',
269
+ title: 'HTTP Client & Interceptor Pipeline',
270
+ summary: 'Full-featured HTTP client driving the KDE Breeze progress cursor engine.',
271
+ content: `# HTTP Client
272
+
273
+ The \`HttpClient\` service provides standard methods (\`get\`, \`post\`, \`put\`, \`patch\`, \`delete\`, \`head\`, \`options\`) and reactive resource helper \`createResource\`.
274
+
275
+ ## Breeze Progress Cursor
276
+ Pending requests automatically increment a reference counter driving the 23-frame animated KDE Plasma Breeze progress cursor engine on \`<body>\`.
277
+
278
+ ## Centralized Interceptors
279
+ Interceptors implement \`HttpInterceptor\` and reside in \`src/app/shared/interceptors/\` (aliased as \`@interceptors/*\`). Wired during bootstrap:
280
+ \`bootstrapApplication({ interceptors: [AuthInterceptor, LoggingInterceptor] })\`.`,
281
+ examples: [
282
+ `import { HttpClient, inject } from '@purity/core';
283
+
284
+ export class PostService {
285
+ private http = inject(HttpClient);
286
+
287
+ getPosts() {
288
+ return this.http.get<Post[]>('https://api.example.com/posts');
289
+ }
290
+ }`
291
+ ]
292
+ },
293
+ interceptors: {
294
+ topic: 'interceptors',
295
+ title: 'Centralized HTTP Interceptors',
296
+ summary: 'Class-based request/response transformation pipeline.',
297
+ content: `# HTTP Interceptors
298
+
299
+ Interceptors handle cross-cutting network concerns (auth tokens, latency logging, error handling).
300
+
301
+ ## Rules
302
+ - Implement \`HttpInterceptor\` interface.
303
+ - Provide method: \`intercept(req: HttpRequest, next: HttpHandler): Promise<HttpResponse>\`.
304
+ - Must be located in \`@interceptors/*\`.`,
305
+ examples: [
306
+ `import { HttpInterceptor, HttpRequest, HttpHandler, HttpResponse } from '@purity/core';
307
+
308
+ export class AuthInterceptor implements HttpInterceptor {
309
+ async intercept(req: HttpRequest, next: HttpHandler): Promise<HttpResponse> {
310
+ const authReq = req.clone({
311
+ headers: req.headers.set('Authorization', 'Bearer token_xyz')
312
+ });
313
+ return next.handle(authReq);
314
+ }
315
+ }`
316
+ ]
317
+ },
318
+ pipes: {
319
+ topic: 'pipes',
320
+ title: 'Transform Pipes (@Pipe & BasePipe)',
321
+ summary: 'Reusable template data formatting engine.',
322
+ content: `# Transform Pipes
323
+
324
+ Pipes format values inside Handlebars interpolations: \`{{ value | pipeName: arg1 : arg2 }}\`.
325
+
326
+ ## Rules
327
+ - Extend \`BasePipe\`.
328
+ - Decorate with \`@Pipe('pipeName')\`.
329
+ - Implement \`transform(value: any, ...args: any[]): any\`.
330
+ - Supports dynamic reactive signal arguments.`,
331
+ examples: [
332
+ `import { Pipe, BasePipe } from '@purity/core';
333
+
334
+ @Pipe('truncate')
335
+ export class TruncatePipe extends BasePipe {
336
+ transform(value: string, limit = 20, ellipsis = '...'): string {
337
+ if (!value || value.length <= limit) return value;
338
+ return value.substring(0, limit) + ellipsis;
339
+ }
340
+ }`
341
+ ]
342
+ },
343
+ directives: {
344
+ topic: 'directives',
345
+ title: 'Custom Directives (@Directive & BaseDirective)',
346
+ summary: 'Attribute-level reactivity and DOM augmentation.',
347
+ content: `# Custom Directives
348
+
349
+ Directives augment DOM elements with custom behavior.
350
+
351
+ ## Rules
352
+ - Extend \`BaseDirective\`.
353
+ - Decorate with \`@Directive('[directiveName]')\`.
354
+ - Implement lifecycles: \`onInit()\`, \`onChanges(newValue, oldValue)\`, \`onDestroy()\`.`,
355
+ examples: [
356
+ `import { Directive, BaseDirective } from '@purity/core';
357
+
358
+ @Directive('[tooltip]')
359
+ export class TooltipDirective extends BaseDirective {
360
+ protected onInit() {
361
+ this.el.title = this.value || '';
362
+ }
363
+
364
+ protected onChanges(newVal: string) {
365
+ this.el.title = newVal || '';
366
+ }
367
+ }`
368
+ ]
369
+ },
370
+ validators: {
371
+ topic: 'validators',
372
+ title: 'Decoupled Form Validation (@Validator)',
373
+ summary: 'Decoupled form/field validation engine with automatic CSS state management.',
374
+ content: `# Form & Field Validation
375
+
376
+ Validators decouple validation logic from component classes.
377
+
378
+ ## Features
379
+ - Extend \`BaseValidator\`.
380
+ - Decorate with \`@Validator({ form: 'selector', fields: { ... } })\`.
381
+ - Automatically toggles CSS classes (\`.is-valid\`, \`.is-invalid\`, \`.is-touched\`, \`.is-dirty\`).
382
+ - Automatically toggles submit button \`disabled\` state.`,
383
+ examples: [
384
+ `import { Validator, BaseValidator } from '@purity/core';
385
+
386
+ @Validator({
387
+ form: '#loginForm',
388
+ fields: {
389
+ email: ['required', 'email'],
390
+ password: ['required', 'minLength:8']
391
+ }
392
+ })
393
+ export class LoginValidator extends BaseValidator {}`
394
+ ]
395
+ },
396
+ behaviors: {
397
+ topic: 'behaviors',
398
+ title: 'Composable Behaviors (@behaviors/*)',
399
+ summary: 'Modular pointer interactions (drag, drop, resize) without class inheritance.',
400
+ content: `# Composable Behaviors
401
+
402
+ Behaviors are modular interaction helpers that attach cleanly inside \`onInit()\` and return a cleanup function.
403
+
404
+ ## Available Behaviors
405
+ - \`drag(element, options)\`: Pointer drag with boundary constraints and snap.
406
+ - \`droppable(element, options)\`: Drop target registration.
407
+ - \`resizable(element, options)\`: Adwaita corner handles with KDE Breeze cursors.`,
408
+ examples: [
409
+ `import { Component } from '@purity/core';
410
+ import { drag } from '@behaviors/draggable/draggable';
411
+
412
+ @Component({ selector: 'floating-card' })
413
+ export class FloatingCard {
414
+ private cleanup?: { destroy(): void };
415
+
416
+ protected onInit() {
417
+ this.cleanup = drag(this, { snap: 20 });
418
+ }
419
+
420
+ protected onDestroy() {
421
+ this.cleanup?.destroy();
422
+ }
423
+ }`
424
+ ]
425
+ },
426
+ router: {
427
+ topic: 'router',
428
+ title: 'Signal Router (<router-layout>)',
429
+ summary: 'Native routing with URL signal synchronization and route guards.',
430
+ content: `# Signal Router
431
+
432
+ Purity includes a native client-side router.
433
+
434
+ ## Features
435
+ - \`<router-layout>\`: Container element mounting matched route components.
436
+ - \`routerLink\`: Directive for reactive link navigation: \`<a routerLink="/about">About</a>\`.
437
+ - \`Router\` service: \`navigate(path)\`, \`currentRoute()\` signal.
438
+ - Automated SEO sync via \`SeoService\`.`,
439
+ examples: [
440
+ `import { Router, Route } from '@purity/core';
441
+
442
+ export const routes: Route[] = [
443
+ { path: '/', component: HomeComponent },
444
+ { path: '/profile', component: ProfileComponent }
445
+ ];`
446
+ ]
447
+ },
448
+ seo: {
449
+ topic: 'seo',
450
+ title: 'SEO Subsystem (SeoService & MetaService)',
451
+ summary: 'Dynamic metadata, OpenGraph, Twitter Cards, and JSON-LD structured data.',
452
+ content: `# SEO Subsystem
453
+
454
+ Automated head metadata management.
455
+
456
+ ## Methods
457
+ - \`setTitle(title)\`: Updates document title.
458
+ - \`setDescription(desc)\`: Sets meta description.
459
+ - \`setCanonicalUrl(url)\`: Manages \`<link rel="canonical">\`.
460
+ - \`setOpenGraph(og)\`: Sets og:title, og:image, og:description.
461
+ - \`setJsonLd(schema)\`: Injects Schema.org JSON-LD structured data.`,
462
+ examples: [
463
+ `import { SeoService, inject } from '@purity/core';
464
+
465
+ export class ProductPage {
466
+ private seo = inject(SeoService);
467
+
468
+ protected onInit() {
469
+ this.seo.setTitle('Product Details - Purity');
470
+ this.seo.setDescription('High-performance reactive frontend framework.');
471
+ }
472
+ }`
473
+ ]
474
+ },
475
+ 'design-system': {
476
+ topic: 'design-system',
477
+ title: 'Adwaita Glassmorphic Design System',
478
+ summary: 'Surfaces, frosted blur, corner radii hierarchy, and modular SCSS tokens.',
479
+ content: `# Adwaita Design System
480
+
481
+ Purity strictly follows Adwaita glassmorphic design standards.
482
+
483
+ ## Corner Radii Hierarchy
484
+ - Windows & top containers: \`var(--radius-window, 16px)\`
485
+ - Inner cards, dialog panels: \`var(--radius-card, 12px)\`
486
+ - Controls (buttons, inputs): \`var(--radius-control, 8px)\`
487
+ - Pills, badges, chips: \`var(--radius-pill, 999px)\`
488
+
489
+ ## Surfaces & Colors
490
+ - Surfaces: \`var(--gnome-surface)\`, \`var(--gnome-card)\`
491
+ - Specular borders: \`var(--gnome-border)\`
492
+ - Frosted blur: \`var(--blur-effect)\`
493
+ - Accent: \`var(--color-primary)\`
494
+
495
+ ## INTERNAL RULE
496
+ "GNOME 50" is an internal design reference between developer and agents. NEVER output the string "GNOME 50" in user-facing UI copy or public documentation. Describe as "Adwaita" or glassmorphic design tokens.`,
497
+ examples: [
498
+ `@use '@styles' as *;
499
+
500
+ .my-card {
501
+ background: var(--gnome-card);
502
+ backdrop-filter: var(--blur-effect);
503
+ border: 1px solid var(--gnome-border);
504
+ border-radius: var(--radius-card);
505
+ padding: 16px;
506
+ }`
507
+ ]
508
+ },
509
+ cursors: {
510
+ topic: 'cursors',
511
+ title: 'KDE Plasma Breeze Cursor System',
512
+ summary: 'Vector SVG cursor hierarchy and animated progress engine.',
513
+ content: `# KDE Plasma Breeze Cursors
514
+
515
+ All components use KDE Plasma Breeze cursor tokens.
516
+
517
+ ## Tokens
518
+ - \`var(--cursor-default)\`: Standard arrow
519
+ - \`var(--cursor-pointer)\`: Pointer hand for clickable items
520
+ - \`var(--cursor-text)\`: I-beam for text inputs
521
+ - \`var(--cursor-grab)\`: Open hand for draggable elements
522
+ - \`var(--cursor-grabbing)\`: Closed hand during active drag
523
+ - \`var(--cursor-not-allowed)\`: Prohibited / disabled state
524
+ - \`var(--cursor-progress)\`: Ref-counted animated spinner during pending HTTP requests`,
525
+ examples: [
526
+ `button {
527
+ cursor: var(--cursor-pointer, pointer);
528
+ }
529
+
530
+ .draggable-item {
531
+ cursor: var(--cursor-grab, grab);
532
+ &:active {
533
+ cursor: var(--cursor-grabbing, grabbing);
534
+ }
535
+ }`
536
+ ]
537
+ },
538
+ styling: {
539
+ topic: 'styling',
540
+ title: 'SCSS Architecture & Rules',
541
+ summary: 'Modular styling rules: @use "@styles" as *; and zero inline styles.',
542
+ content: `# Styling Rules in Purity
543
+
544
+ ## Mandatory Conventions
545
+ 1. **Always use modular SCSS**: Every component SCSS file must begin with:
546
+ \`@use '@styles' as *;\`
547
+ 2. **NEVER use inline styles**: Never write \`style="..."\` in HTML templates.
548
+ 3. **Use design tokens**: Avoid hardcoded hex colors or pixel radii. Use \`var(--radius-control)\`, \`var(--gnome-surface)\`, etc.
549
+ 4. **Theme support**: Respect Dark (default baseline) and Light modes via CSS variables.`,
550
+ examples: [
551
+ `// In user-card.component.scss:
552
+ @use '@styles' as *;
553
+
554
+ .card-container {
555
+ border-radius: var(--radius-card);
556
+ background: var(--gnome-surface);
557
+ border: 1px solid var(--gnome-border);
558
+ cursor: var(--cursor-default);
559
+ }`
560
+ ]
561
+ },
562
+ testing: {
563
+ topic: 'testing',
564
+ title: 'Testing Standards (Vitest & happy-dom)',
565
+ summary: 'Colocated unit tests verifying signals, components, and DOM lifecycles.',
566
+ content: `# Testing with Vitest
567
+
568
+ Purity uses Vitest paired with happy-dom for full Custom Elements v1 and DOM simulation.
569
+
570
+ ## Conventions
571
+ - Colocate \`*.spec.ts\` directly adjacent to source files.
572
+ - Test signals synchronously.
573
+ - Test Custom Element mount via \`document.createElement(selector)\`.
574
+ - Clean up test elements in \`afterEach\`.`,
575
+ examples: [
576
+ `import { describe, it, expect, beforeEach, afterEach } from 'vitest';
577
+ import { signal } from '@purity/core';
578
+
579
+ describe('Signal Reactivity', () => {
580
+ it('updates synchronously', () => {
581
+ const s = signal(10);
582
+ s.set(20);
583
+ expect(s()).toBe(20);
584
+ });
585
+ });`
586
+ ]
587
+ },
588
+ rules: {
589
+ topic: 'rules',
590
+ title: 'Architectural Rules & Quality Checklist',
591
+ summary: '10 non-negotiable rules for all AI agents and developers working in Purity.',
592
+ content: `# Purity Non-Negotiable Rules
593
+
594
+ 1. **Signals**: Use \`signal()\`, \`computed()\`, \`effect()\`, \`untrack()\`. Never use external state libraries.
595
+ 2. **Mutations**: Mutate signals with \`.set()\` or \`.update()\`. Never reassign or mutate \`.value\`.
596
+ 3. **Templates**: Inlined synchronously at build time with \`templateUrl: './xyz.html'\`.
597
+ 4. **Repeaters**: Use \`for="let item of items"\` or \`virtual-for\`. Never \`*ngFor\` or \`v-for\`.
598
+ 5. **Conditionals**: Use \`if="expr"\`, \`else-if="expr"\`, \`else\`. Falsy branches are deferred.
599
+ 6. **Imports**: Path aliases mandatory (\`@purity/core\`, \`@components/*\`, \`@styles\`). Never relative \`../\`.
600
+ 7. **Styles**: Always \`@use '@styles' as *;\`. NEVER use inline \`style="..."\` in templates.
601
+ 8. **Cursors**: Use Breeze tokens: \`var(--cursor-pointer)\`, \`var(--cursor-default)\`, etc.
602
+ 9. **Confidential Reference**: NEVER output "GNOME 50" to user-facing UI or copy. Publicly describe as "Adwaita".
603
+ 10. **Testing**: Colocate tests as \`*.spec.ts\` and run with \`npm test\`.`,
604
+ examples: [
605
+ `// COMPLIANT:
606
+ import { Component, signal } from '@purity/core';
607
+ import '@styles';
608
+
609
+ @Component({ selector: 'valid-widget', templateUrl: './valid-widget.html' })
610
+ export class ValidWidget {
611
+ count = signal(0);
612
+ increment() { this.count.update(n => n + 1); }
613
+ }`
614
+ ]
615
+ }
616
+ };
617
+ //# sourceMappingURL=documentation.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"documentation.js","sourceRoot":"","sources":["../../src/data/documentation.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,11 @@
1
+ import { GeneratedFile, ScaffoldType } from '../types.js';
2
+ export declare function toPascalCase(str: string): string;
3
+ export declare function toKebabCase(str: string): string;
4
+ export declare function generateScaffoldFiles(type: ScaffoldType, rawName: string, options?: {
5
+ selector?: string;
6
+ description?: string;
7
+ }): {
8
+ files: GeneratedFile[];
9
+ selector?: string;
10
+ };
11
+ //# sourceMappingURL=templates.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"templates.d.ts","sourceRoot":"","sources":["../../src/data/templates.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,aAAa,EAAE,YAAY,EAAE,MAAM,aAAa,CAAC;AAE1D,wBAAgB,YAAY,CAAC,GAAG,EAAE,MAAM,GAAG,MAAM,CAIhD;AAED,wBAAgB,WAAW,CAAC,GAAG,EAAE,MAAM,GAAG,MAAM,CAK/C;AAED,wBAAgB,qBAAqB,CACnC,IAAI,EAAE,YAAY,EAClB,OAAO,EAAE,MAAM,EACf,OAAO,GAAE;IAAE,QAAQ,CAAC,EAAE,MAAM,CAAC;IAAC,WAAW,CAAC,EAAE,MAAM,CAAA;CAAO,GACxD;IAAE,KAAK,EAAE,aAAa,EAAE,CAAC;IAAC,QAAQ,CAAC,EAAE,MAAM,CAAA;CAAE,CAkoB/C"}