@getcoherent/cli 0.6.50 → 0.6.51

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.
@@ -2,10 +2,10 @@ import {
2
2
  CORE_CONSTRAINTS,
3
3
  getDesignQualityForType,
4
4
  inferPageTypeFromRoute
5
- } from "./chunk-E23FJX2I.js";
5
+ } from "./chunk-NLL3SHN3.js";
6
6
  import {
7
7
  autoFixCode
8
- } from "./chunk-NOM47EB4.js";
8
+ } from "./chunk-U5SNPHVU.js";
9
9
 
10
10
  // src/commands/chat/plan-generator.ts
11
11
  import { z } from "zod";
@@ -28,10 +28,8 @@ TYPOGRAPHY (most impactful rules):
28
28
  - Create hierarchy through font WEIGHT (medium \u2192 semibold \u2192 bold), NOT font SIZE.
29
29
 
30
30
  COLORS \u2014 ONLY SEMANTIC TOKENS (zero raw colors):
31
- - Backgrounds: bg-background, bg-muted, bg-muted/50, bg-card, bg-primary, bg-secondary, bg-destructive.
32
- - Text: text-foreground (default), text-muted-foreground, text-primary-foreground.
33
- - Borders: border (no color suffix \u2014 uses CSS variable). border-b for headers.
34
- - BANNED: bg-gray-*, bg-blue-*, bg-slate-*, text-gray-*, ANY raw Tailwind color. The validator REJECTS these.
31
+ - Allowed: bg-background, bg-muted, bg-muted/50, bg-card, bg-primary, bg-secondary, bg-destructive, bg-success, bg-warning. text-foreground, text-muted-foreground, text-primary-foreground, text-destructive, text-success. border (bare), border-border. Opacity modifiers OK (bg-primary/50). ring-*, shadow-*, fill-*, stroke-* with same token names.
32
+ - BANNED: ANY raw Tailwind color (bg-gray-*, text-blue-*, etc.), inline style colors, hex values, bg-white, bg-black. The validator REJECTS all of these.
35
33
 
36
34
  SPACING (restricted palette \u2014 only multiples of 4px):
37
35
  - Page content padding: p-4 lg:p-6. Gap between major sections: gap-6 md:gap-8.
@@ -115,7 +113,7 @@ var DESIGN_QUALITY_COMMON = `
115
113
 
116
114
  ### Visual Depth & Layers
117
115
  - Cards: bg-card border border-border/15 rounded-xl (not rounded-md)
118
- - Cards on dark pages: bg-zinc-900/50 border-border/10 backdrop-blur-sm
116
+ - Cards on dark pages: bg-card border-border/10 backdrop-blur-sm
119
117
  - Cards MUST have hover state: hover:border-border/30 transition-colors
120
118
  - Sections alternate between bg-background and bg-muted/5 for rhythm
121
119
  - Section dividers: border-t border-border/10 (subtle, not heavy)
@@ -127,18 +125,18 @@ var DESIGN_QUALITY_COMMON = `
127
125
  - CTA buttons: use the Button component, NEVER raw <button> or <a> styled as button
128
126
 
129
127
  ### Accent Color Discipline
130
- - ONE accent color per page (primary or emerald-400)
131
- - Use for: CTAs, terminal text, check icons, feature icon backgrounds, active states
132
- - NEVER mix blue + purple + emerald on same page
128
+ - ONE accent color per page (primary)
129
+ - Use for: CTAs, check icons, feature icon backgrounds, active states
130
+ - NEVER mix multiple accent colors on same page
133
131
  - Badge: outline style (border-border/30 bg-transparent) not filled color
134
- - Status icons: text-emerald-400 for positive, text-red-400 for negative
132
+ - Status icons: text-success for positive, text-destructive for negative
135
133
 
136
134
  ### Dark Theme Implementation
137
135
  - html element: className="dark"
138
136
  - Background: use CSS variables from globals.css dark section
139
137
  - Text: text-foreground for primary, text-muted-foreground for secondary
140
138
  - NEVER hardcode dark colors (bg-gray-900) \u2014 always use semantic tokens
141
- - Cards and elevated elements: slightly lighter than background (bg-card or bg-zinc-900/50)
139
+ - Cards and elevated elements: slightly lighter than background (bg-card)
142
140
  `;
143
141
  var DESIGN_QUALITY_MARKETING = `
