openspec-cn 0.23.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.
- package/LICENSE +22 -0
- package/README.md +153 -0
- package/bin/openspec.js +3 -0
- package/dist/cli/index.d.ts +2 -0
- package/dist/cli/index.js +480 -0
- package/dist/commands/change.d.ts +35 -0
- package/dist/commands/change.js +277 -0
- package/dist/commands/completion.d.ts +72 -0
- package/dist/commands/completion.js +257 -0
- package/dist/commands/config.d.ts +8 -0
- package/dist/commands/config.js +198 -0
- package/dist/commands/feedback.d.ts +9 -0
- package/dist/commands/feedback.js +183 -0
- package/dist/commands/schema.d.ts +6 -0
- package/dist/commands/schema.js +869 -0
- package/dist/commands/show.d.ts +14 -0
- package/dist/commands/show.js +132 -0
- package/dist/commands/spec.d.ts +15 -0
- package/dist/commands/spec.js +225 -0
- package/dist/commands/validate.d.ts +24 -0
- package/dist/commands/validate.js +294 -0
- package/dist/commands/workflow/index.d.ts +17 -0
- package/dist/commands/workflow/index.js +12 -0
- package/dist/commands/workflow/instructions.d.ts +29 -0
- package/dist/commands/workflow/instructions.js +381 -0
- package/dist/commands/workflow/new-change.d.ts +11 -0
- package/dist/commands/workflow/new-change.js +44 -0
- package/dist/commands/workflow/schemas.d.ts +10 -0
- package/dist/commands/workflow/schemas.js +34 -0
- package/dist/commands/workflow/shared.d.ts +52 -0
- package/dist/commands/workflow/shared.js +111 -0
- package/dist/commands/workflow/status.d.ts +14 -0
- package/dist/commands/workflow/status.js +58 -0
- package/dist/commands/workflow/templates.d.ts +16 -0
- package/dist/commands/workflow/templates.js +68 -0
- package/dist/core/archive.d.ts +11 -0
- package/dist/core/archive.js +280 -0
- package/dist/core/artifact-graph/graph.d.ts +56 -0
- package/dist/core/artifact-graph/graph.js +141 -0
- package/dist/core/artifact-graph/index.d.ts +7 -0
- package/dist/core/artifact-graph/index.js +13 -0
- package/dist/core/artifact-graph/instruction-loader.d.ts +143 -0
- package/dist/core/artifact-graph/instruction-loader.js +214 -0
- package/dist/core/artifact-graph/resolver.d.ts +81 -0
- package/dist/core/artifact-graph/resolver.js +257 -0
- package/dist/core/artifact-graph/schema.d.ts +13 -0
- package/dist/core/artifact-graph/schema.js +108 -0
- package/dist/core/artifact-graph/state.d.ts +12 -0
- package/dist/core/artifact-graph/state.js +54 -0
- package/dist/core/artifact-graph/types.d.ts +45 -0
- package/dist/core/artifact-graph/types.js +43 -0
- package/dist/core/command-generation/adapters/amazon-q.d.ts +13 -0
- package/dist/core/command-generation/adapters/amazon-q.js +26 -0
- package/dist/core/command-generation/adapters/antigravity.d.ts +13 -0
- package/dist/core/command-generation/adapters/antigravity.js +26 -0
- package/dist/core/command-generation/adapters/auggie.d.ts +13 -0
- package/dist/core/command-generation/adapters/auggie.js +27 -0
- package/dist/core/command-generation/adapters/claude.d.ts +13 -0
- package/dist/core/command-generation/adapters/claude.js +50 -0
- package/dist/core/command-generation/adapters/cline.d.ts +14 -0
- package/dist/core/command-generation/adapters/cline.js +27 -0
- package/dist/core/command-generation/adapters/codebuddy.d.ts +13 -0
- package/dist/core/command-generation/adapters/codebuddy.js +28 -0
- package/dist/core/command-generation/adapters/codex.d.ts +13 -0
- package/dist/core/command-generation/adapters/codex.js +27 -0
- package/dist/core/command-generation/adapters/continue.d.ts +13 -0
- package/dist/core/command-generation/adapters/continue.js +28 -0
- package/dist/core/command-generation/adapters/costrict.d.ts +13 -0
- package/dist/core/command-generation/adapters/costrict.js +27 -0
- package/dist/core/command-generation/adapters/crush.d.ts +13 -0
- package/dist/core/command-generation/adapters/crush.js +30 -0
- package/dist/core/command-generation/adapters/cursor.d.ts +14 -0
- package/dist/core/command-generation/adapters/cursor.js +44 -0
- package/dist/core/command-generation/adapters/factory.d.ts +13 -0
- package/dist/core/command-generation/adapters/factory.js +27 -0
- package/dist/core/command-generation/adapters/gemini.d.ts +13 -0
- package/dist/core/command-generation/adapters/gemini.js +26 -0
- package/dist/core/command-generation/adapters/github-copilot.d.ts +13 -0
- package/dist/core/command-generation/adapters/github-copilot.js +26 -0
- package/dist/core/command-generation/adapters/iflow.d.ts +13 -0
- package/dist/core/command-generation/adapters/iflow.js +29 -0
- package/dist/core/command-generation/adapters/index.d.ts +27 -0
- package/dist/core/command-generation/adapters/index.js +27 -0
- package/dist/core/command-generation/adapters/kilocode.d.ts +14 -0
- package/dist/core/command-generation/adapters/kilocode.js +23 -0
- package/dist/core/command-generation/adapters/opencode.d.ts +13 -0
- package/dist/core/command-generation/adapters/opencode.js +26 -0
- package/dist/core/command-generation/adapters/qoder.d.ts +13 -0
- package/dist/core/command-generation/adapters/qoder.js +30 -0
- package/dist/core/command-generation/adapters/qwen.d.ts +13 -0
- package/dist/core/command-generation/adapters/qwen.js +26 -0
- package/dist/core/command-generation/adapters/roocode.d.ts +14 -0
- package/dist/core/command-generation/adapters/roocode.js +27 -0
- package/dist/core/command-generation/adapters/windsurf.d.ts +14 -0
- package/dist/core/command-generation/adapters/windsurf.js +51 -0
- package/dist/core/command-generation/generator.d.ts +21 -0
- package/dist/core/command-generation/generator.js +27 -0
- package/dist/core/command-generation/index.d.ts +22 -0
- package/dist/core/command-generation/index.js +24 -0
- package/dist/core/command-generation/registry.d.ts +36 -0
- package/dist/core/command-generation/registry.js +88 -0
- package/dist/core/command-generation/types.d.ts +55 -0
- package/dist/core/command-generation/types.js +8 -0
- package/dist/core/completions/command-registry.d.ts +7 -0
- package/dist/core/completions/command-registry.js +456 -0
- package/dist/core/completions/completion-provider.d.ts +60 -0
- package/dist/core/completions/completion-provider.js +102 -0
- package/dist/core/completions/factory.d.ts +64 -0
- package/dist/core/completions/factory.js +75 -0
- package/dist/core/completions/generators/bash-generator.d.ts +32 -0
- package/dist/core/completions/generators/bash-generator.js +174 -0
- package/dist/core/completions/generators/fish-generator.d.ts +32 -0
- package/dist/core/completions/generators/fish-generator.js +157 -0
- package/dist/core/completions/generators/powershell-generator.d.ts +33 -0
- package/dist/core/completions/generators/powershell-generator.js +207 -0
- package/dist/core/completions/generators/zsh-generator.d.ts +44 -0
- package/dist/core/completions/generators/zsh-generator.js +250 -0
- package/dist/core/completions/installers/bash-installer.d.ts +87 -0
- package/dist/core/completions/installers/bash-installer.js +318 -0
- package/dist/core/completions/installers/fish-installer.d.ts +43 -0
- package/dist/core/completions/installers/fish-installer.js +143 -0
- package/dist/core/completions/installers/powershell-installer.d.ts +88 -0
- package/dist/core/completions/installers/powershell-installer.js +327 -0
- package/dist/core/completions/installers/zsh-installer.d.ts +125 -0
- package/dist/core/completions/installers/zsh-installer.js +449 -0
- package/dist/core/completions/templates/bash-templates.d.ts +6 -0
- package/dist/core/completions/templates/bash-templates.js +24 -0
- package/dist/core/completions/templates/fish-templates.d.ts +7 -0
- package/dist/core/completions/templates/fish-templates.js +39 -0
- package/dist/core/completions/templates/powershell-templates.d.ts +6 -0
- package/dist/core/completions/templates/powershell-templates.js +25 -0
- package/dist/core/completions/templates/zsh-templates.d.ts +6 -0
- package/dist/core/completions/templates/zsh-templates.js +36 -0
- package/dist/core/completions/types.d.ts +79 -0
- package/dist/core/completions/types.js +2 -0
- package/dist/core/config-prompts.d.ts +9 -0
- package/dist/core/config-prompts.js +34 -0
- package/dist/core/config-schema.d.ts +76 -0
- package/dist/core/config-schema.js +200 -0
- package/dist/core/config.d.ts +17 -0
- package/dist/core/config.js +30 -0
- package/dist/core/converters/json-converter.d.ts +6 -0
- package/dist/core/converters/json-converter.js +51 -0
- package/dist/core/global-config.d.ts +39 -0
- package/dist/core/global-config.js +115 -0
- package/dist/core/index.d.ts +2 -0
- package/dist/core/index.js +3 -0
- package/dist/core/init.d.ts +32 -0
- package/dist/core/init.js +433 -0
- package/dist/core/legacy-cleanup.d.ts +162 -0
- package/dist/core/legacy-cleanup.js +501 -0
- package/dist/core/list.d.ts +9 -0
- package/dist/core/list.js +171 -0
- package/dist/core/parsers/change-parser.d.ts +13 -0
- package/dist/core/parsers/change-parser.js +193 -0
- package/dist/core/parsers/markdown-parser.d.ts +22 -0
- package/dist/core/parsers/markdown-parser.js +187 -0
- package/dist/core/parsers/requirement-blocks.d.ts +37 -0
- package/dist/core/parsers/requirement-blocks.js +201 -0
- package/dist/core/project-config.d.ts +64 -0
- package/dist/core/project-config.js +223 -0
- package/dist/core/schemas/base.schema.d.ts +13 -0
- package/dist/core/schemas/base.schema.js +13 -0
- package/dist/core/schemas/change.schema.d.ts +73 -0
- package/dist/core/schemas/change.schema.js +31 -0
- package/dist/core/schemas/index.d.ts +4 -0
- package/dist/core/schemas/index.js +4 -0
- package/dist/core/schemas/spec.schema.d.ts +18 -0
- package/dist/core/schemas/spec.schema.js +15 -0
- package/dist/core/shared/index.d.ts +8 -0
- package/dist/core/shared/index.js +8 -0
- package/dist/core/shared/skill-generation.d.ts +41 -0
- package/dist/core/shared/skill-generation.js +74 -0
- package/dist/core/shared/tool-detection.d.ts +66 -0
- package/dist/core/shared/tool-detection.js +140 -0
- package/dist/core/specs-apply.d.ts +73 -0
- package/dist/core/specs-apply.js +384 -0
- package/dist/core/styles/palette.d.ts +7 -0
- package/dist/core/styles/palette.js +8 -0
- package/dist/core/templates/index.d.ts +8 -0
- package/dist/core/templates/index.js +9 -0
- package/dist/core/templates/skill-templates.d.ts +112 -0
- package/dist/core/templates/skill-templates.js +2893 -0
- package/dist/core/update.d.ts +42 -0
- package/dist/core/update.js +306 -0
- package/dist/core/validation/constants.d.ts +34 -0
- package/dist/core/validation/constants.js +40 -0
- package/dist/core/validation/types.d.ts +18 -0
- package/dist/core/validation/types.js +2 -0
- package/dist/core/validation/validator.d.ts +33 -0
- package/dist/core/validation/validator.js +409 -0
- package/dist/core/view.d.ts +8 -0
- package/dist/core/view.js +168 -0
- package/dist/index.d.ts +3 -0
- package/dist/index.js +3 -0
- package/dist/prompts/searchable-multi-select.d.ts +27 -0
- package/dist/prompts/searchable-multi-select.js +149 -0
- package/dist/telemetry/config.d.ts +32 -0
- package/dist/telemetry/config.js +68 -0
- package/dist/telemetry/index.d.ts +31 -0
- package/dist/telemetry/index.js +145 -0
- package/dist/ui/ascii-patterns.d.ts +16 -0
- package/dist/ui/ascii-patterns.js +133 -0
- package/dist/ui/welcome-screen.d.ts +10 -0
- package/dist/ui/welcome-screen.js +146 -0
- package/dist/utils/change-metadata.d.ts +51 -0
- package/dist/utils/change-metadata.js +147 -0
- package/dist/utils/change-utils.d.ts +62 -0
- package/dist/utils/change-utils.js +121 -0
- package/dist/utils/file-system.d.ts +36 -0
- package/dist/utils/file-system.js +281 -0
- package/dist/utils/index.d.ts +5 -0
- package/dist/utils/index.js +7 -0
- package/dist/utils/interactive.d.ts +18 -0
- package/dist/utils/interactive.js +21 -0
- package/dist/utils/item-discovery.d.ts +4 -0
- package/dist/utils/item-discovery.js +72 -0
- package/dist/utils/match.d.ts +3 -0
- package/dist/utils/match.js +22 -0
- package/dist/utils/shell-detection.d.ts +20 -0
- package/dist/utils/shell-detection.js +41 -0
- package/dist/utils/task-progress.d.ts +8 -0
- package/dist/utils/task-progress.js +36 -0
- package/package.json +84 -0
- package/schemas/spec-driven/schema.yaml +148 -0
- package/schemas/spec-driven/templates/design.md +19 -0
- package/schemas/spec-driven/templates/proposal.md +23 -0
- package/schemas/spec-driven/templates/spec.md +8 -0
- package/schemas/spec-driven/templates/tasks.md +9 -0
- package/schemas/tdd/schema.yaml +213 -0
- package/schemas/tdd/templates/docs.md +15 -0
- package/schemas/tdd/templates/implementation.md +11 -0
- package/schemas/tdd/templates/spec.md +11 -0
- package/schemas/tdd/templates/test.md +11 -0
- package/scripts/postinstall.js +147 -0
|
@@ -0,0 +1,9 @@
|
|
|
1
|
+
import type { ProjectConfig } from './project-config.js';
|
|
2
|
+
/**
|
|
3
|
+
* Serialize config to YAML string with helpful comments.
|
|
4
|
+
*
|
|
5
|
+
* @param config - Partial config object (schema required, context/rules optional)
|
|
6
|
+
* @returns YAML string ready to write to file
|
|
7
|
+
*/
|
|
8
|
+
export declare function serializeConfig(config: Partial<ProjectConfig>): string;
|
|
9
|
+
//# sourceMappingURL=config-prompts.d.ts.map
|
|
@@ -0,0 +1,34 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Serialize config to YAML string with helpful comments.
|
|
3
|
+
*
|
|
4
|
+
* @param config - Partial config object (schema required, context/rules optional)
|
|
5
|
+
* @returns YAML string ready to write to file
|
|
6
|
+
*/
|
|
7
|
+
export function serializeConfig(config) {
|
|
8
|
+
const lines = [];
|
|
9
|
+
// Schema (required)
|
|
10
|
+
lines.push(`schema: ${config.schema}`);
|
|
11
|
+
lines.push('');
|
|
12
|
+
// Context section with comments
|
|
13
|
+
lines.push('# Project context (optional)');
|
|
14
|
+
lines.push('# This is shown to AI when creating artifacts.');
|
|
15
|
+
lines.push('# Add your tech stack, conventions, style guides, domain knowledge, etc.');
|
|
16
|
+
lines.push('# Example:');
|
|
17
|
+
lines.push('# context: |');
|
|
18
|
+
lines.push('# Tech stack: TypeScript, React, Node.js');
|
|
19
|
+
lines.push('# We use conventional commits');
|
|
20
|
+
lines.push('# Domain: e-commerce platform');
|
|
21
|
+
lines.push('');
|
|
22
|
+
// Rules section with comments
|
|
23
|
+
lines.push('# Per-artifact rules (optional)');
|
|
24
|
+
lines.push('# Add custom rules for specific artifacts.');
|
|
25
|
+
lines.push('# Example:');
|
|
26
|
+
lines.push('# rules:');
|
|
27
|
+
lines.push('# proposal:');
|
|
28
|
+
lines.push('# - Keep proposals under 500 words');
|
|
29
|
+
lines.push('# - Always include a "Non-goals" section');
|
|
30
|
+
lines.push('# tasks:');
|
|
31
|
+
lines.push('# - Break tasks into chunks of max 2 hours');
|
|
32
|
+
return lines.join('\n') + '\n';
|
|
33
|
+
}
|
|
34
|
+
//# sourceMappingURL=config-prompts.js.map
|
|
@@ -0,0 +1,76 @@
|
|
|
1
|
+
import { z } from 'zod';
|
|
2
|
+
/**
|
|
3
|
+
* Zod schema for global OpenSpec configuration.
|
|
4
|
+
* Uses passthrough() to preserve unknown fields for forward compatibility.
|
|
5
|
+
*/
|
|
6
|
+
export declare const GlobalConfigSchema: z.ZodObject<{
|
|
7
|
+
featureFlags: z.ZodDefault<z.ZodOptional<z.ZodRecord<z.ZodString, z.ZodBoolean>>>;
|
|
8
|
+
}, z.core.$loose>;
|
|
9
|
+
export type GlobalConfigType = z.infer<typeof GlobalConfigSchema>;
|
|
10
|
+
/**
|
|
11
|
+
* Default configuration values.
|
|
12
|
+
*/
|
|
13
|
+
export declare const DEFAULT_CONFIG: GlobalConfigType;
|
|
14
|
+
/**
|
|
15
|
+
* Validate a config key path for CLI set operations.
|
|
16
|
+
* Unknown top-level keys are rejected unless explicitly allowed by the caller.
|
|
17
|
+
*/
|
|
18
|
+
export declare function validateConfigKeyPath(path: string): {
|
|
19
|
+
valid: boolean;
|
|
20
|
+
reason?: string;
|
|
21
|
+
};
|
|
22
|
+
/**
|
|
23
|
+
* Get a nested value from an object using dot notation.
|
|
24
|
+
*
|
|
25
|
+
* @param obj - The object to access
|
|
26
|
+
* @param path - Dot-separated path (e.g., "featureFlags.someFlag")
|
|
27
|
+
* @returns The value at the path, or undefined if not found
|
|
28
|
+
*/
|
|
29
|
+
export declare function getNestedValue(obj: Record<string, unknown>, path: string): unknown;
|
|
30
|
+
/**
|
|
31
|
+
* Set a nested value in an object using dot notation.
|
|
32
|
+
* Creates intermediate objects as needed.
|
|
33
|
+
*
|
|
34
|
+
* @param obj - The object to modify (mutated in place)
|
|
35
|
+
* @param path - Dot-separated path (e.g., "featureFlags.someFlag")
|
|
36
|
+
* @param value - The value to set
|
|
37
|
+
*/
|
|
38
|
+
export declare function setNestedValue(obj: Record<string, unknown>, path: string, value: unknown): void;
|
|
39
|
+
/**
|
|
40
|
+
* Delete a nested value from an object using dot notation.
|
|
41
|
+
*
|
|
42
|
+
* @param obj - The object to modify (mutated in place)
|
|
43
|
+
* @param path - Dot-separated path (e.g., "featureFlags.someFlag")
|
|
44
|
+
* @returns true if the key existed and was deleted, false otherwise
|
|
45
|
+
*/
|
|
46
|
+
export declare function deleteNestedValue(obj: Record<string, unknown>, path: string): boolean;
|
|
47
|
+
/**
|
|
48
|
+
* Coerce a string value to its appropriate type.
|
|
49
|
+
* - "true" / "false" -> boolean
|
|
50
|
+
* - Numeric strings -> number
|
|
51
|
+
* - Everything else -> string
|
|
52
|
+
*
|
|
53
|
+
* @param value - The string value to coerce
|
|
54
|
+
* @param forceString - If true, always return the value as a string
|
|
55
|
+
* @returns The coerced value
|
|
56
|
+
*/
|
|
57
|
+
export declare function coerceValue(value: string, forceString?: boolean): string | number | boolean;
|
|
58
|
+
/**
|
|
59
|
+
* Format a value for YAML-like display.
|
|
60
|
+
*
|
|
61
|
+
* @param value - The value to format
|
|
62
|
+
* @param indent - Current indentation level
|
|
63
|
+
* @returns Formatted string
|
|
64
|
+
*/
|
|
65
|
+
export declare function formatValueYaml(value: unknown, indent?: number): string;
|
|
66
|
+
/**
|
|
67
|
+
* Validate a configuration object against the schema.
|
|
68
|
+
*
|
|
69
|
+
* @param config - The configuration to validate
|
|
70
|
+
* @returns Validation result with success status and optional error message
|
|
71
|
+
*/
|
|
72
|
+
export declare function validateConfig(config: unknown): {
|
|
73
|
+
success: boolean;
|
|
74
|
+
error?: string;
|
|
75
|
+
};
|
|
76
|
+
//# sourceMappingURL=config-schema.d.ts.map
|
|
@@ -0,0 +1,200 @@
|
|
|
1
|
+
import { z } from 'zod';
|
|
2
|
+
/**
|
|
3
|
+
* Zod schema for global OpenSpec configuration.
|
|
4
|
+
* Uses passthrough() to preserve unknown fields for forward compatibility.
|
|
5
|
+
*/
|
|
6
|
+
export const GlobalConfigSchema = z
|
|
7
|
+
.object({
|
|
8
|
+
featureFlags: z
|
|
9
|
+
.record(z.string(), z.boolean())
|
|
10
|
+
.optional()
|
|
11
|
+
.default({}),
|
|
12
|
+
})
|
|
13
|
+
.passthrough();
|
|
14
|
+
/**
|
|
15
|
+
* Default configuration values.
|
|
16
|
+
*/
|
|
17
|
+
export const DEFAULT_CONFIG = {
|
|
18
|
+
featureFlags: {},
|
|
19
|
+
};
|
|
20
|
+
const KNOWN_TOP_LEVEL_KEYS = new Set(Object.keys(DEFAULT_CONFIG));
|
|
21
|
+
/**
|
|
22
|
+
* Validate a config key path for CLI set operations.
|
|
23
|
+
* Unknown top-level keys are rejected unless explicitly allowed by the caller.
|
|
24
|
+
*/
|
|
25
|
+
export function validateConfigKeyPath(path) {
|
|
26
|
+
const rawKeys = path.split('.');
|
|
27
|
+
if (rawKeys.length === 0 || rawKeys.some((key) => key.trim() === '')) {
|
|
28
|
+
return { valid: false, reason: 'Key path must not be empty' };
|
|
29
|
+
}
|
|
30
|
+
const rootKey = rawKeys[0];
|
|
31
|
+
if (!KNOWN_TOP_LEVEL_KEYS.has(rootKey)) {
|
|
32
|
+
return { valid: false, reason: `Unknown top-level key "${rootKey}"` };
|
|
33
|
+
}
|
|
34
|
+
if (rootKey === 'featureFlags') {
|
|
35
|
+
if (rawKeys.length > 2) {
|
|
36
|
+
return { valid: false, reason: 'featureFlags values are booleans and do not support nested keys' };
|
|
37
|
+
}
|
|
38
|
+
return { valid: true };
|
|
39
|
+
}
|
|
40
|
+
if (rawKeys.length > 1) {
|
|
41
|
+
return { valid: false, reason: `"${rootKey}" does not support nested keys` };
|
|
42
|
+
}
|
|
43
|
+
return { valid: true };
|
|
44
|
+
}
|
|
45
|
+
/**
|
|
46
|
+
* Get a nested value from an object using dot notation.
|
|
47
|
+
*
|
|
48
|
+
* @param obj - The object to access
|
|
49
|
+
* @param path - Dot-separated path (e.g., "featureFlags.someFlag")
|
|
50
|
+
* @returns The value at the path, or undefined if not found
|
|
51
|
+
*/
|
|
52
|
+
export function getNestedValue(obj, path) {
|
|
53
|
+
const keys = path.split('.');
|
|
54
|
+
let current = obj;
|
|
55
|
+
for (const key of keys) {
|
|
56
|
+
if (current === null || current === undefined) {
|
|
57
|
+
return undefined;
|
|
58
|
+
}
|
|
59
|
+
if (typeof current !== 'object') {
|
|
60
|
+
return undefined;
|
|
61
|
+
}
|
|
62
|
+
current = current[key];
|
|
63
|
+
}
|
|
64
|
+
return current;
|
|
65
|
+
}
|
|
66
|
+
/**
|
|
67
|
+
* Set a nested value in an object using dot notation.
|
|
68
|
+
* Creates intermediate objects as needed.
|
|
69
|
+
*
|
|
70
|
+
* @param obj - The object to modify (mutated in place)
|
|
71
|
+
* @param path - Dot-separated path (e.g., "featureFlags.someFlag")
|
|
72
|
+
* @param value - The value to set
|
|
73
|
+
*/
|
|
74
|
+
export function setNestedValue(obj, path, value) {
|
|
75
|
+
const keys = path.split('.');
|
|
76
|
+
let current = obj;
|
|
77
|
+
for (let i = 0; i < keys.length - 1; i++) {
|
|
78
|
+
const key = keys[i];
|
|
79
|
+
if (current[key] === undefined || current[key] === null || typeof current[key] !== 'object') {
|
|
80
|
+
current[key] = {};
|
|
81
|
+
}
|
|
82
|
+
current = current[key];
|
|
83
|
+
}
|
|
84
|
+
const lastKey = keys[keys.length - 1];
|
|
85
|
+
current[lastKey] = value;
|
|
86
|
+
}
|
|
87
|
+
/**
|
|
88
|
+
* Delete a nested value from an object using dot notation.
|
|
89
|
+
*
|
|
90
|
+
* @param obj - The object to modify (mutated in place)
|
|
91
|
+
* @param path - Dot-separated path (e.g., "featureFlags.someFlag")
|
|
92
|
+
* @returns true if the key existed and was deleted, false otherwise
|
|
93
|
+
*/
|
|
94
|
+
export function deleteNestedValue(obj, path) {
|
|
95
|
+
const keys = path.split('.');
|
|
96
|
+
let current = obj;
|
|
97
|
+
for (let i = 0; i < keys.length - 1; i++) {
|
|
98
|
+
const key = keys[i];
|
|
99
|
+
if (current[key] === undefined || current[key] === null || typeof current[key] !== 'object') {
|
|
100
|
+
return false;
|
|
101
|
+
}
|
|
102
|
+
current = current[key];
|
|
103
|
+
}
|
|
104
|
+
const lastKey = keys[keys.length - 1];
|
|
105
|
+
if (lastKey in current) {
|
|
106
|
+
delete current[lastKey];
|
|
107
|
+
return true;
|
|
108
|
+
}
|
|
109
|
+
return false;
|
|
110
|
+
}
|
|
111
|
+
/**
|
|
112
|
+
* Coerce a string value to its appropriate type.
|
|
113
|
+
* - "true" / "false" -> boolean
|
|
114
|
+
* - Numeric strings -> number
|
|
115
|
+
* - Everything else -> string
|
|
116
|
+
*
|
|
117
|
+
* @param value - The string value to coerce
|
|
118
|
+
* @param forceString - If true, always return the value as a string
|
|
119
|
+
* @returns The coerced value
|
|
120
|
+
*/
|
|
121
|
+
export function coerceValue(value, forceString = false) {
|
|
122
|
+
if (forceString) {
|
|
123
|
+
return value;
|
|
124
|
+
}
|
|
125
|
+
// Boolean coercion
|
|
126
|
+
if (value === 'true') {
|
|
127
|
+
return true;
|
|
128
|
+
}
|
|
129
|
+
if (value === 'false') {
|
|
130
|
+
return false;
|
|
131
|
+
}
|
|
132
|
+
// Number coercion - must be a valid finite number
|
|
133
|
+
const num = Number(value);
|
|
134
|
+
if (!isNaN(num) && isFinite(num) && value.trim() !== '') {
|
|
135
|
+
return num;
|
|
136
|
+
}
|
|
137
|
+
return value;
|
|
138
|
+
}
|
|
139
|
+
/**
|
|
140
|
+
* Format a value for YAML-like display.
|
|
141
|
+
*
|
|
142
|
+
* @param value - The value to format
|
|
143
|
+
* @param indent - Current indentation level
|
|
144
|
+
* @returns Formatted string
|
|
145
|
+
*/
|
|
146
|
+
export function formatValueYaml(value, indent = 0) {
|
|
147
|
+
const indentStr = ' '.repeat(indent);
|
|
148
|
+
if (value === null || value === undefined) {
|
|
149
|
+
return 'null';
|
|
150
|
+
}
|
|
151
|
+
if (typeof value === 'boolean' || typeof value === 'number') {
|
|
152
|
+
return String(value);
|
|
153
|
+
}
|
|
154
|
+
if (typeof value === 'string') {
|
|
155
|
+
return value;
|
|
156
|
+
}
|
|
157
|
+
if (Array.isArray(value)) {
|
|
158
|
+
if (value.length === 0) {
|
|
159
|
+
return '[]';
|
|
160
|
+
}
|
|
161
|
+
return value.map((item) => `${indentStr}- ${formatValueYaml(item, indent + 1)}`).join('\n');
|
|
162
|
+
}
|
|
163
|
+
if (typeof value === 'object') {
|
|
164
|
+
const entries = Object.entries(value);
|
|
165
|
+
if (entries.length === 0) {
|
|
166
|
+
return '{}';
|
|
167
|
+
}
|
|
168
|
+
return entries
|
|
169
|
+
.map(([key, val]) => {
|
|
170
|
+
const formattedVal = formatValueYaml(val, indent + 1);
|
|
171
|
+
if (typeof val === 'object' && val !== null && Object.keys(val).length > 0) {
|
|
172
|
+
return `${indentStr}${key}:\n${formattedVal}`;
|
|
173
|
+
}
|
|
174
|
+
return `${indentStr}${key}: ${formattedVal}`;
|
|
175
|
+
})
|
|
176
|
+
.join('\n');
|
|
177
|
+
}
|
|
178
|
+
return String(value);
|
|
179
|
+
}
|
|
180
|
+
/**
|
|
181
|
+
* Validate a configuration object against the schema.
|
|
182
|
+
*
|
|
183
|
+
* @param config - The configuration to validate
|
|
184
|
+
* @returns Validation result with success status and optional error message
|
|
185
|
+
*/
|
|
186
|
+
export function validateConfig(config) {
|
|
187
|
+
try {
|
|
188
|
+
GlobalConfigSchema.parse(config);
|
|
189
|
+
return { success: true };
|
|
190
|
+
}
|
|
191
|
+
catch (error) {
|
|
192
|
+
if (error instanceof z.ZodError) {
|
|
193
|
+
const zodError = error;
|
|
194
|
+
const messages = zodError.issues.map((e) => `${e.path.join('.')}: ${e.message}`);
|
|
195
|
+
return { success: false, error: messages.join('; ') };
|
|
196
|
+
}
|
|
197
|
+
return { success: false, error: 'Unknown validation error' };
|
|
198
|
+
}
|
|
199
|
+
}
|
|
200
|
+
//# sourceMappingURL=config-schema.js.map
|
|
@@ -0,0 +1,17 @@
|
|
|
1
|
+
export declare const OPENSPEC_DIR_NAME = "openspec";
|
|
2
|
+
export declare const OPENSPEC_MARKERS: {
|
|
3
|
+
start: string;
|
|
4
|
+
end: string;
|
|
5
|
+
};
|
|
6
|
+
export interface OpenSpecConfig {
|
|
7
|
+
aiTools: string[];
|
|
8
|
+
}
|
|
9
|
+
export interface AIToolOption {
|
|
10
|
+
name: string;
|
|
11
|
+
value: string;
|
|
12
|
+
available: boolean;
|
|
13
|
+
successLabel?: string;
|
|
14
|
+
skillsDir?: string;
|
|
15
|
+
}
|
|
16
|
+
export declare const AI_TOOLS: AIToolOption[];
|
|
17
|
+
//# sourceMappingURL=config.d.ts.map
|
|
@@ -0,0 +1,30 @@
|
|
|
1
|
+
export const OPENSPEC_DIR_NAME = 'openspec';
|
|
2
|
+
export const OPENSPEC_MARKERS = {
|
|
3
|
+
start: '<!-- OPENSPEC:START -->',
|
|
4
|
+
end: '<!-- OPENSPEC:END -->'
|
|
5
|
+
};
|
|
6
|
+
export const AI_TOOLS = [
|
|
7
|
+
{ name: 'Amazon Q Developer', value: 'amazon-q', available: true, successLabel: 'Amazon Q Developer', skillsDir: '.amazonq' },
|
|
8
|
+
{ name: 'Antigravity', value: 'antigravity', available: true, successLabel: 'Antigravity', skillsDir: '.agent' },
|
|
9
|
+
{ name: 'Auggie (Augment CLI)', value: 'auggie', available: true, successLabel: 'Auggie', skillsDir: '.augment' },
|
|
10
|
+
{ name: 'Claude Code', value: 'claude', available: true, successLabel: 'Claude Code', skillsDir: '.claude' },
|
|
11
|
+
{ name: 'Cline', value: 'cline', available: true, successLabel: 'Cline', skillsDir: '.cline' },
|
|
12
|
+
{ name: 'Codex', value: 'codex', available: true, successLabel: 'Codex', skillsDir: '.codex' },
|
|
13
|
+
{ name: 'CodeBuddy Code (CLI)', value: 'codebuddy', available: true, successLabel: 'CodeBuddy Code', skillsDir: '.codebuddy' },
|
|
14
|
+
{ name: 'Continue', value: 'continue', available: true, successLabel: 'Continue (VS Code / JetBrains / Cli)', skillsDir: '.continue' },
|
|
15
|
+
{ name: 'CoStrict', value: 'costrict', available: true, successLabel: 'CoStrict', skillsDir: '.cospec' },
|
|
16
|
+
{ name: 'Crush', value: 'crush', available: true, successLabel: 'Crush', skillsDir: '.crush' },
|
|
17
|
+
{ name: 'Cursor', value: 'cursor', available: true, successLabel: 'Cursor', skillsDir: '.cursor' },
|
|
18
|
+
{ name: 'Factory Droid', value: 'factory', available: true, successLabel: 'Factory Droid', skillsDir: '.factory' },
|
|
19
|
+
{ name: 'Gemini CLI', value: 'gemini', available: true, successLabel: 'Gemini CLI', skillsDir: '.gemini' },
|
|
20
|
+
{ name: 'GitHub Copilot', value: 'github-copilot', available: true, successLabel: 'GitHub Copilot', skillsDir: '.github' },
|
|
21
|
+
{ name: 'iFlow', value: 'iflow', available: true, successLabel: 'iFlow', skillsDir: '.iflow' },
|
|
22
|
+
{ name: 'Kilo Code', value: 'kilocode', available: true, successLabel: 'Kilo Code', skillsDir: '.kilocode' },
|
|
23
|
+
{ name: 'OpenCode', value: 'opencode', available: true, successLabel: 'OpenCode', skillsDir: '.opencode' },
|
|
24
|
+
{ name: 'Qoder', value: 'qoder', available: true, successLabel: 'Qoder', skillsDir: '.qoder' },
|
|
25
|
+
{ name: 'Qwen Code', value: 'qwen', available: true, successLabel: 'Qwen Code', skillsDir: '.qwen' },
|
|
26
|
+
{ name: 'RooCode', value: 'roocode', available: true, successLabel: 'RooCode', skillsDir: '.roo' },
|
|
27
|
+
{ name: 'Windsurf', value: 'windsurf', available: true, successLabel: 'Windsurf', skillsDir: '.windsurf' },
|
|
28
|
+
{ name: 'AGENTS.md (works with Amp, VS Code, …)', value: 'agents', available: false, successLabel: 'your AGENTS.md-compatible assistant' }
|
|
29
|
+
];
|
|
30
|
+
//# sourceMappingURL=config.js.map
|
|
@@ -0,0 +1,51 @@
|
|
|
1
|
+
import { readFileSync } from 'fs';
|
|
2
|
+
import path from 'path';
|
|
3
|
+
import { MarkdownParser } from '../parsers/markdown-parser.js';
|
|
4
|
+
import { ChangeParser } from '../parsers/change-parser.js';
|
|
5
|
+
import { FileSystemUtils } from '../../utils/file-system.js';
|
|
6
|
+
export class JsonConverter {
|
|
7
|
+
convertSpecToJson(filePath) {
|
|
8
|
+
const content = readFileSync(filePath, 'utf-8');
|
|
9
|
+
const parser = new MarkdownParser(content);
|
|
10
|
+
const specName = this.extractNameFromPath(filePath);
|
|
11
|
+
const spec = parser.parseSpec(specName);
|
|
12
|
+
const jsonSpec = {
|
|
13
|
+
...spec,
|
|
14
|
+
metadata: {
|
|
15
|
+
...spec.metadata,
|
|
16
|
+
sourcePath: filePath,
|
|
17
|
+
},
|
|
18
|
+
};
|
|
19
|
+
return JSON.stringify(jsonSpec, null, 2);
|
|
20
|
+
}
|
|
21
|
+
async convertChangeToJson(filePath) {
|
|
22
|
+
const content = readFileSync(filePath, 'utf-8');
|
|
23
|
+
const changeName = this.extractNameFromPath(filePath);
|
|
24
|
+
const changeDir = path.dirname(filePath);
|
|
25
|
+
const parser = new ChangeParser(content, changeDir);
|
|
26
|
+
const change = await parser.parseChangeWithDeltas(changeName);
|
|
27
|
+
const jsonChange = {
|
|
28
|
+
...change,
|
|
29
|
+
metadata: {
|
|
30
|
+
...change.metadata,
|
|
31
|
+
sourcePath: filePath,
|
|
32
|
+
},
|
|
33
|
+
};
|
|
34
|
+
return JSON.stringify(jsonChange, null, 2);
|
|
35
|
+
}
|
|
36
|
+
extractNameFromPath(filePath) {
|
|
37
|
+
const normalizedPath = FileSystemUtils.toPosixPath(filePath);
|
|
38
|
+
const parts = normalizedPath.split('/');
|
|
39
|
+
for (let i = parts.length - 1; i >= 0; i--) {
|
|
40
|
+
if (parts[i] === 'specs' || parts[i] === 'changes') {
|
|
41
|
+
if (i < parts.length - 1) {
|
|
42
|
+
return parts[i + 1];
|
|
43
|
+
}
|
|
44
|
+
}
|
|
45
|
+
}
|
|
46
|
+
const fileName = parts[parts.length - 1] ?? '';
|
|
47
|
+
const dotIndex = fileName.lastIndexOf('.');
|
|
48
|
+
return dotIndex > 0 ? fileName.slice(0, dotIndex) : fileName;
|
|
49
|
+
}
|
|
50
|
+
}
|
|
51
|
+
//# sourceMappingURL=json-converter.js.map
|
|
@@ -0,0 +1,39 @@
|
|
|
1
|
+
export declare const GLOBAL_CONFIG_DIR_NAME = "openspec";
|
|
2
|
+
export declare const GLOBAL_CONFIG_FILE_NAME = "config.json";
|
|
3
|
+
export declare const GLOBAL_DATA_DIR_NAME = "openspec";
|
|
4
|
+
export interface GlobalConfig {
|
|
5
|
+
featureFlags?: Record<string, boolean>;
|
|
6
|
+
}
|
|
7
|
+
/**
|
|
8
|
+
* Gets the global configuration directory path following XDG Base Directory Specification.
|
|
9
|
+
*
|
|
10
|
+
* - All platforms: $XDG_CONFIG_HOME/openspec/ if XDG_CONFIG_HOME is set
|
|
11
|
+
* - Unix/macOS fallback: ~/.config/openspec/
|
|
12
|
+
* - Windows fallback: %APPDATA%/openspec/
|
|
13
|
+
*/
|
|
14
|
+
export declare function getGlobalConfigDir(): string;
|
|
15
|
+
/**
|
|
16
|
+
* Gets the global data directory path following XDG Base Directory Specification.
|
|
17
|
+
* Used for user data like schema overrides.
|
|
18
|
+
*
|
|
19
|
+
* - All platforms: $XDG_DATA_HOME/openspec/ if XDG_DATA_HOME is set
|
|
20
|
+
* - Unix/macOS fallback: ~/.local/share/openspec/
|
|
21
|
+
* - Windows fallback: %LOCALAPPDATA%/openspec/
|
|
22
|
+
*/
|
|
23
|
+
export declare function getGlobalDataDir(): string;
|
|
24
|
+
/**
|
|
25
|
+
* Gets the path to the global config file.
|
|
26
|
+
*/
|
|
27
|
+
export declare function getGlobalConfigPath(): string;
|
|
28
|
+
/**
|
|
29
|
+
* Loads the global configuration from disk.
|
|
30
|
+
* Returns default configuration if file doesn't exist or is invalid.
|
|
31
|
+
* Merges loaded config with defaults to ensure new fields are available.
|
|
32
|
+
*/
|
|
33
|
+
export declare function getGlobalConfig(): GlobalConfig;
|
|
34
|
+
/**
|
|
35
|
+
* Saves the global configuration to disk.
|
|
36
|
+
* Creates the config directory if it doesn't exist.
|
|
37
|
+
*/
|
|
38
|
+
export declare function saveGlobalConfig(config: GlobalConfig): void;
|
|
39
|
+
//# sourceMappingURL=global-config.d.ts.map
|
|
@@ -0,0 +1,115 @@
|
|
|
1
|
+
import * as fs from 'node:fs';
|
|
2
|
+
import * as path from 'node:path';
|
|
3
|
+
import * as os from 'node:os';
|
|
4
|
+
// Constants
|
|
5
|
+
export const GLOBAL_CONFIG_DIR_NAME = 'openspec';
|
|
6
|
+
export const GLOBAL_CONFIG_FILE_NAME = 'config.json';
|
|
7
|
+
export const GLOBAL_DATA_DIR_NAME = 'openspec';
|
|
8
|
+
const DEFAULT_CONFIG = {
|
|
9
|
+
featureFlags: {}
|
|
10
|
+
};
|
|
11
|
+
/**
|
|
12
|
+
* Gets the global configuration directory path following XDG Base Directory Specification.
|
|
13
|
+
*
|
|
14
|
+
* - All platforms: $XDG_CONFIG_HOME/openspec/ if XDG_CONFIG_HOME is set
|
|
15
|
+
* - Unix/macOS fallback: ~/.config/openspec/
|
|
16
|
+
* - Windows fallback: %APPDATA%/openspec/
|
|
17
|
+
*/
|
|
18
|
+
export function getGlobalConfigDir() {
|
|
19
|
+
// XDG_CONFIG_HOME takes precedence on all platforms when explicitly set
|
|
20
|
+
const xdgConfigHome = process.env.XDG_CONFIG_HOME;
|
|
21
|
+
if (xdgConfigHome) {
|
|
22
|
+
return path.join(xdgConfigHome, GLOBAL_CONFIG_DIR_NAME);
|
|
23
|
+
}
|
|
24
|
+
const platform = os.platform();
|
|
25
|
+
if (platform === 'win32') {
|
|
26
|
+
// Windows: use %APPDATA%
|
|
27
|
+
const appData = process.env.APPDATA;
|
|
28
|
+
if (appData) {
|
|
29
|
+
return path.join(appData, GLOBAL_CONFIG_DIR_NAME);
|
|
30
|
+
}
|
|
31
|
+
// Fallback for Windows if APPDATA is not set
|
|
32
|
+
return path.join(os.homedir(), 'AppData', 'Roaming', GLOBAL_CONFIG_DIR_NAME);
|
|
33
|
+
}
|
|
34
|
+
// Unix/macOS fallback: ~/.config
|
|
35
|
+
return path.join(os.homedir(), '.config', GLOBAL_CONFIG_DIR_NAME);
|
|
36
|
+
}
|
|
37
|
+
/**
|
|
38
|
+
* Gets the global data directory path following XDG Base Directory Specification.
|
|
39
|
+
* Used for user data like schema overrides.
|
|
40
|
+
*
|
|
41
|
+
* - All platforms: $XDG_DATA_HOME/openspec/ if XDG_DATA_HOME is set
|
|
42
|
+
* - Unix/macOS fallback: ~/.local/share/openspec/
|
|
43
|
+
* - Windows fallback: %LOCALAPPDATA%/openspec/
|
|
44
|
+
*/
|
|
45
|
+
export function getGlobalDataDir() {
|
|
46
|
+
// XDG_DATA_HOME takes precedence on all platforms when explicitly set
|
|
47
|
+
const xdgDataHome = process.env.XDG_DATA_HOME;
|
|
48
|
+
if (xdgDataHome) {
|
|
49
|
+
return path.join(xdgDataHome, GLOBAL_DATA_DIR_NAME);
|
|
50
|
+
}
|
|
51
|
+
const platform = os.platform();
|
|
52
|
+
if (platform === 'win32') {
|
|
53
|
+
// Windows: use %LOCALAPPDATA%
|
|
54
|
+
const localAppData = process.env.LOCALAPPDATA;
|
|
55
|
+
if (localAppData) {
|
|
56
|
+
return path.join(localAppData, GLOBAL_DATA_DIR_NAME);
|
|
57
|
+
}
|
|
58
|
+
// Fallback for Windows if LOCALAPPDATA is not set
|
|
59
|
+
return path.join(os.homedir(), 'AppData', 'Local', GLOBAL_DATA_DIR_NAME);
|
|
60
|
+
}
|
|
61
|
+
// Unix/macOS fallback: ~/.local/share
|
|
62
|
+
return path.join(os.homedir(), '.local', 'share', GLOBAL_DATA_DIR_NAME);
|
|
63
|
+
}
|
|
64
|
+
/**
|
|
65
|
+
* Gets the path to the global config file.
|
|
66
|
+
*/
|
|
67
|
+
export function getGlobalConfigPath() {
|
|
68
|
+
return path.join(getGlobalConfigDir(), GLOBAL_CONFIG_FILE_NAME);
|
|
69
|
+
}
|
|
70
|
+
/**
|
|
71
|
+
* Loads the global configuration from disk.
|
|
72
|
+
* Returns default configuration if file doesn't exist or is invalid.
|
|
73
|
+
* Merges loaded config with defaults to ensure new fields are available.
|
|
74
|
+
*/
|
|
75
|
+
export function getGlobalConfig() {
|
|
76
|
+
const configPath = getGlobalConfigPath();
|
|
77
|
+
try {
|
|
78
|
+
if (!fs.existsSync(configPath)) {
|
|
79
|
+
return { ...DEFAULT_CONFIG };
|
|
80
|
+
}
|
|
81
|
+
const content = fs.readFileSync(configPath, 'utf-8');
|
|
82
|
+
const parsed = JSON.parse(content);
|
|
83
|
+
// Merge with defaults (loaded values take precedence)
|
|
84
|
+
return {
|
|
85
|
+
...DEFAULT_CONFIG,
|
|
86
|
+
...parsed,
|
|
87
|
+
// Deep merge featureFlags
|
|
88
|
+
featureFlags: {
|
|
89
|
+
...DEFAULT_CONFIG.featureFlags,
|
|
90
|
+
...(parsed.featureFlags || {})
|
|
91
|
+
}
|
|
92
|
+
};
|
|
93
|
+
}
|
|
94
|
+
catch (error) {
|
|
95
|
+
// Log warning for parse errors, but not for missing files
|
|
96
|
+
if (error instanceof SyntaxError) {
|
|
97
|
+
console.error(`Warning: Invalid JSON in ${configPath}, using defaults`);
|
|
98
|
+
}
|
|
99
|
+
return { ...DEFAULT_CONFIG };
|
|
100
|
+
}
|
|
101
|
+
}
|
|
102
|
+
/**
|
|
103
|
+
* Saves the global configuration to disk.
|
|
104
|
+
* Creates the config directory if it doesn't exist.
|
|
105
|
+
*/
|
|
106
|
+
export function saveGlobalConfig(config) {
|
|
107
|
+
const configDir = getGlobalConfigDir();
|
|
108
|
+
const configPath = getGlobalConfigPath();
|
|
109
|
+
// Create directory if it doesn't exist
|
|
110
|
+
if (!fs.existsSync(configDir)) {
|
|
111
|
+
fs.mkdirSync(configDir, { recursive: true });
|
|
112
|
+
}
|
|
113
|
+
fs.writeFileSync(configPath, JSON.stringify(config, null, 2) + '\n', 'utf-8');
|
|
114
|
+
}
|
|
115
|
+
//# sourceMappingURL=global-config.js.map
|
|
@@ -0,0 +1,3 @@
|
|
|
1
|
+
// Core OpenSpec logic will be implemented here
|
|
2
|
+
export { GLOBAL_CONFIG_DIR_NAME, GLOBAL_CONFIG_FILE_NAME, GLOBAL_DATA_DIR_NAME, getGlobalConfigDir, getGlobalConfigPath, getGlobalConfig, saveGlobalConfig, getGlobalDataDir } from './global-config.js';
|
|
3
|
+
//# sourceMappingURL=index.js.map
|
|
@@ -0,0 +1,32 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Init Command
|
|
3
|
+
*
|
|
4
|
+
* Sets up OpenSpec with Agent Skills and /opsx:* slash commands.
|
|
5
|
+
* This is the unified setup command that replaces both the old init and experimental commands.
|
|
6
|
+
*/
|
|
7
|
+
type InitCommandOptions = {
|
|
8
|
+
tools?: string;
|
|
9
|
+
force?: boolean;
|
|
10
|
+
interactive?: boolean;
|
|
11
|
+
};
|
|
12
|
+
export declare class InitCommand {
|
|
13
|
+
private readonly toolsArg?;
|
|
14
|
+
private readonly force;
|
|
15
|
+
private readonly interactiveOption?;
|
|
16
|
+
constructor(options?: InitCommandOptions);
|
|
17
|
+
execute(targetPath: string): Promise<void>;
|
|
18
|
+
private validate;
|
|
19
|
+
private canPromptInteractively;
|
|
20
|
+
private handleLegacyCleanup;
|
|
21
|
+
private performLegacyCleanup;
|
|
22
|
+
private getSelectedTools;
|
|
23
|
+
private resolveToolsArg;
|
|
24
|
+
private validateTools;
|
|
25
|
+
private createDirectoryStructure;
|
|
26
|
+
private generateSkillsAndCommands;
|
|
27
|
+
private createConfig;
|
|
28
|
+
private displaySuccessMessage;
|
|
29
|
+
private startSpinner;
|
|
30
|
+
}
|
|
31
|
+
export {};
|
|
32
|
+
//# sourceMappingURL=init.d.ts.map
|