creek 0.3.0 → 0.3.2
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/bin.js +2 -0
- package/hono.d.ts +1 -0
- package/hono.js +1 -0
- package/index.d.ts +1 -0
- package/index.js +1 -0
- package/package.json +30 -35
- package/react.d.ts +1 -0
- package/react.js +1 -0
- package/README.md +0 -184
- package/dist/commands/claim.d.ts +0 -18
- package/dist/commands/claim.js +0 -93
- package/dist/commands/deploy.d.ts +0 -38
- package/dist/commands/deploy.js +0 -807
- package/dist/commands/deployments.d.ts +0 -18
- package/dist/commands/deployments.js +0 -84
- package/dist/commands/env.d.ts +0 -2
- package/dist/commands/env.js +0 -104
- package/dist/commands/init.d.ts +0 -18
- package/dist/commands/init.js +0 -69
- package/dist/commands/login.d.ts +0 -23
- package/dist/commands/login.js +0 -120
- package/dist/commands/projects.d.ts +0 -13
- package/dist/commands/projects.js +0 -38
- package/dist/commands/status.d.ts +0 -18
- package/dist/commands/status.js +0 -115
- package/dist/commands/whoami.d.ts +0 -13
- package/dist/commands/whoami.js +0 -43
- package/dist/index.d.ts +0 -3
- package/dist/index.js +0 -36
- package/dist/utils/auth-server.d.ts +0 -22
- package/dist/utils/auth-server.js +0 -91
- package/dist/utils/bundle.d.ts +0 -6
- package/dist/utils/bundle.js +0 -39
- package/dist/utils/config.d.ts +0 -12
- package/dist/utils/config.js +0 -37
- package/dist/utils/git-clone.d.ts +0 -44
- package/dist/utils/git-clone.js +0 -193
- package/dist/utils/nextjs.d.ts +0 -48
- package/dist/utils/nextjs.js +0 -368
- package/dist/utils/output.d.ts +0 -38
- package/dist/utils/output.js +0 -45
- package/dist/utils/repo-url.d.ts +0 -48
- package/dist/utils/repo-url.js +0 -201
- package/dist/utils/sandbox.d.ts +0 -50
- package/dist/utils/sandbox.js +0 -69
- package/dist/utils/ssr-bundle.d.ts +0 -6
- package/dist/utils/ssr-bundle.js +0 -48
- package/dist/utils/tos.d.ts +0 -28
- package/dist/utils/tos.js +0 -95
package/dist/utils/nextjs.js
DELETED
|
@@ -1,368 +0,0 @@
|
|
|
1
|
-
/**
|
|
2
|
-
* Next.js-specific build utilities for Creek CLI.
|
|
3
|
-
*
|
|
4
|
-
* Two build paths:
|
|
5
|
-
* - **Adapter path** (Next.js >= 16.2): Uses @solcreek/adapter-nextjs via
|
|
6
|
-
* NEXT_ADAPTER_PATH. Zero workarounds, typed outputs, direct esbuild bundle.
|
|
7
|
-
* - **Legacy path** (Next.js < 16.2): Uses @opennextjs/cloudflare with
|
|
8
|
-
* workarounds (standalone patch, middleware manifest inline, etc.)
|
|
9
|
-
*
|
|
10
|
-
* The CLI auto-detects the Next.js version and picks the right path.
|
|
11
|
-
*/
|
|
12
|
-
import { existsSync, cpSync, mkdirSync, writeFileSync, readFileSync, readdirSync, rmSync } from "node:fs";
|
|
13
|
-
import { join, dirname, resolve } from "node:path";
|
|
14
|
-
import { createRequire } from "node:module";
|
|
15
|
-
import { execSync, execFileSync } from "node:child_process";
|
|
16
|
-
import consola from "consola";
|
|
17
|
-
// ---------------------------------------------------------------------------
|
|
18
|
-
// Version detection + unified entry point
|
|
19
|
-
// ---------------------------------------------------------------------------
|
|
20
|
-
/** Read the installed Next.js version from node_modules. */
|
|
21
|
-
export function getNextVersion(cwd) {
|
|
22
|
-
try {
|
|
23
|
-
const pkgPath = join(cwd, "node_modules/next/package.json");
|
|
24
|
-
return JSON.parse(readFileSync(pkgPath, "utf-8")).version;
|
|
25
|
-
}
|
|
26
|
-
catch {
|
|
27
|
-
return null;
|
|
28
|
-
}
|
|
29
|
-
}
|
|
30
|
-
/** Simple semver >= comparison (major.minor.patch only). */
|
|
31
|
-
function semverGte(version, target) {
|
|
32
|
-
const parse = (v) => v.split(".").map(Number);
|
|
33
|
-
const [aMaj, aMin, aPat] = parse(version);
|
|
34
|
-
const [bMaj, bMin, bPat] = parse(target);
|
|
35
|
-
if (aMaj !== bMaj)
|
|
36
|
-
return aMaj > bMaj;
|
|
37
|
-
if (aMin !== bMin)
|
|
38
|
-
return aMin > bMin;
|
|
39
|
-
return aPat >= bPat;
|
|
40
|
-
}
|
|
41
|
-
/**
|
|
42
|
-
* Build a Next.js app using the Creek adapter (>= 16.2).
|
|
43
|
-
*
|
|
44
|
-
* Sets NEXT_ADAPTER_PATH to the adapter bundled with the CLI.
|
|
45
|
-
* No opennext, no wrangler, no config patching — the adapter handles
|
|
46
|
-
* everything inside onBuildComplete().
|
|
47
|
-
*/
|
|
48
|
-
function resolveAdapterPath() {
|
|
49
|
-
try {
|
|
50
|
-
const require = createRequire(import.meta.url);
|
|
51
|
-
return require.resolve("@solcreek/adapter-nextjs");
|
|
52
|
-
}
|
|
53
|
-
catch {
|
|
54
|
-
return null;
|
|
55
|
-
}
|
|
56
|
-
}
|
|
57
|
-
function buildWithAdapter(cwd) {
|
|
58
|
-
const adapterPath = resolveAdapterPath();
|
|
59
|
-
if (!adapterPath) {
|
|
60
|
-
consola.warn(" @solcreek/adapter-nextjs not found — install it for optimal Next.js builds");
|
|
61
|
-
return; // caller falls back to legacy
|
|
62
|
-
}
|
|
63
|
-
consola.start(" Building Next.js with Creek adapter...\n");
|
|
64
|
-
// --webpack is required: Turbopack does not generate standalone output,
|
|
65
|
-
// and its chunked format uses a custom runtime incompatible with esbuild.
|
|
66
|
-
execSync("npx next build --webpack", {
|
|
67
|
-
cwd,
|
|
68
|
-
stdio: "inherit",
|
|
69
|
-
env: { ...process.env, NEXT_ADAPTER_PATH: adapterPath },
|
|
70
|
-
});
|
|
71
|
-
}
|
|
72
|
-
/**
|
|
73
|
-
* Unified Next.js build entry point.
|
|
74
|
-
*
|
|
75
|
-
* - Next.js >= 16.2: Creek adapter path (recommended)
|
|
76
|
-
* - Next.js < 16.2: legacy opennext path (best effort)
|
|
77
|
-
*/
|
|
78
|
-
export function buildNextjs(cwd, isMonorepo, projectName) {
|
|
79
|
-
const version = getNextVersion(cwd);
|
|
80
|
-
const useAdapter = version && semverGte(version, "16.2.0") && resolveAdapterPath();
|
|
81
|
-
if (useAdapter) {
|
|
82
|
-
buildWithAdapter(cwd);
|
|
83
|
-
}
|
|
84
|
-
else {
|
|
85
|
-
if (version) {
|
|
86
|
-
consola.warn(` Next.js ${version} — using legacy build path`);
|
|
87
|
-
}
|
|
88
|
-
buildNextjsForWorkers(cwd, isMonorepo, projectName);
|
|
89
|
-
}
|
|
90
|
-
}
|
|
91
|
-
/** Check if the adapter output exists (vs legacy opennext output). */
|
|
92
|
-
export function hasAdapterOutput(cwd) {
|
|
93
|
-
return existsSync(join(cwd, ".creek/adapter-output/manifest.json"));
|
|
94
|
-
}
|
|
95
|
-
/**
|
|
96
|
-
* Patch the bundled worker to fix opennext's dynamic require issues.
|
|
97
|
-
*
|
|
98
|
-
* @deprecated Legacy path — only used for Next.js < 16.2. For >= 16.2,
|
|
99
|
-
* the Creek adapter handles middleware via typed AdapterOutputs.
|
|
100
|
-
*/
|
|
101
|
-
export function patchBundledWorker(bundleDir, openNextDir) {
|
|
102
|
-
const workerPath = join(bundleDir, "worker.js");
|
|
103
|
-
if (!existsSync(workerPath))
|
|
104
|
-
return;
|
|
105
|
-
let code = readFileSync(workerPath, "utf-8");
|
|
106
|
-
let patched = false;
|
|
107
|
-
// Read the actual middleware manifest from the build output
|
|
108
|
-
const manifestPath = join(openNextDir, "server-functions/default/.next/server/middleware-manifest.json");
|
|
109
|
-
let manifest = '{"version":3,"middleware":{},"sortedMiddleware":[],"functions":{}}';
|
|
110
|
-
if (existsSync(manifestPath)) {
|
|
111
|
-
manifest = readFileSync(manifestPath, "utf-8").trim();
|
|
112
|
-
}
|
|
113
|
-
// Patch: getMiddlewareManifest() { return __require(this.middlewareManifestPath); }
|
|
114
|
-
// → getMiddlewareManifest() { return <inline manifest>; }
|
|
115
|
-
const pattern = /getMiddlewareManifest\(\)\s*\{[^}]*__require\(this\.middlewareManifestPath\)[^}]*\}/;
|
|
116
|
-
if (pattern.test(code)) {
|
|
117
|
-
code = code.replace(pattern, `getMiddlewareManifest() { return ${manifest}; }`);
|
|
118
|
-
patched = true;
|
|
119
|
-
}
|
|
120
|
-
if (patched) {
|
|
121
|
-
writeFileSync(workerPath, code);
|
|
122
|
-
consola.info(" Patched worker: inline middleware manifest");
|
|
123
|
-
}
|
|
124
|
-
}
|
|
125
|
-
const CREEK_DIR = ".creek";
|
|
126
|
-
const OPENNEXT_PKG = "@opennextjs/cloudflare";
|
|
127
|
-
const OPENNEXT_VERSION = "^1.18.0";
|
|
128
|
-
/**
|
|
129
|
-
* Ensure @opennextjs/cloudflare is available in .creek/node_modules.
|
|
130
|
-
* Returns the path to the opennextjs-cloudflare CLI binary.
|
|
131
|
-
*/
|
|
132
|
-
function ensureOpenNext(cwd) {
|
|
133
|
-
const creekDir = join(cwd, CREEK_DIR);
|
|
134
|
-
const opennextBin = join(creekDir, "node_modules/.bin/opennextjs-cloudflare");
|
|
135
|
-
if (existsSync(opennextBin))
|
|
136
|
-
return opennextBin;
|
|
137
|
-
consola.start(` Installing ${OPENNEXT_PKG} (one-time setup)...`);
|
|
138
|
-
mkdirSync(creekDir, { recursive: true });
|
|
139
|
-
const pkgPath = join(creekDir, "package.json");
|
|
140
|
-
if (!existsSync(pkgPath)) {
|
|
141
|
-
writeFileSync(pkgPath, JSON.stringify({
|
|
142
|
-
private: true,
|
|
143
|
-
dependencies: { [OPENNEXT_PKG]: OPENNEXT_VERSION },
|
|
144
|
-
}, null, 2));
|
|
145
|
-
}
|
|
146
|
-
execSync("npm install --no-audit --no-fund --ignore-scripts --no-optional", {
|
|
147
|
-
cwd: creekDir,
|
|
148
|
-
stdio: "pipe",
|
|
149
|
-
});
|
|
150
|
-
consola.success(` ${OPENNEXT_PKG} installed`);
|
|
151
|
-
return opennextBin;
|
|
152
|
-
}
|
|
153
|
-
/**
|
|
154
|
-
* Generate wrangler.jsonc in project root for opennext to read.
|
|
155
|
-
* Only created if not already present — opennext needs it at the project root.
|
|
156
|
-
*/
|
|
157
|
-
function ensureWranglerConfig(cwd, projectName) {
|
|
158
|
-
// If user already has wrangler config, don't touch it
|
|
159
|
-
for (const name of ["wrangler.jsonc", "wrangler.json", "wrangler.toml"]) {
|
|
160
|
-
if (existsSync(join(cwd, name)))
|
|
161
|
-
return null;
|
|
162
|
-
}
|
|
163
|
-
// Create minimal config for opennext
|
|
164
|
-
const configPath = join(cwd, "wrangler.jsonc");
|
|
165
|
-
writeFileSync(configPath, JSON.stringify({
|
|
166
|
-
name: projectName,
|
|
167
|
-
main: ".open-next/worker.js",
|
|
168
|
-
compatibility_date: "2025-03-14",
|
|
169
|
-
compatibility_flags: ["nodejs_compat"],
|
|
170
|
-
assets: { directory: ".open-next/assets", binding: "ASSETS" },
|
|
171
|
-
}, null, 2));
|
|
172
|
-
return configPath; // caller can clean up after build
|
|
173
|
-
}
|
|
174
|
-
/**
|
|
175
|
-
* Fix the standalone output path for monorepo builds.
|
|
176
|
-
*
|
|
177
|
-
* When outputFileTracingRoot points to the monorepo root, Next.js outputs to:
|
|
178
|
-
* .next/standalone/{relative-app-path}/.next/
|
|
179
|
-
* instead of:
|
|
180
|
-
* .next/standalone/.next/
|
|
181
|
-
*
|
|
182
|
-
* This breaks @opennextjs/cloudflare's createCacheAssets.
|
|
183
|
-
*/
|
|
184
|
-
export function fixStandalonePath(appDir) {
|
|
185
|
-
const standaloneDir = join(appDir, ".next/standalone");
|
|
186
|
-
const expectedDotNext = join(standaloneDir, ".next");
|
|
187
|
-
if (!existsSync(standaloneDir))
|
|
188
|
-
return false;
|
|
189
|
-
if (existsSync(join(expectedDotNext, "server")))
|
|
190
|
-
return false; // already correct
|
|
191
|
-
const shifted = findShiftedDotNext(standaloneDir);
|
|
192
|
-
if (!shifted) {
|
|
193
|
-
consola.warn(" Could not find .next in standalone output — path fix skipped");
|
|
194
|
-
return false;
|
|
195
|
-
}
|
|
196
|
-
consola.info(" Fixing monorepo standalone path...");
|
|
197
|
-
cpSync(shifted, expectedDotNext, { recursive: true });
|
|
198
|
-
const serverJs = join(shifted, "..", "server.js");
|
|
199
|
-
if (existsSync(serverJs)) {
|
|
200
|
-
cpSync(serverJs, join(standaloneDir, "server.js"));
|
|
201
|
-
}
|
|
202
|
-
return true;
|
|
203
|
-
}
|
|
204
|
-
function findMonorepoRoot(cwd) {
|
|
205
|
-
let dir = resolve(cwd);
|
|
206
|
-
while (dir !== dirname(dir)) {
|
|
207
|
-
dir = dirname(dir);
|
|
208
|
-
if (existsSync(join(dir, "pnpm-workspace.yaml")))
|
|
209
|
-
return dir;
|
|
210
|
-
if (existsSync(join(dir, "turbo.json")))
|
|
211
|
-
return dir;
|
|
212
|
-
try {
|
|
213
|
-
const pkg = JSON.parse(readFileSync(join(dir, "package.json"), "utf-8"));
|
|
214
|
-
if (pkg.workspaces)
|
|
215
|
-
return dir;
|
|
216
|
-
}
|
|
217
|
-
catch { }
|
|
218
|
-
}
|
|
219
|
-
return null;
|
|
220
|
-
}
|
|
221
|
-
function findShiftedDotNext(dir, depth = 0) {
|
|
222
|
-
if (depth > 5)
|
|
223
|
-
return null;
|
|
224
|
-
let entries;
|
|
225
|
-
try {
|
|
226
|
-
entries = readdirSync(dir, { withFileTypes: true });
|
|
227
|
-
}
|
|
228
|
-
catch {
|
|
229
|
-
return null;
|
|
230
|
-
}
|
|
231
|
-
for (const entry of entries) {
|
|
232
|
-
if (!entry.isDirectory())
|
|
233
|
-
continue;
|
|
234
|
-
if (entry.name === ".next" && existsSync(join(dir, ".next/server"))) {
|
|
235
|
-
return join(dir, ".next");
|
|
236
|
-
}
|
|
237
|
-
if (entry.name !== "node_modules" && entry.name !== ".next") {
|
|
238
|
-
const result = findShiftedDotNext(join(dir, entry.name), depth + 1);
|
|
239
|
-
if (result)
|
|
240
|
-
return result;
|
|
241
|
-
}
|
|
242
|
-
}
|
|
243
|
-
return null;
|
|
244
|
-
}
|
|
245
|
-
/**
|
|
246
|
-
* Inject required Next.js config for CF Workers deployment.
|
|
247
|
-
*
|
|
248
|
-
* Reads the user's next.config, checks if output/outputFileTracingRoot/turbopack.root
|
|
249
|
-
* are set, and patches the file if needed. Returns a restore function.
|
|
250
|
-
*
|
|
251
|
-
* Injected settings:
|
|
252
|
-
* - output: "standalone" (required for opennext)
|
|
253
|
-
* - outputFileTracingRoot: monorepo root (required for correct standalone path)
|
|
254
|
-
* - turbopack.root: monorepo root (required for pnpm dep resolution)
|
|
255
|
-
*/
|
|
256
|
-
function injectNextConfig(cwd, monorepoRoot) {
|
|
257
|
-
const configNames = ["next.config.ts", "next.config.js", "next.config.mjs"];
|
|
258
|
-
let configPath = null;
|
|
259
|
-
let originalContent = null;
|
|
260
|
-
for (const name of configNames) {
|
|
261
|
-
const p = join(cwd, name);
|
|
262
|
-
if (existsSync(p)) {
|
|
263
|
-
configPath = p;
|
|
264
|
-
originalContent = readFileSync(p, "utf-8");
|
|
265
|
-
break;
|
|
266
|
-
}
|
|
267
|
-
}
|
|
268
|
-
if (!configPath || !originalContent) {
|
|
269
|
-
// No next.config found — create a minimal one
|
|
270
|
-
configPath = join(cwd, "next.config.ts");
|
|
271
|
-
const root = monorepoRoot ?? cwd;
|
|
272
|
-
writeFileSync(configPath, `
|
|
273
|
-
import type { NextConfig } from "next";
|
|
274
|
-
const nextConfig: NextConfig = {
|
|
275
|
-
output: "standalone",
|
|
276
|
-
outputFileTracingRoot: "${root}",
|
|
277
|
-
turbopack: { root: "${root}" },
|
|
278
|
-
};
|
|
279
|
-
export default nextConfig;
|
|
280
|
-
`);
|
|
281
|
-
return () => { rmSync(configPath); };
|
|
282
|
-
}
|
|
283
|
-
// Check what's missing
|
|
284
|
-
const hasStandalone = /output\s*:\s*["']standalone["']/.test(originalContent);
|
|
285
|
-
const hasTracingRoot = /outputFileTracingRoot/.test(originalContent);
|
|
286
|
-
const hasTurboRoot = /turbopack\s*:\s*\{[^}]*root/.test(originalContent);
|
|
287
|
-
if (hasStandalone && hasTracingRoot && hasTurboRoot)
|
|
288
|
-
return null; // all set
|
|
289
|
-
// Need to patch — wrap the existing config
|
|
290
|
-
const root = monorepoRoot ?? cwd;
|
|
291
|
-
const isTS = configPath.endsWith(".ts");
|
|
292
|
-
const ext = configPath.endsWith(".mjs") ? "mjs" : (isTS ? "ts" : "js");
|
|
293
|
-
// Backup original
|
|
294
|
-
const backupPath = configPath + ".creek-backup";
|
|
295
|
-
writeFileSync(backupPath, originalContent);
|
|
296
|
-
// Build patched config that imports + extends the original
|
|
297
|
-
// We can't easily wrap TS configs, so inject settings at the top level
|
|
298
|
-
let patched = originalContent;
|
|
299
|
-
if (!hasStandalone) {
|
|
300
|
-
// Add output: "standalone" to the config object
|
|
301
|
-
patched = patched.replace(/const\s+\w+\s*(?::\s*\w+)?\s*=\s*\{/, (match) => `${match}\n output: "standalone",`);
|
|
302
|
-
}
|
|
303
|
-
if (!hasTracingRoot && monorepoRoot) {
|
|
304
|
-
patched = patched.replace(/const\s+\w+\s*(?::\s*\w+)?\s*=\s*\{/, (match) => `${match}\n outputFileTracingRoot: "${root}",`);
|
|
305
|
-
}
|
|
306
|
-
if (!hasTurboRoot && monorepoRoot) {
|
|
307
|
-
if (/turbopack\s*:\s*\{/.test(patched)) {
|
|
308
|
-
// turbopack block exists, add root
|
|
309
|
-
patched = patched.replace(/turbopack\s*:\s*\{/, `turbopack: {\n root: "${root}",`);
|
|
310
|
-
}
|
|
311
|
-
else {
|
|
312
|
-
// No turbopack block, add one
|
|
313
|
-
patched = patched.replace(/const\s+\w+\s*(?::\s*\w+)?\s*=\s*\{/, (match) => `${match}\n turbopack: { root: "${root}" },`);
|
|
314
|
-
}
|
|
315
|
-
}
|
|
316
|
-
// Add resolve import if needed for path
|
|
317
|
-
if (patched !== originalContent) {
|
|
318
|
-
consola.info(" Injecting Creek build config into next.config...");
|
|
319
|
-
writeFileSync(configPath, patched);
|
|
320
|
-
}
|
|
321
|
-
return () => {
|
|
322
|
-
// Restore original
|
|
323
|
-
if (existsSync(backupPath)) {
|
|
324
|
-
writeFileSync(configPath, readFileSync(backupPath, "utf-8"));
|
|
325
|
-
rmSync(backupPath);
|
|
326
|
-
}
|
|
327
|
-
};
|
|
328
|
-
}
|
|
329
|
-
/**
|
|
330
|
-
* Build a Next.js app for Cloudflare Workers via legacy opennext path.
|
|
331
|
-
*
|
|
332
|
-
* @deprecated Legacy path for Next.js < 16.2. Use buildNextjs() which
|
|
333
|
-
* auto-selects the adapter path for >= 16.2.
|
|
334
|
-
*/
|
|
335
|
-
export function buildNextjsForWorkers(cwd, isMonorepo, projectName = "app") {
|
|
336
|
-
// Step 1: Ensure opennext is available
|
|
337
|
-
const opennextBin = ensureOpenNext(cwd);
|
|
338
|
-
// Step 2: Ensure wrangler config
|
|
339
|
-
const generatedConfig = ensureWranglerConfig(cwd, projectName);
|
|
340
|
-
// Step 3: Inject next.config settings
|
|
341
|
-
const monorepoRoot = isMonorepo ? findMonorepoRoot(cwd) : null;
|
|
342
|
-
const restoreConfig = injectNextConfig(cwd, monorepoRoot);
|
|
343
|
-
try {
|
|
344
|
-
// Step 4: next build
|
|
345
|
-
consola.start(" Building Next.js app...\n");
|
|
346
|
-
execSync("npx next build", { cwd, stdio: "inherit" });
|
|
347
|
-
// Step 4: Fix monorepo standalone path
|
|
348
|
-
if (isMonorepo) {
|
|
349
|
-
fixStandalonePath(cwd);
|
|
350
|
-
}
|
|
351
|
-
// Step 5: opennextjs-cloudflare post-processing
|
|
352
|
-
consola.start(" Bundling for Cloudflare Workers...");
|
|
353
|
-
execFileSync(opennextBin, ["build", "--skipNextBuild"], {
|
|
354
|
-
cwd,
|
|
355
|
-
stdio: "inherit",
|
|
356
|
-
});
|
|
357
|
-
}
|
|
358
|
-
finally {
|
|
359
|
-
// Restore original next.config
|
|
360
|
-
if (restoreConfig)
|
|
361
|
-
restoreConfig();
|
|
362
|
-
// Clean up generated wrangler config
|
|
363
|
-
if (generatedConfig && existsSync(generatedConfig)) {
|
|
364
|
-
rmSync(generatedConfig);
|
|
365
|
-
}
|
|
366
|
-
}
|
|
367
|
-
}
|
|
368
|
-
//# sourceMappingURL=nextjs.js.map
|
package/dist/utils/output.d.ts
DELETED
|
@@ -1,38 +0,0 @@
|
|
|
1
|
-
/**
|
|
2
|
-
* Shared output utilities for agent-friendly CLI.
|
|
3
|
-
*
|
|
4
|
-
* --json flag + non-TTY auto-detection ensures every command
|
|
5
|
-
* can produce structured output for agents, CI/CD, and pipes.
|
|
6
|
-
*/
|
|
7
|
-
export declare const isTTY: boolean;
|
|
8
|
-
/** Output structured JSON and exit. */
|
|
9
|
-
export declare function jsonOutput(data: Record<string, unknown>, exitCode?: number): never;
|
|
10
|
-
/** Resolve JSON mode: explicit --json flag OR non-TTY environment. */
|
|
11
|
-
export declare function resolveJsonMode(args: {
|
|
12
|
-
json?: boolean;
|
|
13
|
-
}): boolean;
|
|
14
|
-
/**
|
|
15
|
-
* Common --json and --yes args to spread into any command's args definition.
|
|
16
|
-
*
|
|
17
|
-
* Usage:
|
|
18
|
-
* args: { ...globalArgs, myArg: { ... } }
|
|
19
|
-
*/
|
|
20
|
-
export declare const globalArgs: {
|
|
21
|
-
json: {
|
|
22
|
-
type: "boolean";
|
|
23
|
-
description: string;
|
|
24
|
-
default: boolean;
|
|
25
|
-
};
|
|
26
|
-
yes: {
|
|
27
|
-
type: "boolean";
|
|
28
|
-
description: string;
|
|
29
|
-
default: boolean;
|
|
30
|
-
};
|
|
31
|
-
};
|
|
32
|
-
/** Should we skip interactive prompts? */
|
|
33
|
-
export declare function shouldAutoConfirm(args: {
|
|
34
|
-
yes?: boolean;
|
|
35
|
-
}): boolean;
|
|
36
|
-
/** Output an error in the appropriate format and exit. */
|
|
37
|
-
export declare function exitError(jsonMode: boolean, error: string, message: string, exitCode?: number): never;
|
|
38
|
-
//# sourceMappingURL=output.d.ts.map
|
package/dist/utils/output.js
DELETED
|
@@ -1,45 +0,0 @@
|
|
|
1
|
-
/**
|
|
2
|
-
* Shared output utilities for agent-friendly CLI.
|
|
3
|
-
*
|
|
4
|
-
* --json flag + non-TTY auto-detection ensures every command
|
|
5
|
-
* can produce structured output for agents, CI/CD, and pipes.
|
|
6
|
-
*/
|
|
7
|
-
export const isTTY = process.stdout.isTTY ?? false;
|
|
8
|
-
/** Output structured JSON and exit. */
|
|
9
|
-
export function jsonOutput(data, exitCode = 0) {
|
|
10
|
-
process.stdout.write(JSON.stringify(data, null, 2) + "\n");
|
|
11
|
-
process.exit(exitCode);
|
|
12
|
-
}
|
|
13
|
-
/** Resolve JSON mode: explicit --json flag OR non-TTY environment. */
|
|
14
|
-
export function resolveJsonMode(args) {
|
|
15
|
-
return args.json === true || !isTTY;
|
|
16
|
-
}
|
|
17
|
-
/**
|
|
18
|
-
* Common --json and --yes args to spread into any command's args definition.
|
|
19
|
-
*
|
|
20
|
-
* Usage:
|
|
21
|
-
* args: { ...globalArgs, myArg: { ... } }
|
|
22
|
-
*/
|
|
23
|
-
export const globalArgs = {
|
|
24
|
-
json: {
|
|
25
|
-
type: "boolean",
|
|
26
|
-
description: "Output results as JSON (auto-enabled in CI/CD and pipes)",
|
|
27
|
-
default: false,
|
|
28
|
-
},
|
|
29
|
-
yes: {
|
|
30
|
-
type: "boolean",
|
|
31
|
-
description: "Skip confirmation prompts (auto-enabled in non-TTY)",
|
|
32
|
-
default: false,
|
|
33
|
-
},
|
|
34
|
-
};
|
|
35
|
-
/** Should we skip interactive prompts? */
|
|
36
|
-
export function shouldAutoConfirm(args) {
|
|
37
|
-
return args.yes === true || !isTTY;
|
|
38
|
-
}
|
|
39
|
-
/** Output an error in the appropriate format and exit. */
|
|
40
|
-
export function exitError(jsonMode, error, message, exitCode = 1) {
|
|
41
|
-
if (jsonMode)
|
|
42
|
-
jsonOutput({ ok: false, error, message }, exitCode);
|
|
43
|
-
return process.exit(exitCode);
|
|
44
|
-
}
|
|
45
|
-
//# sourceMappingURL=output.js.map
|
package/dist/utils/repo-url.d.ts
DELETED
|
@@ -1,48 +0,0 @@
|
|
|
1
|
-
/**
|
|
2
|
-
* Git repository URL parsing and security validation.
|
|
3
|
-
*
|
|
4
|
-
* Security model:
|
|
5
|
-
* - HTTPS only (no git://, ssh://, file://, ext::)
|
|
6
|
-
* - Hostname allowlist (github.com, gitlab.com, bitbucket.org only)
|
|
7
|
-
* - Owner/repo validated against strict character set
|
|
8
|
-
* - No embedded credentials
|
|
9
|
-
* - Subpath validated against traversal attacks
|
|
10
|
-
*/
|
|
11
|
-
export interface ParsedRepoUrl {
|
|
12
|
-
provider: "github" | "gitlab" | "bitbucket";
|
|
13
|
-
owner: string;
|
|
14
|
-
repo: string;
|
|
15
|
-
branch: string | null;
|
|
16
|
-
cloneUrl: string;
|
|
17
|
-
displayUrl: string;
|
|
18
|
-
}
|
|
19
|
-
/**
|
|
20
|
-
* Quick check: does this string look like a repo URL or shorthand?
|
|
21
|
-
* Used to route between directory deploy and repo deploy.
|
|
22
|
-
*/
|
|
23
|
-
export declare function isRepoUrl(input: string): boolean;
|
|
24
|
-
/**
|
|
25
|
-
* Parse a repo URL or shorthand into structured components.
|
|
26
|
-
* Supports:
|
|
27
|
-
* https://github.com/owner/repo
|
|
28
|
-
* https://github.com/owner/repo.git
|
|
29
|
-
* https://github.com/owner/repo#branch
|
|
30
|
-
* https://github.com/owner/repo/tree/branch
|
|
31
|
-
* github:owner/repo
|
|
32
|
-
* github:owner/repo#branch
|
|
33
|
-
*/
|
|
34
|
-
export declare function parseRepoUrl(input: string): ParsedRepoUrl;
|
|
35
|
-
/**
|
|
36
|
-
* Validate a parsed repo URL for security.
|
|
37
|
-
* Throws RepoUrlError on any violation.
|
|
38
|
-
*/
|
|
39
|
-
export declare function validateRepoUrl(parsed: ParsedRepoUrl): void;
|
|
40
|
-
/**
|
|
41
|
-
* Validate a --path subdirectory argument.
|
|
42
|
-
* Prevents path traversal and other filesystem attacks.
|
|
43
|
-
*/
|
|
44
|
-
export declare function validateSubpath(path: string): void;
|
|
45
|
-
export declare class RepoUrlError extends Error {
|
|
46
|
-
constructor(message: string);
|
|
47
|
-
}
|
|
48
|
-
//# sourceMappingURL=repo-url.d.ts.map
|