144
142
  ## DESIGN QUALITY \u2014 MARKETING PAGES
@@ -155,15 +153,15 @@ var DESIGN_QUALITY_MARKETING = `
155
153
 
156
154
  ### Icons in Feature Cards
157
155
  - Wrap in colored container: bg-primary/10 rounded-lg p-2.5
158
- - Icon color: text-primary (or text-emerald-400 for dark themes)
156
+ - Icon color: text-primary
159
157
  - Icon size: h-5 w-5 inside the container
160
158
  - NEVER bare icons floating in a card without container
161
159
 
162
160
  ### Terminal / Code Blocks
163
161
  - Background: bg-zinc-950 (near-black, not gray)
164
162
  - Border: border-border/10 rounded-xl
165
- - Text: font-mono text-sm text-emerald-400
166
- - Prompt: text-emerald-500 "$ " prefix (green dollar sign)
163
+ - Text: font-mono text-sm text-emerald-400 (EXCEPTION: terminal blocks use raw green for aesthetics)
164
+ - Prompt: text-emerald-500 "$ " prefix (EXCEPTION: terminal prompt uses raw green)
167
165
  - Title bar (optional): flex with 3 dots (bg-zinc-700 rounded-full w-2.5 h-2.5) + title text-zinc-500 text-[11px]
168
166
  - Copy button: text-zinc-500 hover:text-zinc-300
169
167
 
@@ -177,8 +175,8 @@ var DESIGN_QUALITY_MARKETING = `
177
175
 
178
176
  ### Comparison Sections (before/after, with/without)
179
177
  - Two cards side by side: grid md:grid-cols-2 gap-6
180
- - Negative card: neutral border, items with X icon text-red-400
181
- - Positive card: accent border (border-emerald-500/20), items with Check icon text-emerald-400
178
+ - Negative card: neutral border, items with X icon text-destructive
179
+ - Positive card: accent border (border-primary/20), items with Check icon text-success
182
180
  - Header of each card: text-sm font-semibold uppercase tracking-wider
183
181
 
184
182
  ### Step/Process Sections
