@polymorphism-tech/morph-spec 4.7.1 → 4.8.1
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/.morph/analytics/threads-log.jsonl +54 -0
- package/.morph/state.json +198 -0
- package/LICENSE +1 -2
- package/README.md +379 -414
- package/bin/morph-spec.js +57 -403
- package/bin/validate.js +2 -26
- package/claude-plugin.json +2 -2
- package/docs/ARCHITECTURE.md +43 -46
- package/docs/CHEATSHEET.md +203 -221
- package/docs/COMMAND-FLOWS.md +319 -289
- package/docs/QUICKSTART.md +2 -8
- package/docs/plans/2026-02-22-claude-docs-morph-alignment-analysis.md +2 -0
- package/docs/plans/2026-02-22-claude-settings.md +2 -0
- package/docs/plans/2026-02-22-morph-cc-alignment-impl.md +2 -0
- package/docs/plans/2026-02-22-morph-spec-next.md +2 -0
- package/docs/plans/2026-02-22-native-alignment-design.md +2 -0
- package/docs/plans/2026-02-22-native-alignment-impl.md +2 -0
- package/docs/plans/2026-02-22-native-enrichment-design.md +2 -0
- package/docs/plans/2026-02-22-native-enrichment.md +2 -0
- package/docs/plans/2026-02-23-ddd-architecture-refactor.md +2 -0
- package/docs/plans/2026-02-23-ddd-nextsteps.md +2 -0
- package/docs/plans/2026-02-23-infra-architect-refactor.md +2 -0
- package/docs/plans/2026-02-23-nextjs-code-review-design.md +2 -1
- package/docs/plans/2026-02-23-nextjs-code-review-impl.md +2 -0
- package/docs/plans/2026-02-23-nextjs-standards-design.md +2 -1
- package/docs/plans/2026-02-23-nextjs-standards-impl.md +2 -0
- package/docs/plans/2026-02-24-cli-radical-simplification.md +592 -0
- package/docs/plans/2026-02-24-framework-failure-points.md +125 -0
- package/docs/plans/2026-02-24-morph-init-design.md +337 -0
- package/docs/plans/2026-02-24-morph-init-impl.md +1269 -0
- package/docs/plans/2026-02-24-tutorial-command-design.md +71 -0
- package/docs/plans/2026-02-24-tutorial-command.md +298 -0
- package/framework/CLAUDE.md +2 -2
- package/framework/commands/morph-proposal.md +3 -3
- package/framework/hooks/README.md +11 -10
- package/framework/hooks/claude-code/notification/approval-reminder.js +2 -0
- package/framework/hooks/claude-code/post-tool-use/dispatch.js +1 -1
- package/framework/hooks/claude-code/pre-tool-use/protect-readonly-files.js +4 -55
- package/framework/hooks/claude-code/session-start/inject-morph-context.js +20 -5
- package/framework/hooks/claude-code/statusline.py +6 -1
- package/framework/hooks/claude-code/stop/validate-completion.js +1 -1
- package/framework/hooks/claude-code/user-prompt/enrich-prompt.js +1 -1
- package/framework/hooks/dev/check-sync-health.js +117 -0
- package/framework/hooks/dev/guard-version-numbers.js +57 -0
- package/framework/hooks/dev/sync-standards-registry.js +60 -0
- package/framework/hooks/dev/sync-template-registry.js +60 -0
- package/framework/hooks/dev/validate-skill-format.js +70 -0
- package/framework/hooks/dev/validate-standard-format.js +73 -0
- package/framework/hooks/shared/payload-utils.js +39 -0
- package/framework/hooks/shared/state-reader.js +25 -1
- package/framework/rules/morph-workflow.md +1 -1
- package/framework/skills/level-0-meta/morph-init/SKILL.md +216 -0
- package/framework/skills/level-0-meta/morph-replicate/SKILL.md +4 -4
- package/framework/skills/level-0-meta/tool-usage-guide/SKILL.md +4 -4
- package/framework/skills/level-0-meta/verification-before-completion/SKILL.md +1 -1
- package/framework/skills/level-1-workflows/phase-clarify/SKILL.md +192 -191
- package/framework/skills/level-1-workflows/phase-codebase-analysis/SKILL.md +181 -180
- package/framework/skills/level-1-workflows/phase-design/SKILL.md +339 -338
- package/framework/skills/level-1-workflows/phase-implement/SKILL.md +254 -253
- package/framework/skills/level-1-workflows/phase-setup/SKILL.md +168 -170
- package/framework/skills/level-1-workflows/phase-tasks/SKILL.md +284 -283
- package/framework/skills/level-1-workflows/phase-uiux/SKILL.md +246 -245
- package/framework/templates/examples/design-system-examples.md +1 -1
- package/framework/templates/ui/FluentDesignTheme.cs +1 -1
- package/framework/templates/ui/MudTheme.cs +1 -1
- package/framework/templates/ui/design-system.css +1 -1
- package/package.json +4 -2
- package/scripts/bump-version.js +248 -0
- package/scripts/install-dev-hooks.js +138 -0
- package/src/commands/agents/index.js +1 -2
- package/src/commands/index.js +13 -16
- package/src/commands/project/doctor.js +100 -14
- package/src/commands/project/index.js +7 -10
- package/src/commands/project/init.js +398 -555
- package/src/commands/project/install-plugin-cmd.js +28 -0
- package/src/commands/project/setup-infra-cmd.js +12 -0
- package/src/commands/project/tutorial.js +115 -0
- package/src/commands/project/update.js +22 -37
- package/src/commands/state/approve.js +213 -221
- package/src/commands/state/index.js +0 -1
- package/src/commands/state/state.js +337 -365
- package/src/commands/templates/index.js +0 -4
- package/src/commands/trust/trust.js +1 -93
- package/src/commands/utils/index.js +1 -5
- package/src/commands/validation/index.js +1 -5
- package/src/core/registry/command-registry.js +11 -285
- package/src/core/state/state-manager.js +5 -2
- package/src/lib/detectors/index.js +81 -87
- package/src/lib/detectors/structure-detector.js +275 -273
- package/src/lib/generators/recap-generator.js +232 -225
- package/src/lib/installers/mcp-installer.js +18 -3
- package/src/scripts/global-install.js +34 -0
- package/src/scripts/install-plugin.js +126 -0
- package/src/scripts/setup-infra.js +203 -0
- package/src/utils/agents-installer.js +10 -1
- package/src/utils/hooks-installer.js +70 -17
- package/CLAUDE.md +0 -77
- package/docs/claude-alignment-report.md +0 -137
- package/docs/examples/order-management/contracts.cs +0 -84
- package/docs/examples/order-management/proposal.md +0 -24
- package/docs/examples/order-management/spec.md +0 -162
- package/src/commands/feature/create-story.js +0 -362
- package/src/commands/feature/index.js +0 -6
- package/src/commands/feature/shard-spec.js +0 -225
- package/src/commands/feature/sprint-status.js +0 -250
- package/src/commands/generation/generate-onboarding.js +0 -169
- package/src/commands/generation/generate.js +0 -276
- package/src/commands/generation/index.js +0 -5
- package/src/commands/learning/capture-pattern.js +0 -121
- package/src/commands/learning/index.js +0 -5
- package/src/commands/learning/search-patterns.js +0 -126
- package/src/commands/mcp/mcp.js +0 -102
- package/src/commands/project/changes.js +0 -66
- package/src/commands/project/cost.js +0 -179
- package/src/commands/project/detect.js +0 -114
- package/src/commands/project/diff.js +0 -278
- package/src/commands/project/revert.js +0 -173
- package/src/commands/project/standards.js +0 -80
- package/src/commands/project/sync.js +0 -167
- package/src/commands/project/update-agents.js +0 -23
- package/src/commands/state/rollback-phase.js +0 -185
- package/src/commands/templates/template-customize.js +0 -87
- package/src/commands/templates/template-list.js +0 -114
- package/src/commands/templates/template-show.js +0 -129
- package/src/commands/templates/template-validate.js +0 -91
- package/src/commands/utils/troubleshoot.js +0 -222
- package/src/commands/validation/analyze-blazor-concurrency.js +0 -193
- package/src/commands/validation/lint-fluent.js +0 -352
- package/src/commands/validation/validate-blazor-state.js +0 -210
- package/src/commands/validation/validate-blazor.js +0 -156
- package/src/commands/validation/validate-css.js +0 -84
- package/src/lib/detectors/conversation-analyzer.js +0 -163
- package/src/lib/learning/index.js +0 -7
- package/src/lib/learning/learning-system.js +0 -520
- package/src/lib/troubleshooting/index.js +0 -8
- package/src/lib/troubleshooting/troubleshoot-grep.js +0 -198
- package/src/lib/troubleshooting/troubleshoot-index.js +0 -144
- package/src/llm/environment-detector.js +0 -43
|
@@ -1,84 +0,0 @@
|
|
|
1
|
-
/**
|
|
2
|
-
* MORPH-SPEC validate-css Command
|
|
3
|
-
*
|
|
4
|
-
* Validates that all CSS classes used in Razor files are defined in CSS files.
|
|
5
|
-
* Helps catch missing CSS definitions before runtime.
|
|
6
|
-
*
|
|
7
|
-
* Usage:
|
|
8
|
-
* morph-spec validate-css [path]
|
|
9
|
-
* morph-spec validate-css src/MyApp.Web
|
|
10
|
-
* morph-spec validate-css --verbose
|
|
11
|
-
* morph-spec validate-css --generate-stub
|
|
12
|
-
*/
|
|
13
|
-
|
|
14
|
-
import chalk from 'chalk';
|
|
15
|
-
import { existsSync, writeFileSync } from 'fs';
|
|
16
|
-
import { resolve, join } from 'path';
|
|
17
|
-
import {
|
|
18
|
-
validateCssClasses,
|
|
19
|
-
formatValidationResults,
|
|
20
|
-
generateCssStub
|
|
21
|
-
} from '../../lib/validators/css/css-validator.js';
|
|
22
|
-
|
|
23
|
-
/**
|
|
24
|
-
* Execute the validate-css command
|
|
25
|
-
* @param {string} path - Project path to validate
|
|
26
|
-
* @param {Object} options - Command options
|
|
27
|
-
*/
|
|
28
|
-
export async function validateCssCommand(path, options = {}) {
|
|
29
|
-
const projectPath = resolve(path || '.');
|
|
30
|
-
const { verbose, generateStub, includeUtilities } = options;
|
|
31
|
-
|
|
32
|
-
// Validate path exists
|
|
33
|
-
if (!existsSync(projectPath)) {
|
|
34
|
-
console.error(chalk.red(`\n Error: Path does not exist: ${projectPath}\n`));
|
|
35
|
-
process.exit(1);
|
|
36
|
-
}
|
|
37
|
-
|
|
38
|
-
console.log(chalk.cyan('\n Validating CSS classes...\n'));
|
|
39
|
-
console.log(chalk.gray(` Path: ${projectPath}`));
|
|
40
|
-
console.log('');
|
|
41
|
-
|
|
42
|
-
try {
|
|
43
|
-
// Run validation
|
|
44
|
-
const results = await validateCssClasses(projectPath, {
|
|
45
|
-
verbose,
|
|
46
|
-
includeUtilities
|
|
47
|
-
});
|
|
48
|
-
|
|
49
|
-
// Output results
|
|
50
|
-
const formatted = formatValidationResults(results, verbose);
|
|
51
|
-
console.log(formatted);
|
|
52
|
-
|
|
53
|
-
// Generate stub if requested
|
|
54
|
-
if (generateStub && !results.valid) {
|
|
55
|
-
const stubContent = generateCssStub(results);
|
|
56
|
-
const stubPath = join(projectPath, 'missing-classes.css');
|
|
57
|
-
|
|
58
|
-
writeFileSync(stubPath, stubContent, 'utf8');
|
|
59
|
-
console.log(chalk.green(`\n Generated stub file: ${stubPath}\n`));
|
|
60
|
-
}
|
|
61
|
-
|
|
62
|
-
// Summary with colors
|
|
63
|
-
if (results.valid) {
|
|
64
|
-
console.log(chalk.green('\n All CSS classes are properly defined!\n'));
|
|
65
|
-
process.exit(0);
|
|
66
|
-
} else {
|
|
67
|
-
console.log(chalk.yellow(`\n Found ${results.missingClasses.length} missing CSS class(es)\n`));
|
|
68
|
-
|
|
69
|
-
// Suggestions
|
|
70
|
-
console.log(chalk.cyan('Suggestions:'));
|
|
71
|
-
console.log(chalk.gray(' 1. Add the missing classes to your design-system.css'));
|
|
72
|
-
console.log(chalk.gray(' 2. Run with --generate-stub to create a template file'));
|
|
73
|
-
console.log(chalk.gray(' 3. If using utility frameworks (Tailwind), add --include-utilities\n'));
|
|
74
|
-
|
|
75
|
-
process.exit(1);
|
|
76
|
-
}
|
|
77
|
-
} catch (error) {
|
|
78
|
-
console.error(chalk.red(`\n Error: ${error.message}\n`));
|
|
79
|
-
if (verbose) {
|
|
80
|
-
console.error(error.stack);
|
|
81
|
-
}
|
|
82
|
-
process.exit(1);
|
|
83
|
-
}
|
|
84
|
-
}
|
|
@@ -1,163 +0,0 @@
|
|
|
1
|
-
/**
|
|
2
|
-
* Conversation Analyzer - Analyzes Claude Code conversation history for user preferences
|
|
3
|
-
*
|
|
4
|
-
* Note: This is a basic implementation. Full conversation analysis would require
|
|
5
|
-
* access to Claude Code's message history API or local cache.
|
|
6
|
-
*/
|
|
7
|
-
|
|
8
|
-
import { existsSync, readFileSync } from 'fs';
|
|
9
|
-
import { join } from 'path';
|
|
10
|
-
|
|
11
|
-
/**
|
|
12
|
-
* Analyze conversation history
|
|
13
|
-
* @param {string} projectPath - Project root path
|
|
14
|
-
* @returns {Promise<Object>} Conversation analysis results
|
|
15
|
-
*/
|
|
16
|
-
export async function analyzeConversation(projectPath) {
|
|
17
|
-
const result = {
|
|
18
|
-
preferences: {},
|
|
19
|
-
decisions: [],
|
|
20
|
-
patterns: [],
|
|
21
|
-
available: false
|
|
22
|
-
};
|
|
23
|
-
|
|
24
|
-
// Check if .morph/context exists (past decisions)
|
|
25
|
-
const contextPath = join(projectPath, '.morph', 'context');
|
|
26
|
-
if (existsSync(contextPath)) {
|
|
27
|
-
result.available = true;
|
|
28
|
-
|
|
29
|
-
// Read decisions-history.md if exists
|
|
30
|
-
const decisionsFile = join(contextPath, 'decisions-history.md');
|
|
31
|
-
if (existsSync(decisionsFile)) {
|
|
32
|
-
const content = readFileSync(decisionsFile, 'utf8');
|
|
33
|
-
result.decisions = extractDecisions(content);
|
|
34
|
-
}
|
|
35
|
-
}
|
|
36
|
-
|
|
37
|
-
// Check .morph/features/*/decisions.md
|
|
38
|
-
const outputsPath = join(projectPath, '.morph', 'features');
|
|
39
|
-
if (existsSync(outputsPath)) {
|
|
40
|
-
const { readdirSync } = await import('fs');
|
|
41
|
-
const features = readdirSync(outputsPath, { withFileTypes: true })
|
|
42
|
-
.filter(dirent => dirent.isDirectory())
|
|
43
|
-
.map(dirent => dirent.name);
|
|
44
|
-
|
|
45
|
-
for (const feature of features) {
|
|
46
|
-
const decisionsFile = join(outputsPath, feature, 'decisions.md');
|
|
47
|
-
if (existsSync(decisionsFile)) {
|
|
48
|
-
const content = readFileSync(decisionsFile, 'utf8');
|
|
49
|
-
result.decisions.push(...extractDecisions(content));
|
|
50
|
-
}
|
|
51
|
-
}
|
|
52
|
-
}
|
|
53
|
-
|
|
54
|
-
// Extract patterns from decisions
|
|
55
|
-
result.patterns = inferPatternsFromDecisions(result.decisions);
|
|
56
|
-
|
|
57
|
-
// Extract preferences
|
|
58
|
-
result.preferences = extractPreferences(result.decisions);
|
|
59
|
-
|
|
60
|
-
return result;
|
|
61
|
-
}
|
|
62
|
-
|
|
63
|
-
/**
|
|
64
|
-
* Extract decisions from markdown
|
|
65
|
-
*/
|
|
66
|
-
function extractDecisions(markdown) {
|
|
67
|
-
const decisions = [];
|
|
68
|
-
const lines = markdown.split('\n');
|
|
69
|
-
|
|
70
|
-
let currentDecision = null;
|
|
71
|
-
|
|
72
|
-
for (const line of lines) {
|
|
73
|
-
// Look for decision headings
|
|
74
|
-
if (line.match(/^##\s+Decision/i) || line.match(/^###\s+ADR/i)) {
|
|
75
|
-
if (currentDecision) {
|
|
76
|
-
decisions.push(currentDecision);
|
|
77
|
-
}
|
|
78
|
-
currentDecision = { text: '', category: 'unknown', confidence: 0.5 };
|
|
79
|
-
}
|
|
80
|
-
|
|
81
|
-
if (currentDecision) {
|
|
82
|
-
currentDecision.text += line + '\n';
|
|
83
|
-
|
|
84
|
-
// Categorize
|
|
85
|
-
if (line.includes('UI') || line.includes('component') || line.includes('Fluent') || line.includes('Mud')) {
|
|
86
|
-
currentDecision.category = 'ui-ux';
|
|
87
|
-
currentDecision.confidence = 0.8;
|
|
88
|
-
} else if (line.includes('pattern') || line.includes('architecture') || line.includes('CQRS')) {
|
|
89
|
-
currentDecision.category = 'architecture';
|
|
90
|
-
currentDecision.confidence = 0.8;
|
|
91
|
-
} else if (line.includes('Azure') || line.includes('Container') || line.includes('deployment')) {
|
|
92
|
-
currentDecision.category = 'azure';
|
|
93
|
-
currentDecision.confidence = 0.8;
|
|
94
|
-
} else if (line.includes('class') || line.includes('method') || line.includes('naming')) {
|
|
95
|
-
currentDecision.category = 'coding';
|
|
96
|
-
currentDecision.confidence = 0.8;
|
|
97
|
-
}
|
|
98
|
-
}
|
|
99
|
-
}
|
|
100
|
-
|
|
101
|
-
if (currentDecision) {
|
|
102
|
-
decisions.push(currentDecision);
|
|
103
|
-
}
|
|
104
|
-
|
|
105
|
-
return decisions;
|
|
106
|
-
}
|
|
107
|
-
|
|
108
|
-
/**
|
|
109
|
-
* Infer patterns from decisions
|
|
110
|
-
*/
|
|
111
|
-
function inferPatternsFromDecisions(decisions) {
|
|
112
|
-
const patterns = [];
|
|
113
|
-
|
|
114
|
-
for (const decision of decisions) {
|
|
115
|
-
const text = decision.text.toLowerCase();
|
|
116
|
-
|
|
117
|
-
if (text.includes('always use') || text.includes('sempre usar')) {
|
|
118
|
-
patterns.push(`Pattern: ${decision.text.split('\n')[0].substring(0, 60)}...`);
|
|
119
|
-
}
|
|
120
|
-
|
|
121
|
-
if (text.includes('never') || text.includes('nunca')) {
|
|
122
|
-
patterns.push(`Anti-pattern: ${decision.text.split('\n')[0].substring(0, 60)}...`);
|
|
123
|
-
}
|
|
124
|
-
}
|
|
125
|
-
|
|
126
|
-
return patterns;
|
|
127
|
-
}
|
|
128
|
-
|
|
129
|
-
/**
|
|
130
|
-
* Extract user preferences
|
|
131
|
-
*/
|
|
132
|
-
function extractPreferences(decisions) {
|
|
133
|
-
const preferences = {
|
|
134
|
-
uiLibrary: null,
|
|
135
|
-
architecture: null,
|
|
136
|
-
testing: null,
|
|
137
|
-
deployment: null
|
|
138
|
-
};
|
|
139
|
-
|
|
140
|
-
for (const decision of decisions) {
|
|
141
|
-
const text = decision.text.toLowerCase();
|
|
142
|
-
|
|
143
|
-
if (text.includes('fluent ui') && !text.includes('not')) {
|
|
144
|
-
preferences.uiLibrary = 'Fluent UI';
|
|
145
|
-
} else if (text.includes('mudblazor') && !text.includes('not')) {
|
|
146
|
-
preferences.uiLibrary = 'MudBlazor';
|
|
147
|
-
}
|
|
148
|
-
|
|
149
|
-
if (text.includes('clean architecture')) {
|
|
150
|
-
preferences.architecture = 'Clean Architecture';
|
|
151
|
-
} else if (text.includes('cqrs')) {
|
|
152
|
-
preferences.architecture = 'CQRS';
|
|
153
|
-
}
|
|
154
|
-
|
|
155
|
-
if (text.includes('container apps')) {
|
|
156
|
-
preferences.deployment = 'Azure Container Apps';
|
|
157
|
-
} else if (text.includes('app service')) {
|
|
158
|
-
preferences.deployment = 'Azure App Service';
|
|
159
|
-
}
|
|
160
|
-
}
|
|
161
|
-
|
|
162
|
-
return preferences;
|
|
163
|
-
}
|