@heyditto/cli 2.12.1 → 2.14.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.
@@ -0,0 +1,198 @@
1
+ import { mkdir, readFile, stat, writeFile } from "node:fs/promises";
2
+ import path from "node:path";
3
+ import { DittoConfigError, DittoConfigNotFound, loadDittoConfig, slugify, summarize } from "./load.js";
4
+ import { CONFIG_FILE, DITTO_DIR, MISE_FILE } from "./types.js";
5
+ import { MISE_TOOL_FOR_TYPE } from "../teleport/catalog.js";
6
+ import { discoverWorkspace } from "../teleport/workspace.js";
7
+ import { formatBytes } from "../teleport/types.js";
8
+ function out(line) {
9
+ process.stdout.write(line + "\n");
10
+ }
11
+ function err(line) {
12
+ process.stderr.write(line + "\n");
13
+ }
14
+ /** `heyditto repo init|validate|show` — the repository's `.ditto/` contract. */
15
+ export function registerConfigCommands(program, addExamples) {
16
+ const config = program.command("repo").description("scaffold, validate and inspect a repository's .ditto/ configuration");
17
+ addExamples(config
18
+ .command("init [path]")
19
+ .description("write a starter .ditto/ (config.toml + mise.toml) from the projects detected in a repository")
20
+ .option("--force", "overwrite existing .ditto files")
21
+ .action(cmdInit), ` heyditto repo init scaffold .ditto/ for the current repository
22
+ heyditto repo init ~/code/app scaffold for another checkout`);
23
+ config
24
+ .command("validate [path]")
25
+ .description("validate .ditto/config.toml, .ditto/endpoints/*.toml and the mise choice; exit 1 on any problem")
26
+ .option("--workspace <dir>", "parent folder whose .ditto/ supplies defaults")
27
+ .action(async (pathArg, options) => {
28
+ const dir = path.resolve(pathArg ?? process.cwd());
29
+ try {
30
+ const eff = await loadDittoConfig(dir, { workspaceDir: options.workspace });
31
+ for (const w of eff.warnings)
32
+ err(`warning: ${w}`);
33
+ out(`ok: ${path.join(DITTO_DIR, CONFIG_FILE)} is valid (schema v${eff.config.version}, ${Object.keys(eff.endpoints).length} endpoint(s), mise: ${eff.misePath || "none"}, digest ${summarize(eff).digest.slice(0, 12)})`);
34
+ }
35
+ catch (e) {
36
+ if (e instanceof DittoConfigNotFound) {
37
+ err(`no ${DITTO_DIR}/${CONFIG_FILE} in ${dir}; run \`heyditto repo init\` to create one`);
38
+ }
39
+ else if (e instanceof DittoConfigError) {
40
+ err(e.message);
41
+ }
42
+ else {
43
+ throw e;
44
+ }
45
+ process.exitCode = 1;
46
+ }
47
+ });
48
+ config
49
+ .command("show [path]")
50
+ .description("print the effective configuration with the layer each table came from")
51
+ .option("--workspace <dir>", "parent folder whose .ditto/ supplies defaults")
52
+ .option("--json", "machine-readable output")
53
+ .action(async (pathArg, options) => {
54
+ const dir = path.resolve(pathArg ?? process.cwd());
55
+ try {
56
+ const eff = await loadDittoConfig(dir, { workspaceDir: options.workspace });
57
+ if (options.json) {
58
+ out(JSON.stringify({ ...eff, summary: summarize(eff) }, null, 2));
59
+ return;
60
+ }
61
+ out(`repository: ${eff.config.repository.name} digest: ${summarize(eff).digest.slice(0, 12)} layers: ${eff.layers.join(" < ") || "defaults"}`);
62
+ for (const [table, src] of Object.entries(eff.sources).sort()) {
63
+ out(` ${table.padEnd(24)} ${src.layer}${src.path ? ` (${path.relative(dir, src.path)})` : ""}`);
64
+ }
65
+ out(` mise: ${eff.misePath || "none"}`);
66
+ for (const w of eff.warnings)
67
+ err(`warning: ${w}`);
68
+ }
69
+ catch (e) {
70
+ if (e instanceof DittoConfigNotFound || e instanceof DittoConfigError) {
71
+ err(e.message);
72
+ process.exitCode = 1;
73
+ return;
74
+ }
75
+ throw e;
76
+ }
77
+ });
78
+ }
79
+ async function cmdInit(pathArg, options) {
80
+ const dir = path.resolve(pathArg ?? process.cwd());
81
+ const discovery = await discoverWorkspace(dir, { maxDepth: 2 });
82
+ const types = [...new Set(discovery.projects.flatMap((p) => p.types))];
83
+ const tools = [...new Set(types.map((t) => MISE_TOOL_FOR_TYPE[t]).filter(Boolean))];
84
+ const dittoDir = path.join(dir, DITTO_DIR);
85
+ await mkdir(path.join(dittoDir, "endpoints"), { recursive: true });
86
+ const configPath = path.join(dittoDir, CONFIG_FILE);
87
+ const misePath = path.join(dittoDir, MISE_FILE);
88
+ const rootMise = path.join(dir, MISE_FILE);
89
+ if (!options.force && (await exists(configPath))) {
90
+ err(`${path.relative(process.cwd(), configPath)} exists; pass --force to overwrite`);
91
+ process.exitCode = 1;
92
+ return;
93
+ }
94
+ // repository.name must start with a letter or digit; slugify (kept identical to
95
+ // the backend's, which feeds the digest) can leave a leading underscore.
96
+ const name = slugify(path.basename(dir)).replace(/^_+/, "") || "repo";
97
+ const labels = discovery.projects.filter((p) => p.labels.length).map((p) => `${p.relPath}: ${p.labels.join(", ")}`);
98
+ const config = `# Ditto repository configuration — see https://heyditto.ai/docs/ditto-config
99
+ version = 1
100
+
101
+ [repository]
102
+ name = "${name}"
103
+ # default_endpoint = "work" # a name from .ditto/endpoints/ or an existing endpoint slug
104
+
105
+ [teleport]
106
+ # capture_roots = ["."]
107
+ # exclude = ["fixtures/large/"] # on top of the built-in and per-language rules
108
+ # include = ["vendor/"] # force a path back in
109
+ # required_mirrors = ["ditto-primary", "ditto-secondary"]
110
+
111
+ [teleport.harness]
112
+ kind = "auto" # auto | claude-code | codex | none
113
+ session = "latest" # latest | explicit
114
+
115
+ [teleport.offload]
116
+ unpushed = "refuse" # refuse | acknowledge
117
+
118
+ [environment]
119
+ ${(await exists(rootMise)) ? 'mise_config = "mise.toml"' : `mise_config = "${DITTO_DIR}/${MISE_FILE}"`}
120
+ # [environment.vars]
121
+ # DITTO_ENV = "local"
122
+ # [environment.secrets]
123
+ # OPENAI_API_KEY = "secret://openai/api-key" # references only, never values
124
+
125
+ [tasks]
126
+ # setup = "mise:setup"
127
+ # test = "npm test"
128
+
129
+ [policy.repair]
130
+ max_attempts = 3
131
+ install_only = true
132
+ `;
133
+ await writeFile(configPath, config);
134
+ out(`wrote ${path.relative(process.cwd(), configPath)}`);
135
+ if (!(await exists(rootMise)) && (options.force || !(await exists(misePath)))) {
136
+ const toolLines = tools.length ? tools.map((t) => `${t} = "latest" # pin a version before relying on it`).join("\n") : "# node = \"22\"";
137
+ await writeFile(misePath, `# Tools, environment and tasks for this repository (https://mise.jdx.dev).
138
+ # Detected: ${labels.join("; ") || "no known project types"}
139
+ [tools]
140
+ ${toolLines}
141
+
142
+ [env]
143
+ # NON-secret values only; secrets live in Ditto Secrets and are referenced from .ditto/config.toml
144
+
145
+ [tasks.setup]
146
+ run = "echo 'declare your setup here'"
147
+ `);
148
+ out(`wrote ${path.relative(process.cwd(), misePath)}`);
149
+ }
150
+ else if (await exists(rootMise)) {
151
+ out(`kept existing ${MISE_FILE} (declared as environment.mise_config)`);
152
+ }
153
+ await writeFile(path.join(dittoDir, ".gitignore"), "local.toml\n");
154
+ out(`wrote ${path.relative(process.cwd(), path.join(dittoDir, ".gitignore"))}`);
155
+ for (const l of labels)
156
+ out(` detected ${l}`);
157
+ out("next: review .ditto/config.toml, then `heyditto repo validate` and `heyditto teleport plan`");
158
+ }
159
+ async function exists(p) {
160
+ return stat(p).then(() => true, () => false);
161
+ }
162
+ /** Human rendering of a capture plan. */
163
+ export function formatCapturePlan(plan) {
164
+ const lines = [];
165
+ lines.push(`${plan.kind === "repo" ? "repository" : "folder"} ${plan.root}: ${plan.repos.length} repo(s), ${formatBytes(plan.totals.includedBytes)} to capture, ${formatBytes(plan.totals.excludedBytes)} excluded`);
166
+ for (const r of plan.repos) {
167
+ const kinds = r.projects.map((p) => `${p.relPath === "." ? "" : p.relPath + ": "}${p.labels.join("/") || "unknown"}`).join(", ");
168
+ lines.push(` ${r.relPath} [${r.kind}] ${kinds}`);
169
+ lines.push(` include ${formatBytes(r.includedBytes)} in ${r.includedFiles} files${r.estimatePartial ? " (estimate partial)" : ""}`);
170
+ for (const rule of r.rules.filter((x) => x.bytes > 0 || x.source === "config").sort((a, b) => b.bytes - a.bytes)) {
171
+ lines.push(` exclude ${rule.pattern.padEnd(40)} ${formatBytes(rule.bytes).padStart(10)} ${rule.reason}`);
172
+ }
173
+ if (r.excludedEstimatePartial)
174
+ lines.push(" note: excluded sizes are a lower bound (too many files to count)");
175
+ for (const inc of r.includes)
176
+ lines.push(` force-include ${inc} (.ditto teleport.include)`);
177
+ for (const t of r.trackedArtifacts)
178
+ lines.push(` note: ${t} is git-tracked; excluded from the working tree but its bytes remain in history packs`);
179
+ if (r.dittoConfig)
180
+ lines.push(` .ditto: digest ${r.dittoConfig.digest.slice(0, 12)} (${(r.dittoConfig.layers ?? []).join(" < ") || "defaults"})${r.dittoConfig.misePath ? `, mise ${r.dittoConfig.misePath}` : ""}`);
181
+ for (const w of r.configWarnings)
182
+ lines.push(` warning: ${w}`);
183
+ }
184
+ for (const s of plan.symlinks)
185
+ lines.push(` symlink ${s.relPath} → ${s.target}: ${s.status}`);
186
+ for (const u of plan.unrelated)
187
+ lines.push(` unrelated: ${u} (not part of any project; blocks a whole-folder offload)`);
188
+ for (const c of plan.conflicts)
189
+ lines.push(` conflict: ${c}`);
190
+ if (plan.repos.length === 0)
191
+ lines.push(" no repositories found");
192
+ return lines;
193
+ }
194
+ /** Read helper for tests and scripts. */
195
+ export async function readText(p) {
196
+ return readFile(p, "utf8");
197
+ }
198
+ //# sourceMappingURL=commands.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"commands.js","sourceRoot":"","sources":["../../src/dittoconfig/commands.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,26 @@
1
+ import { type DittoConfigSummary, type EffectiveConfig } from "./types.js";
2
+ /** A single, user-fixable problem in a `.ditto/` document. Mirrors Go's ValidationError. */
3
+ export declare class DittoConfigError extends Error {
4
+ readonly file?: string | undefined;
5
+ readonly field?: string | undefined;
6
+ constructor(message: string, file?: string | undefined, field?: string | undefined);
7
+ }
8
+ export declare class DittoConfigNotFound extends Error {
9
+ readonly dir: string;
10
+ constructor(dir: string);
11
+ }
12
+ export interface LoadOptions {
13
+ /** Parent folder whose `.ditto/config.toml` supplies defaults below the repository's. */
14
+ workspaceDir?: string;
15
+ /** Dotted-key overrides applied last, e.g. `{ "teleport.harness.kind": "codex" }`. */
16
+ overrides?: Record<string, string>;
17
+ }
18
+ /** Loads `.ditto/` for a repository with the same layering and validation as the backend. */
19
+ export declare function loadDittoConfig(repoDir: string, opts?: LoadOptions): Promise<EffectiveConfig>;
20
+ /** Digest identical to the Go package's: sha256 of the canonical JSON of {config, endpoints, misePath}. */
21
+ export declare function digest(eff: EffectiveConfig): string;
22
+ export declare function summarize(eff: EffectiveConfig): DittoConfigSummary;
23
+ export declare function validateEffective(eff: EffectiveConfig): void;
24
+ /** Canonical JSON: object keys sorted recursively, undefined dropped — matches Go's encoding/json map ordering for our shapes. */
25
+ export declare function canonicalJson(v: unknown): string;
26
+ export declare function slugify(s: string): string;