@@ -493,7 +491,7 @@ var RULES_DATA_DISPLAY = `
493
491
  DATA DISPLAY RULES:
494
492
 
495
493
  STAT / METRIC CARDS: See the Stats Grid reference pattern in DESIGN QUALITY \u2014 APP PAGES. Follow that exact pattern.
496
- - Trend up: text-emerald-600 (light) / text-emerald-400 (dark) \u2014 exception to semantic-only rule for trend indicators.
494
+ - Trend up: text-success.
497
495
  - Trend down: text-destructive.
498
496
  - Trend icon: ArrowUp / ArrowDown className="size-3 inline mr-1".
499
497
  - No actions on stat cards. Click entire card to drill down (if applicable).
@@ -530,12 +528,12 @@ MOCK DATA IN COMPONENTS:
530
528
  - NEVER store display strings ("2 hours ago", "Yesterday") in data \u2014 always compute from ISO date.
531
529
 
532
530
  STATUS INDICATORS (dot + text):
533
- - Pattern: <div className="flex items-center gap-2"><div className="size-2 rounded-full bg-emerald-500" /><span className="text-sm">Active</span></div>
534
- - Colors: bg-emerald-500 (active/online), bg-destructive (error/offline), bg-yellow-500 (warning), bg-muted-foreground (inactive).
531
+ - Pattern: <div className="flex items-center gap-2"><div className="size-2 rounded-full bg-success" /><span className="text-sm">Active</span></div>
532
+ - Colors: bg-success (active/online), bg-destructive (error/offline), bg-warning (warning), bg-muted-foreground (inactive).
535
533
  - Alternative: use Badge variants for status in tables/lists (preferred over dots).
536
534
 
537
535
  TREND INDICATORS:
538
- - Up (positive): <span className="text-sm text-emerald-600 flex items-center"><ArrowUp className="size-3 mr-1" />12.5%</span>
536
+ - Up (positive): <span className="text-sm text-success flex items-center"><ArrowUp className="size-3 mr-1" />12.5%</span>
539
537
  - Down (negative): <span className="text-sm text-destructive flex items-center"><ArrowDown className="size-3 mr-1" />3.2%</span>
540
538
  - Neutral: <span className="text-sm text-muted-foreground">0%</span>
541
539
  - Always include arrow icon + sign (+ or -) + percentage.
@@ -1,3 +1,7 @@
1
+ // src/utils/quality-validator.ts
2
+ import { readdir, readFile } from "fs/promises";
3
+ import { join } from "path";
4
+
1
5
  // src/utils/component-rules.ts
2
6
  function extractJsxElementProps(code, openTagStart) {
3
7
  let i = openTagStart;
@@ -155,7 +159,12 @@ function applyComponentRules(code) {
155
159
  }
156
160
 
157
161
  // src/utils/quality-validator.ts
158
- var RAW_COLOR_RE = /(?:(?:hover|focus|active|group-hover|focus-visible|focus-within):)?(?:bg|text|border|ring|outline|shadow|from|to|via)-(gray|blue|red|green|yellow|purple|pink|indigo|orange|slate|zinc|stone|neutral|emerald|teal|cyan|sky|violet|fuchsia|rose|amber|lime)-\d+/g;
162
+ var RAW_COLOR_RE = /(?:(?:[a-z][a-z0-9-]*:)*)?(?:bg|text|border|ring|outline|shadow|from|to|via|divide|placeholder|decoration|caret|fill|stroke|accent)-(gray|blue|red|green|yellow|purple|pink|indigo|orange|slate|zinc|stone|neutral|emerald|teal|cyan|sky|violet|fuchsia|rose|amber|lime)-\d+/g;
163
+ var RAW_BW_COLOR_RE = /(?:(?:[a-z][a-z0-9-]*:)*)?(?:bg|text|border|ring|outline|shadow|divide|fill|stroke)-(white|black)\b/g;
164
+ var INLINE_STYLE_COLOR_RE = /style=\{[^}]*(color|background|backgroundColor|borderColor)\s*:\s*['"]?(#[0-9a-fA-F]{3,8}|rgb|hsl|red|blue|orange|green|purple|yellow|pink|white|black|gray|grey)\b/gi;
165
+ var ARBITRARY_COLOR_RE = /\b(?:bg|text|border|ring|shadow|fill|stroke|from|to|via)-\[(?:#[0-9a-fA-F]{3,8}|rgb|hsl|color-mix)/gi;
166
+ var SVG_COLOR_RE = /\b(?:fill|stroke)=["'](?!none|currentColor|url|inherit|transparent)([^"']+)["']/g;
167
+ var COLOR_PROP_RE = /\b(?:color|accentColor|iconColor|fillColor)=["']#[0-9a-fA-F]{3,8}["']/g;
159
168
  var HEX_IN_CLASS_RE = /className="[^"]*#[0-9a-fA-F]{3,8}[^"]*"/g;
160
169
  var TEXT_BASE_RE = /\btext-base\b/g;
161
170
  var HEAVY_SHADOW_RE = /\bshadow-(md|lg|xl|2xl)\b/g;
@@ -251,6 +260,51 @@ function validatePageQuality(code, validRoutes, pageType) {
251
260
  "error"
252
261
  ).filter((issue) => !isTerminalContext(issue.line))
253
262
  );
263
+ issues.push(
264
+ ...checkLines(
265
+ code,
266
+ RAW_BW_COLOR_RE,
267
+ "RAW_COLOR",
268
+ "Use semantic tokens (bg-background, text-foreground) instead of white/black",
269
+ "error"
270
+ )
271
+ );
272
+ issues.push(
273
+ ...checkLines(
274
+ code,
275
+ INLINE_STYLE_COLOR_RE,
276
+ "inline-style-color",
277
+ "Use semantic Tailwind classes instead of inline style colors",
278
+ "error"
279
+ )
280
+ );
281
+ issues.push(
282
+ ...checkLines(
283
+ code,
284
+ ARBITRARY_COLOR_RE,
285
+ "arbitrary-color",
286
+ "Use semantic tokens instead of arbitrary color values like bg-[#hex]",
287
+ "error"
288
+ )
289
+ );
290
+ issues.push(
291
+ ...checkLines(
292
+ code,
293
+ SVG_COLOR_RE,
294
+ "svg-raw-color",
295
+ "Use currentColor or CSS variables for SVG fill/stroke, not raw colors",
296
+ "error"
297
+ )
298
+ );
299
+ issues.push(
300
+ ...checkLines(
301
+ code,
302
+ COLOR_PROP_RE,
303
+ "color-prop",
304
+ "Use semantic color tokens instead of hex values in color props",
305
+ "error"
306
+ )
307
+ );
254
308
  issues.push(
255
309
  ...checkLines(
256
310
  code,
@@ -613,7 +667,7 @@ function resolveHref(linkText, context) {
613
667
  function replaceRawColors(classes, colorMap) {
614
668
  let changed = false;
615
669
  let result = classes;
616
- const accentColorRe = /\b((?:(?:hover|focus|active|group-hover|focus-visible|focus-within):)?)(bg|text|border|ring|outline|shadow|from|to|via)-(emerald|blue|violet|indigo|purple|teal|cyan|sky|rose|amber|red|green|yellow|pink|orange|fuchsia|lime)-(\d+)(?:\/\d+)?\b/g;
670
+ const accentColorRe = /\b((?:(?:[a-z][a-z0-9-]*:)*)?)(bg|text|border|ring|outline|shadow|from|to|via|divide|placeholder|decoration|caret|fill|stroke|accent)-(emerald|blue|violet|indigo|purple|teal|cyan|sky|rose|amber|red|green|yellow|pink|orange|fuchsia|lime)-(\d+)(?:\/\d+)?\b/g;
617
671
  result = result.replace(accentColorRe, (m, statePrefix, prefix, color, shade) => {
618
672
  const bareNoOpacity = m.replace(statePrefix, "").replace(/\/\d+$/, "");
619
673
  if (colorMap[bareNoOpacity]) {
@@ -668,7 +722,7 @@ function replaceRawColors(classes, colorMap) {
668
722
  }
669
723
  return m;
670
724
  });
671
- const neutralColorRe = /\b((?:(?:hover|focus|active|group-hover|focus-visible|focus-within):)?)(bg|text|border|ring|outline|shadow)-(zinc|slate|gray|neutral|stone)-(\d+)(?:\/\d+)?\b/g;
725
+ const neutralColorRe = /\b((?:(?:[a-z][a-z0-9-]*:)*)?)(bg|text|border|ring|outline|shadow|divide|placeholder|decoration|caret|fill|stroke|accent)-(zinc|slate|gray|neutral|stone)-(\d+)(?:\/\d+)?\b/g;
672
726
  result = result.replace(neutralColorRe, (m, statePrefix, prefix, _color, shade) => {
673
727
  const bareNoOpacity = m.replace(statePrefix, "").replace(/\/\d+$/, "");
674
728
  if (colorMap[bareNoOpacity]) {
@@ -1041,6 +1095,15 @@ ${fixed}`;
1041
1095
  return fullMatch;
1042
1096
  });
1043
1097
  if (hadColorFix) fixes.push("raw colors \u2192 semantic tokens");
1098
+ if (hadColorFix) {
1099
+ const postFixIssues = validatePageQuality(fixed);
1100
+ const postFixErrors = postFixIssues.filter(
1101
+ (i) => i.severity === "error" && ["raw-color", "inline-style-color", "arbitrary-color", "svg-raw-color", "color-prop"].includes(i.type)
1102
+ );
1103
+ if (postFixErrors.length > 0) {
1104
+ fixes.push(`post-fix re-validation found ${postFixErrors.length} remaining color issue(s)`);
1105
+ }
1106
+ }
1044
1107
  const selectRe = /<select\b[^>]*>([\s\S]*?)<\/select>/g;
1045
1108
  let hadSelectFix = false;
1046
1109
  fixed = fixed.replace(selectRe, (_match, inner) => {
@@ -1455,11 +1518,34 @@ function verifyIncrementalEdit(before, after) {
1455
1518
  }
1456
1519
  return issues;
1457
1520
  }
1521
+ async function validateSharedComponents(projectRoot) {
1522
+ const sharedDir = join(projectRoot, "components", "shared");
1523
+ let files;
1524
+ try {
1525
+ const entries = await readdir(sharedDir);
1526
+ files = entries.filter((f) => f.endsWith(".tsx"));
1527
+ } catch {
1528
+ return [];
1529
+ }
1530
+ const allIssues = [];
1531
+ for (const file of files) {
1532
+ const code = await readFile(join(sharedDir, file), "utf-8");
1533
+ const issues = validatePageQuality(code);
1534
+ for (const issue of issues) {
1535
+ allIssues.push({
1536
+ ...issue,
1537
+ message: `[shared/${file}] ${issue.message}`
1538
+ });
1539
+ }
1540
+ }
1541
+ return allIssues;
1542
+ }
1458
1543
 
1459
1544
  export {
1460
1545
  validatePageQuality,
1461
1546
  autoFixCode,
1462
1547
  formatIssues,
1463
1548
  checkDesignConsistency,
1464
- verifyIncrementalEdit
1549
+ verifyIncrementalEdit,
1550
+ validateSharedComponents
1465
1551
  };
@@ -6,7 +6,7 @@ import {
6
6
  getPageGroup,
7
7
  installPackages,
8
8
  sanitizeMetadataStrings
9
- } from "./chunk-VLBVBF6V.js";
9
+ } from "./chunk-IFJK5OPI.js";
10
10
  import {
11
11
  toKebabCase
12
12
  } from "./chunk-4TLYDTT3.js";
@@ -2147,7 +2147,7 @@ async function regeneratePage(pageId, config, projectRoot) {
2147
2147
  const code = await generator.generate(page, appType);
2148
2148
  const route = page.route || "/";
2149
2149
  const isAuth = isAuthRoute(route) || isAuthRoute(page.name || page.id || "");
2150
- const { loadPlan: loadPlanForPath } = await import("./plan-generator-PIDLFRWZ.js");
2150
+ const { loadPlan: loadPlanForPath } = await import("./plan-generator-D2UBTVCN.js");
2151
2151
  const planForPath = loadPlanForPath(projectRoot);
2152
2152
  const filePath = routeToFsPath(projectRoot, route, planForPath || isAuth);
2153
2153
  await mkdir3(dirname3(filePath), { recursive: true });
@@ -12,11 +12,11 @@ import {
12
12
  regeneratePage,
13
13
  scanAndInstallSharedDeps,
14
14
  validateAndFixGeneratedCode
15
- } from "./chunk-4I7ATX6G.js";
16
- import "./chunk-VLBVBF6V.js";
15
+ } from "./chunk-UZGT5APM.js";
16
+ import "./chunk-IFJK5OPI.js";
17
17
  import "./chunk-4TLYDTT3.js";
18
- import "./chunk-E23FJX2I.js";
19
- import "./chunk-NOM47EB4.js";
18
+ import "./chunk-NLL3SHN3.js";
19
+ import "./chunk-U5SNPHVU.js";
20
20
  import "./chunk-3RG5ZIWI.js";
21
21
  export {
22
22
  buildAppLayoutCode,
@@ -18,7 +18,7 @@ import {
18
18
  getDesignQualityForType,
19
19
  inferPageTypeFromRoute,
20
20
  selectContextualRules
21
- } from "./chunk-E23FJX2I.js";
21
+ } from "./chunk-NLL3SHN3.js";
22
22
  import "./chunk-3RG5ZIWI.js";
23
23
  export {
24
24
  CORE_CONSTRAINTS,
package/dist/index.js CHANGED
@@ -34,7 +34,7 @@ import {
34
34
  warnIfVolatile,
35
35
  warnInlineDuplicates,
36
36
  writeFile
37
- } from "./chunk-4I7ATX6G.js";
37
+ } from "./chunk-UZGT5APM.js";
38
38
  import {
39
39
  COHERENT_REQUIRED_PACKAGES,
40
40
  ensureUseClientIfNeeded,
@@ -52,7 +52,7 @@ import {
52
52
  sanitizeMetadataStrings,
53
53
  savePlan,
54
54
  updateArchitecturePlan
55
- } from "./chunk-VLBVBF6V.js";
55
+ } from "./chunk-IFJK5OPI.js";
56
56
  import {
57
57
  isValidTsx,
58
58
  safeWrite
@@ -74,7 +74,7 @@ import {
74
74
  getDesignQualityForType,
75
75
  inferPageTypeFromRoute,
76
76
  selectContextualRules
77
- } from "./chunk-E23FJX2I.js";
77
+ } from "./chunk-NLL3SHN3.js";
78
78
  import {
79
79
  fixGlobalsCss,
80
80
  generateV4GlobalsCss,
@@ -87,7 +87,7 @@ import {
87
87
  formatIssues,
88
88
  validatePageQuality,
89
89
  verifyIncrementalEdit
90
- } from "./chunk-NOM47EB4.js";
90
+ } from "./chunk-U5SNPHVU.js";
91
91
  import {
92
92
  __require
93
93
  } from "./chunk-3RG5ZIWI.js";
@@ -3941,7 +3941,7 @@ async function splitGeneratePages(spinner, message, modCtx, provider, parseOpts)
3941
3941
  if (plan && plan.sharedComponents.length > 0) {
3942
3942
  spinner.start(`Phase 4.5/6 \u2014 Generating ${plan.sharedComponents.length} shared components from plan...`);
3943
3943
  try {
3944
- const { generateSharedComponentsFromPlan } = await import("./plan-generator-PIDLFRWZ.js");
3944
+ const { generateSharedComponentsFromPlan } = await import("./plan-generator-D2UBTVCN.js");
3945
3945
  const generated = await generateSharedComponentsFromPlan(
3946
3946
  plan,
3947
3947
  styleContext,
@@ -4696,6 +4696,16 @@ async function applyModification(request, dsm, cm, pm, projectRoot, aiProvider,
4696
4696
  console.log(chalk8.dim(" \u{1F527} Post-generation fixes:"));
4697
4697
  fixes.forEach((f) => console.log(chalk8.dim(` ${f}`)));
4698
4698
  }
4699
+ const colorIssueTypes = ["raw-color", "inline-style-color", "arbitrary-color", "svg-raw-color", "color-prop"];
4700
+ const colorIssues = validatePageQuality(fixedCode).filter(
4701
+ (i) => i.severity === "error" && colorIssueTypes.includes(i.type)
4702
+ );
4703
+ if (colorIssues.length > 0) {
4704
+ console.warn(
4705
+ `\u26A0 Component has ${colorIssues.length} color issue(s) after auto-fix:
4706
+ ` + colorIssues.map((i) => ` L${i.line}: ${i.message}`).join("\n")
4707
+ );
4708
+ }
4699
4709
  await writeFile(fullPath, fixedCode);
4700
4710
  printSharedComponentReport({
4701
4711
  id: resolved.id,
@@ -5859,7 +5869,7 @@ async function chatCommand(message, options) {
5859
5869
  spinner.start(`Creating shared component: ${componentName}...`);
5860
5870
  const { createAIProvider: createAIProvider2 } = await import("./ai-provider-CGSIYFZT.js");
5861
5871
  const { generateSharedComponent: generateSharedComponent6 } = await import("@getcoherent/core");
5862
- const { autoFixCode: autoFixCode2 } = await import("./quality-validator-2KIT6QKA.js");
5872
+ const { autoFixCode: autoFixCode2 } = await import("./quality-validator-IM6YFKLI.js");
5863
5873
  const { extractPropsInterface, extractDependencies } = await import("./component-extractor-VYJLT5NR.js");
5864
5874
  const aiProvider = await createAIProvider2(provider ?? "auto");
5865
5875
  const prompt = `Generate a React component called "${componentName}". Description: ${message}.
@@ -6328,7 +6338,7 @@ Return JSON: { "requests": [{ "type": "add-page", "changes": { "name": "${compon
6328
6338
  }
6329
6339
  try {
6330
6340
  const { validateReuse } = await import("./reuse-validator-XR2ZEYC4.js");
6331
- const { inferPageTypeFromRoute: inferPageTypeFromRoute2 } = await import("./design-constraints-HGNEY3W3.js");
6341
+ const { inferPageTypeFromRoute: inferPageTypeFromRoute2 } = await import("./design-constraints-PFZDW2XW.js");
6332
6342
  const manifest2 = await loadManifest6(projectRoot);
6333
6343
  const reuseplan = projectRoot ? loadPlan(projectRoot) : null;
6334
6344
  if (manifest2.shared.length > 0) {
@@ -8468,8 +8478,8 @@ async function fixCommand(opts = {}) {
8468
8478
  console.log(chalk15.green(` \u2714 ${verb} syntax: ${syntaxFixed} file(s) (use client, metadata, quotes)`));
8469
8479
  }
8470
8480
  try {
8471
- const { loadPlan: loadPlan2 } = await import("./plan-generator-PIDLFRWZ.js");
8472
- const { ensurePlanGroupLayouts: ensurePlanGroupLayouts2 } = await import("./code-generator-YSGVHVNN.js");
8481
+ const { loadPlan: loadPlan2 } = await import("./plan-generator-D2UBTVCN.js");
8482
+ const { ensurePlanGroupLayouts: ensurePlanGroupLayouts2 } = await import("./code-generator-IZ6XM6WG.js");
8473
8483
  const plan = loadPlan2(projectRoot);
8474
8484
  if (plan) {
8475
8485
  if (!dsm) {
@@ -8523,7 +8533,7 @@ async function fixCommand(opts = {}) {
8523
8533
  const publicExists = existsSync13(publicLayoutPath);
8524
8534
  const needsPublicLayout = !publicExists || !readFileSync10(publicLayoutPath, "utf-8").includes("<Header");
8525
8535
  if (needsPublicLayout) {
8526
- const { buildPublicLayoutCodeForSidebar } = await import("./code-generator-YSGVHVNN.js");
8536
+ const { buildPublicLayoutCodeForSidebar } = await import("./code-generator-IZ6XM6WG.js");
8527
8537
  mkdirSync7(resolve8(projectRoot, "app", "(public)"), { recursive: true });
8528
8538
  const publicResult = safeWrite(publicLayoutPath, buildPublicLayoutCodeForSidebar(), projectRoot, backups);
8529
8539
  if (publicResult.ok) {
@@ -8572,7 +8582,7 @@ async function fixCommand(opts = {}) {
8572
8582
  }
8573
8583
  const themeTogglePath = resolve8(projectRoot, "components", "shared", "theme-toggle.tsx");
8574
8584
  if (!existsSync13(themeTogglePath)) {
8575
- const { generateThemeToggleCode } = await import("./code-generator-YSGVHVNN.js");
8585
+ const { generateThemeToggleCode } = await import("./code-generator-IZ6XM6WG.js");
8576
8586
  mkdirSync7(resolve8(projectRoot, "components", "shared"), { recursive: true });
8577
8587
  const themeResult = safeWrite(themeTogglePath, generateThemeToggleCode(), projectRoot, backups);
8578
8588
  if (themeResult.ok) {
@@ -8593,7 +8603,7 @@ async function fixCommand(opts = {}) {
8593
8603
  const isMinimal = appLayoutCode.length < 500 && !appLayoutCode.includes("Header") && !appLayoutCode.includes("Footer") && !appLayoutCode.includes("Sidebar") && !appLayoutCode.includes("SidebarProvider") && !appLayoutCode.includes("SidebarTrigger") && !appLayoutCode.includes("Sheet");
8594
8604
  const navType = dsm.getConfig().navigation?.type || "header";
8595
8605
  if (isMinimal && navType !== "none") {
8596
- const { buildAppLayoutCode, buildGroupLayoutCode } = await import("./code-generator-YSGVHVNN.js");
8606
+ const { buildAppLayoutCode, buildGroupLayoutCode } = await import("./code-generator-IZ6XM6WG.js");
8597
8607
  const isSidebar = navType === "sidebar" || navType === "both";
8598
8608
  const newLayout = isSidebar ? buildAppLayoutCode(navType, dsm.getConfig().name) : buildGroupLayoutCode("header", dsm.getConfig().pages?.map((p) => p.name) || [], dsm.getConfig().name);
8599
8609
  if (!dryRun) {
@@ -9140,7 +9150,7 @@ async function checkCommand(opts = {}) {
9140
9150
  if (!skipShared) {
9141
9151
  try {
9142
9152
  const { validateReuse } = await import("./reuse-validator-XR2ZEYC4.js");
9143
- const { inferPageTypeFromRoute: inferPageTypeFromRoute2 } = await import("./design-constraints-HGNEY3W3.js");
9153
+ const { inferPageTypeFromRoute: inferPageTypeFromRoute2 } = await import("./design-constraints-PFZDW2XW.js");
9144
9154
  const manifest = await loadManifest9(projectRoot);
9145
9155
  const appDir = resolve9(projectRoot, "app");
9146
9156
  const pageFiles = existsSync14(appDir) ? findTsxFiles(appDir) : [];
@@ -11,9 +11,9 @@ import {
11
11
  routeToKey,
12
12
  savePlan,
13
13
  updateArchitecturePlan
14
- } from "./chunk-VLBVBF6V.js";
15
- import "./chunk-E23FJX2I.js";
16
- import "./chunk-NOM47EB4.js";
14
+ } from "./chunk-IFJK5OPI.js";
15
+ import "./chunk-NLL3SHN3.js";
16
+ import "./chunk-U5SNPHVU.js";
17
17
  import "./chunk-3RG5ZIWI.js";
18
18
  export {
19
19
  ArchitecturePlanSchema,
@@ -3,13 +3,15 @@ import {
3
3
  checkDesignConsistency,
4
4
  formatIssues,
5
5
  validatePageQuality,
6
+ validateSharedComponents,
6
7
  verifyIncrementalEdit
7
- } from "./chunk-NOM47EB4.js";
8
+ } from "./chunk-U5SNPHVU.js";
8
9
  import "./chunk-3RG5ZIWI.js";
9
10
  export {
10
11
  autoFixCode,
11
12
  checkDesignConsistency,
12
13
  formatIssues,
13
14
  validatePageQuality,
15
+ validateSharedComponents,
14
16
  verifyIncrementalEdit
15
17
  };
package/package.json CHANGED
@@ -3,7 +3,7 @@
3
3
  "publishConfig": {
4
4
  "access": "public"
5
5
  },
6
- "version": "0.6.50",
6
+ "version": "0.6.51",
7
7
  "description": "CLI interface for Coherent Design Method",
8
8
  "type": "module",
9
9
  "main": "./dist/index.js",
@@ -33,8 +33,15 @@
33
33
  ],
34
34
  "author": "Coherent Design Method",
35
35
  "license": "MIT",
36
+ "scripts": {
37
+ "dev": "tsup --watch",
38
+ "build": "tsup",
39
+ "typecheck": "tsc --noEmit",
40
+ "test": "vitest"
41
+ },
36
42
  "dependencies": {
37
43
  "@anthropic-ai/sdk": "^0.32.0",
44
+ "@getcoherent/core": "workspace:*",
38
45
  "chalk": "^5.3.0",
39
46
  "chokidar": "^4.0.1",
40
47
  "commander": "^11.1.0",
@@ -42,8 +49,7 @@
42
49
  "open": "^10.1.0",
43
50
  "ora": "^7.0.1",
44
51
  "prompts": "^2.4.2",
45
- "zod": "^3.22.4",
46
- "@getcoherent/core": "0.6.50"
52
+ "zod": "^3.22.4"
47
53
  },
48
54
  "devDependencies": {
49
55
  "@types/node": "^20.11.0",
@@ -52,11 +58,5 @@
52
58
  "react": "^19.2.4",
53
59
  "tsup": "^8.0.1",
54
60
  "typescript": "^5.3.3"
55
- },
56
- "scripts": {
57
- "dev": "tsup --watch",
58
- "build": "tsup",
59
- "typecheck": "tsc --noEmit",
60
- "test": "vitest"
61
61
  }
62
- }
62
+ }
package/LICENSE DELETED
@@ -1,21 +0,0 @@
1
- MIT License
2
-
3
- Copyright (c) 2025 Sergei Kovtun
4
-
5
- Permission is hereby granted, free of charge, to any person obtaining a copy
6
- of this software and associated documentation files (the "Software"), to deal
7
- in the Software without restriction, including without limitation the rights
8
- to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
9
- copies of the Software, and to permit persons to whom the Software is
10
- furnished to do so, subject to the following conditions:
11
-
12
- The above copyright notice and this permission notice shall be included in all
13
- copies or substantial portions of the Software.
14
-
15
- THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16
- IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17
- FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
18
- AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
19
- LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
20
- OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
21
- SOFTWARE.