@tdk-landscape/tdk-cli-core 1.3.137 → 1.3.138
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/cli/dist/commands/resource.js +22 -9
- package/cli/dist/generator/resource-templates.js +1 -1
- package/cli/dist-bundle/{chunk-DUOGIS2Y.js → chunk-Q6PZ6ZPA.js} +1 -1
- package/cli/dist-bundle/cli.js +74 -74
- package/cli/dist-bundle/{cold-preflight-UATSRM67.js → cold-preflight-6VMSECY4.js} +1 -1
- package/cli/package.json +1 -1
- package/package.json +1 -1
|
@@ -12,7 +12,7 @@ import { hasDddLicense } from "../generator/extension-fetch.js";
|
|
|
12
12
|
import { getDockerfileTemplate, getTestTemplate, getWorkerIndexTemplate, } from "../generator/resource-templates.js";
|
|
13
13
|
import { CREATABLE_RESOURCE_TYPES } from "../types/index.js";
|
|
14
14
|
import { assertValid, confirmOrCancel } from "../utils/command-helpers.js";
|
|
15
|
-
import { BRING_YOUR_OWN_TYPE, SERVICE_JSON } from "../utils/constants.js";
|
|
15
|
+
import { BRING_YOUR_OWN_TYPE, PORT_RANGES, SERVICE_JSON } from "../utils/constants.js";
|
|
16
16
|
import { chooseResourcePath, isPathDiscovered, readDiscoveryPaths, } from "../utils/discovery-paths.js";
|
|
17
17
|
import { errorFactories, requireProjectRoot, runCommand, TdkError } from "../utils/errors.js";
|
|
18
18
|
import { writeFilesWithProgress } from "../utils/file-helpers.js";
|
|
@@ -62,17 +62,25 @@ export const TYPE_SPECIFIC = {
|
|
|
62
62
|
};
|
|
63
63
|
const BYO_RESTART_POLICIES = ["no", "on-failure", "unless-stopped", "always"];
|
|
64
64
|
export function resolveByoPort(value, assignedPort, resources) {
|
|
65
|
+
return resolveResourcePort(BRING_YOUR_OWN_TYPE, value, assignedPort, resources);
|
|
66
|
+
}
|
|
67
|
+
// `--port` is an override for every port-assigned type, validated against that type's range.
|
|
68
|
+
// Without it the next free port in the type's range is used.
|
|
69
|
+
export function resolveResourcePort(resourceType, value, assignedPort, resources) {
|
|
65
70
|
if (!value)
|
|
66
71
|
return assignedPort;
|
|
72
|
+
const { min, max } = PORT_RANGES[resourceType];
|
|
73
|
+
const flag = resourceType === BRING_YOUR_OWN_TYPE ? "BYO --port" : "--port";
|
|
74
|
+
const subject = resourceType === BRING_YOUR_OWN_TYPE ? "BYO port" : "Port";
|
|
67
75
|
if (!/^\d+$/.test(value)) {
|
|
68
|
-
throw new TdkError(
|
|
76
|
+
throw new TdkError(`${flag} must be an integer from ${min} through ${max}.`);
|
|
69
77
|
}
|
|
70
78
|
const port = Number(value);
|
|
71
|
-
if (!Number.isInteger(port) || port <
|
|
72
|
-
throw new TdkError(
|
|
79
|
+
if (!Number.isInteger(port) || port < min || port > max) {
|
|
80
|
+
throw new TdkError(`${flag} must be an integer from ${min} through ${max}.`);
|
|
73
81
|
}
|
|
74
82
|
if (resources.some((resource) => resource.config?.port === port)) {
|
|
75
|
-
throw new TdkError(
|
|
83
|
+
throw new TdkError(`${subject} ${port} is already assigned to another resource.`);
|
|
76
84
|
}
|
|
77
85
|
return port;
|
|
78
86
|
}
|
|
@@ -277,7 +285,7 @@ export const resourceCommand = new Command("resource")
|
|
|
277
285
|
.option("--no-proxy", "Disable the Traefik route (bring-your-own only)")
|
|
278
286
|
.option("--restart <policy>", "Compose restart policy: no, on-failure, unless-stopped, always (bring-your-own only; use no for one-shot jobs)")
|
|
279
287
|
.option("--image <name>", "Docker image name instead of building from Dockerfile (for bring-your-own)")
|
|
280
|
-
.option("--port <port>", "Port
|
|
288
|
+
.option("--port <port>", "Port for the resource, within its type's range (default: next free port in that range)")
|
|
281
289
|
.option("--feature <feature...>", "Enable a resource feature (for example: prisma)")
|
|
282
290
|
.action(async (name, options) => {
|
|
283
291
|
if (options.frameworks) {
|
|
@@ -436,6 +444,11 @@ export const resourceCommand = new Command("resource")
|
|
|
436
444
|
// Check if resource already exists
|
|
437
445
|
const isExistingResource = existsSync(fullPath);
|
|
438
446
|
const hasServiceJson = existsSync(resolve(fullPath, SERVICE_JSON));
|
|
447
|
+
if (options.port !== undefined && resourceType === "sdk") {
|
|
448
|
+
throw new TdkError("--port does not apply to --type sdk.", [
|
|
449
|
+
"Drop --port, or use a service type",
|
|
450
|
+
]);
|
|
451
|
+
}
|
|
439
452
|
if (resourceType === "sdk" && !hasServiceJson) {
|
|
440
453
|
throw new TdkError(`No service.json in ${finalResourcePath}`, [
|
|
441
454
|
'Add one with "appType": "sdk", then run this again to register it',
|
|
@@ -462,9 +475,9 @@ export const resourceCommand = new Command("resource")
|
|
|
462
475
|
]);
|
|
463
476
|
}
|
|
464
477
|
}
|
|
465
|
-
const assignedPort = resourceType ===
|
|
466
|
-
?
|
|
467
|
-
: nextPort;
|
|
478
|
+
const assignedPort = resourceType === "sdk"
|
|
479
|
+
? 0
|
|
480
|
+
: resolveResourcePort(resourceType, options.port, nextPort, allResources);
|
|
468
481
|
console.log(chalk.gray("\nResource details:"));
|
|
469
482
|
console.log(chalk.gray(` Name: ${resourceName}`));
|
|
470
483
|
console.log(chalk.gray(` Type: ${resourceType}`));
|
|
@@ -9,7 +9,7 @@ To create a stack, use:`},services:{singular:"service",command:"tdk resource <na
|
|
|
9
9
|
To create a service:`},"stack-services":{singular:"service",command:"tdk resource <name> --stack <stack-name>",context:`
|
|
10
10
|
To add services to this stack:`}};function gu(e,t){let n=no[e];console.log(t?f.yellow(`No ${n.singular}s found${t}.`):f.yellow(`No ${n.singular}s found.`)),console.log(f.gray(n.context)),console.log(f.gray(` ${n.command}`)),e==="stacks"&&(console.log(f.gray(`
|
|
11
11
|
Or create a new resource with a stack:`)),console.log(f.gray(" tdk resource <name> --stack <stack-name>")))}function ku(e){console.log(f.yellow(e||"Cancelled."))}function yu(e){console.log(f.blue(`TDK ${e}
|
|
12
|
-
`))}function Su(e,t){console.log(f.green(`All ${e} are ${t}!`))}var at=62;function bu(e="\u2500",t=at){return e.repeat(t)}function On(e,t=at-2){let n=Math.max(0,t-e.length),r=Math.floor(n/2),s=n-r;return" ".repeat(r)+e+" ".repeat(s)}function Tu(e,t){return e.length>t?`${e.slice(0,t-1)}\u2026`:e.padEnd(t)}function xu(e,t){return e.length<=t?e:`${e.slice(0,t-3)}...`}function vu(e){console.log(f.green(`\u2713 ${e}`))}function wu(e){console.log(f.blue(e))}function Pu(e,t=2){console.log(f.gray(`${" ".repeat(t)}${e}`))}function $u(e){return e<1024?`${e} B`:e<1024*1024?`${(e/1024).toFixed(1)} KB`:`${(e/(1024*1024)).toFixed(1)} MB`}function Eu(e,t,n=at){let r=n-2,s="\u2500".repeat(r);console.log(),console.log(f.cyan(`\u256D${s}\u256E`)),console.log(f.cyan("\u2502")+f.bold.white(On(e,r))+f.cyan("\u2502")),t&&(console.log(f.cyan(`\u251C${s}\u2524`)),console.log(f.cyan("\u2502")+f.gray(On(t,r))+f.cyan("\u2502"))),console.log(f.cyan(`\u2570${s}\u256F`))}import{existsSync as so}from"node:fs";import{dirname as oo,join as io,resolve as Nn}from"node:path";import{cwd as ao}from"node:process";var Dn={name:"tdk-cli-internal",private:!0,version:"1.3.137",description:"TDK CLI \u2014 start services on your laptop.",keywords:["tdk","tilt","cli","local-dev","microservices"],homepage:"https://github.com/tdk-landscape/tdk-cli-core#readme",bugs:{url:"https://github.com/tdk-landscape/tdk-cli-core/issues"},repository:{type:"git",url:"git+https://github.com/tdk-landscape/tdk-cli-core.git",directory:"cli"},license:"MIT",author:"TDK Team",type:"module",main:"./dist/index.js",types:"./dist/index.d.ts",bin:{tdk:"bin/tdk.js","tdk-cli":"bin/tdk.js"},files:["dist","dist-bundle","bin","templates","README.md","Tiltfile","engine","discovery","specs","ext","!ext/ide-components/code_executor","shared-platform-engineering/docker-templates"],scripts:{build:"tsc && node scripts/bundle.mjs","build:watch":"tsc --watch",lint:"biome check .","lint:fix":"biome check . --write",typecheck:"tsc --project tsconfig.typecheck.json",clean:"rm -rf dist",dev:"bun run build:watch",test:"vitest run","test:watch":"vitest",prepack:"../scripts/stage-npm-engine.sh && npm run build"},dependencies:{commander:"^15.0.0",handlebars:"^4.7.8"},devDependencies:{"@biomejs/biome":"^2.5.13","@types/node":"^22.0.0","@types/react":"^19.3.0",ajv:"^8.17.1",chalk:"^6.0.1",esbuild:"^0.28.2",ink:"^7.1.1",knip:"^6.38.0",react:"^19.3.0","react-devtools-core":"^8.0.0",typescript:"^7.0.2",vite:"^8.3.1",vitest:"^5.0.0"},engines:{node:">=22.12.0"}};function m(e=ao()){let t=Nn(e),n=Nn("/");for(;t!==n;){if(so(io(t,".tdk","project.json")))return t;let r=oo(t);if(r===t)break;t=r}return null}var _e=null;function co(){if(_e)return _e;let e=Dn;if(!e||typeof e!="object"||Array.isArray(e))throw new Error("Invalid package.json: expected object");let t=e;return _e={name:String(t.name??"@tdk-landscape/tdk-cli-core"),version:String(t.version??"0.0.0"),fullPackage:t},_e}function Cn(){return co().version}import{readFileSync as uo}from"node:fs";import{join as lo}from"node:path";function Ae(){let e=m();if(e)try{let t=uo(lo(e,".tdk","project.json"),"utf-8"),n=JSON.parse(t);if(n?.project?.name)return n.project.name}catch{}return"tdk-project"}function ct(e){let t=Ae(),n=process.env.TDK_SERVICE_BASE_URL??`http://${t}.localhost${e?`:${e}`:""}`;try{let r=new URL(n.includes("://")?n:`http://${n}`),s=r.hostname,o=r.port||(e?String(e):"");if(s==="localhost"||/^\d+\.\d+\.\d+\.\d+$/.test(s))return{appBase:`${r.protocol}//${s}${o?`:${o}`:""}`,apiBase:`${r.protocol}//${s}${o?`:${o}`:""}`};let i=s.replace(/^(app|api)\./,"");return{appBase:`${r.protocol}//app.${i}${o?`:${o}`:""}`,apiBase:`${r.protocol}//api.${i}${o?`:${o}`:""}`}}catch{return{appBase:`http://app.${t}.localhost`,apiBase:`http://api.${t}.localhost`}}}function po(e){return`${e.replace(/\/+$/,"")}/health`}function ut(e){if(P(e.config?.appType)){let t=e.name.replace(/-api$/,"");return e.config?.apiPath??`/api/${t}`}return e.config?.basePath??`/${e.name}`}function jn(e,t){let{appBase:n,apiBase:r}=ct(t);return e.filter(s=>s.config?.appType==="frontend"||P(s.config?.appType)).map(s=>{let o=P(s.config.appType)?r:n;return{name:s.name,appType:s.config.appType,url:`${o}${po(ut(s))}`}})}async function fo(e,t){try{let n=await fetch(e.url,{method:"GET",redirect:"manual",signal:AbortSignal.timeout(t)});return{...e,ok:n.ok,status:n.status}}catch(n){let r=n instanceof Error&&n.name==="TimeoutError"?`no response within ${t}ms`:n instanceof Error?n.message:String(n);return{...e,ok:!1,error:r}}}async function In(e,t){return Promise.all(e.map(n=>fo(n,t)))}import{existsSync as X,readdirSync as ir,readFileSync as ar,statSync as kt}from"node:fs";import{dirname as Zo,join as W}from"node:path";var le=class{data;options;constructor(t){this.data=new Map,this.options=t}has(t){let n=this.data.get(t);return n?Date.now()-n.timestamp>this.options.ttlMs?(this.data.delete(t),!1):!0:!1}get(t){if(this.has(t))return this.data.get(t)?.value}set(t,n){this.data.set(t,{value:n,timestamp:Date.now()})}delete(t){this.data.delete(t)}clear(){this.data.clear()}keys(){let t=[];for(let n of this.data.keys())this.has(n)&&t.push(n);return t}size(){return this.keys().length}};function Fn(e){let t=0;return{isValid(){return Date.now()-t<e},markUpdated(){t=Date.now()},reset(){t=0}}}import{execFileSync as xo,execSync as vo}from"node:child_process";import{existsSync as yo}from"node:fs";import{delimiter as So,extname as bo,join as To}from"node:path";import{delimiter as Hu,extname as mo}from"node:path";function Oe(){return process.platform==="win32"}function ho(e){return e==="linux"?"linux":e==="darwin"?"darwin":e==="win32"?"windows":null}function go(e){return e==="x64"?"amd64":e==="arm64"?"arm64":null}function ko(e,t){let n=ho(e),r=go(t);if(!n||!r||n==="windows"&&r!=="amd64")return null;let s=`tdk-${n}-${r}`;return n==="windows"?`${s}.exe`:s}function Vu(){return ko(process.platform,process.arch)}function Wu(){return Oe()?"tdk.exe":"tdk"}function Mn(e,t=Oe()){return t?mo(e)?[e]:[e,`${e}.exe`,`${e}.cmd`,`${e}.bat`]:[e]}function $(e){let t=process.env.PATH??process.env.Path??"",n=Oe(),r=Mn(e,n);if(n&&!bo(e))for(let s of(process.env.PATHEXT??".EXE;.CMD;.BAT;.COM").split(";")){let o=s.toLowerCase();o&&!r.includes(`${e}${o}`)&&r.push(`${e}${o}`)}for(let s of t.split(So))if(s)for(let o of r){let i=To(s,o);if(yo(i))return i}return null}var Ln=1e4;function Bn(){let e=!1;if(process.platform==="win32")try{return xo($("docker")??"docker",["ps"],{stdio:"ignore",timeout:Ln,windowsHide:!0}),"running"}catch(t){return t.code==="ETIMEDOUT"?"unresponsive":"missing"}for(let t of["docker ps","colima status","podman ps"])try{return vo(t,{stdio:"ignore",timeout:Ln}),"running"}catch(n){n.code==="ETIMEDOUT"&&(e=!0)}return e?"unresponsive":"missing"}function wo(e,t){let n=Array.from({length:t.length+1},(r,s)=>s);for(let r=1;r<=e.length;r++){let s=[r];for(let o=1;o<=t.length;o++){let i=e[r-1]===t[o-1]?0:1;s[o]=Math.min(s[o-1]+1,n[o]+1,n[o-1]+i)}n=s}return n[t.length]}function Po(e,t){if(e.length!==t.length)return!1;for(let n=0;n<e.length-1;n++)if(e[n]!==t[n]&&e[n]===t[n+1]&&e[n+1]===t[n]&&e.slice(0,n)===t.slice(0,n)&&e.slice(n+2)===t.slice(n+2))return!0;return!1}function Un(e,t){if(e.length<2||t.length===0||t.includes(e))return;let n=e.toLowerCase(),r,s=Number.POSITIVE_INFINITY;for(let o of t){if(o.length===0)continue;let i=o.toLowerCase(),a=Po(n,i)?1:wo(n,i),c=Math.max(1,Math.min(2,Math.floor(Math.max(n.length,i.length)/3)));a>c||(a<s||a===s&&(r===void 0||o<r))&&(r=o,s=a)}return r}import{spawn as $o}from"node:child_process";import{join as Eo}from"node:path";function Ro(e,t=[],n={}){return new Promise((r,s)=>{let o=[e,...t];n.verbose&&console.log(`Executing: tilt ${o.join(" ")}`);let i=$o($("tilt")??"tilt",o,{stdio:n.inheritStdio?"inherit":"pipe",shell:!1,windowsHide:process.platform==="win32",timeout:n.timeoutMs}),a="",c="";n.inheritStdio||(i.stdout?.on("data",u=>{a+=u.toString()}),i.stderr?.on("data",u=>{c+=u.toString()})),i.on("close",u=>{r({exitCode:u??1,stdout:a,stderr:c})}),i.on("error",u=>{s(new Error(`Failed to spawn tilt: ${u.message}`))})})}async function Hn(){try{return(await Ro("version",[],{inheritStdio:!1,timeoutMs:1e4})).exitCode===0}catch{return!1}}function _o(){let e=m();if(!e)throw L.notInProject();return Eo(e,".tdk",".tdk-out","Tiltfile")}function Vn(e){let t=_o();e.push("-f",t)}function od(e,t={}){let n=[];return Vn(n),t.focusTargets&&t.focusTargets.length>0&&n.push("--",`--focus=${t.focusTargets.join(",")}`),n.push(...e),t.verbose&&!t.quiet&&n.push("--verbose"),t.watch&&n.push("--watch"),n}function id(e={}){let t=[];return Vn(t),e.force&&t.push("--force"),e.focusTargets&&e.focusTargets.length>0&&t.push("--",`--focus=${e.focusTargets.join(",")}`),t}function Wn(e){return e instanceof Error?e.message:String(e)}function md(e,t){if(process.env.TDK_VERBOSE){let n=t!==void 0?`: ${Wn(t)}`:"";console.warn(f.gray(`${e}${n}`))}}var E=class extends Error{suggestions;exitCode;constructor(t,n=[],r=1){super(t),this.name="TdkError",this.suggestions=n,this.exitCode=r}display(){Do(this.message,void 0,this.suggestions)}exit(){this.display(),process.exit(this.exitCode)}};function dt(e,t,n=!1){let r=new Set;for(let s of e){let o=Un(s,t);o&&r.add(n?`Did you mean "${o}" for "${s}"?`:`Did you mean "${o}"?`)}return[...r]}var L={tiltNotInstalled:()=>new E("Tilt CLI is not installed",["Install Tilt: `brew install tilt` (macOS)","Or download from: https://docs.tilt.dev/install.html","Verify with: `tilt version`",`Setup guide: ${rt}`]),dockerNotAvailable:()=>new E("Docker (or a compatible container runtime) is not running",["Start Docker Desktop, then verify with: `docker ps`","Or start Colima: `colima start`","Or start the Docker service on Linux: `sudo systemctl start docker`",`Setup guide: ${rt}`]),dockerNotResponding:()=>new E("Docker is running but not responding (`docker ps` hung for 10s)",["Quit and reopen Docker Desktop, or run `colima restart`","Then verify with: `docker ps`"]),stackNotFound:(e,t=[])=>new E(`Stack "${e}" not found`,[...dt([e],t),"Run `tdk stacks` to see available stacks","Run `tdk stack` to assign resources to a stack"]),resourceNotFound:(e,t=[])=>new E(`Resource "${e}" not found`,[...dt([e],t),"Run `tdk resources` to list all resources","Check the resource name spelling"]),unknownServices:(e,t)=>{let n=dt(e,t,e.length>1);return new E(`Unknown service ${e.join(", ")}. Valid names: ${t.join(", ")}`,n,2)},directoryExists:e=>new E(`Directory already exists: ${e}`,["Use `--path` to specify a different location","Remove the existing directory if no longer needed"]),invalidPath:e=>new E(`Invalid path: ${e}`,["Path must be within the project directory",'Path cannot contain special characters like <>:"|?*']),notInProject:()=>new E("Could not find project root (no .tdk/project.json found)",["Run this from within a TDK project","Run `tdk project --yes` to initialize a new project"])};function hd(){let e=m();return e||L.notInProject().exit()}function Ao(e){e instanceof E&&e.exit(),console.error(f.red(`Error: ${Wn(e)}`)),process.exit(1)}async function Oo(e,t){try{return await e()}catch(n){return t?.verbose&&n instanceof Error&&n.stack&&console.error(f.gray(n.stack)),Ao(n)}}async function gd(e,t){let n=[],r=Bn();return r==="unresponsive"?n.push(L.dockerNotResponding()):r==="missing"&&n.push(L.dockerNotAvailable()),await Hn()||n.push(L.tiltNotInstalled()),n.length>0&&(console.error(f.red(`
|
|
12
|
+
`))}function Su(e,t){console.log(f.green(`All ${e} are ${t}!`))}var at=62;function bu(e="\u2500",t=at){return e.repeat(t)}function On(e,t=at-2){let n=Math.max(0,t-e.length),r=Math.floor(n/2),s=n-r;return" ".repeat(r)+e+" ".repeat(s)}function Tu(e,t){return e.length>t?`${e.slice(0,t-1)}\u2026`:e.padEnd(t)}function xu(e,t){return e.length<=t?e:`${e.slice(0,t-3)}...`}function vu(e){console.log(f.green(`\u2713 ${e}`))}function wu(e){console.log(f.blue(e))}function Pu(e,t=2){console.log(f.gray(`${" ".repeat(t)}${e}`))}function $u(e){return e<1024?`${e} B`:e<1024*1024?`${(e/1024).toFixed(1)} KB`:`${(e/(1024*1024)).toFixed(1)} MB`}function Eu(e,t,n=at){let r=n-2,s="\u2500".repeat(r);console.log(),console.log(f.cyan(`\u256D${s}\u256E`)),console.log(f.cyan("\u2502")+f.bold.white(On(e,r))+f.cyan("\u2502")),t&&(console.log(f.cyan(`\u251C${s}\u2524`)),console.log(f.cyan("\u2502")+f.gray(On(t,r))+f.cyan("\u2502"))),console.log(f.cyan(`\u2570${s}\u256F`))}import{existsSync as so}from"node:fs";import{dirname as oo,join as io,resolve as Nn}from"node:path";import{cwd as ao}from"node:process";var Dn={name:"tdk-cli-internal",private:!0,version:"1.3.138",description:"TDK CLI \u2014 start services on your laptop.",keywords:["tdk","tilt","cli","local-dev","microservices"],homepage:"https://github.com/tdk-landscape/tdk-cli-core#readme",bugs:{url:"https://github.com/tdk-landscape/tdk-cli-core/issues"},repository:{type:"git",url:"git+https://github.com/tdk-landscape/tdk-cli-core.git",directory:"cli"},license:"MIT",author:"TDK Team",type:"module",main:"./dist/index.js",types:"./dist/index.d.ts",bin:{tdk:"bin/tdk.js","tdk-cli":"bin/tdk.js"},files:["dist","dist-bundle","bin","templates","README.md","Tiltfile","engine","discovery","specs","ext","!ext/ide-components/code_executor","shared-platform-engineering/docker-templates"],scripts:{build:"tsc && node scripts/bundle.mjs","build:watch":"tsc --watch",lint:"biome check .","lint:fix":"biome check . --write",typecheck:"tsc --project tsconfig.typecheck.json",clean:"rm -rf dist",dev:"bun run build:watch",test:"vitest run","test:watch":"vitest",prepack:"../scripts/stage-npm-engine.sh && npm run build"},dependencies:{commander:"^15.0.0",handlebars:"^4.7.8"},devDependencies:{"@biomejs/biome":"^2.5.13","@types/node":"^22.0.0","@types/react":"^19.3.0",ajv:"^8.17.1",chalk:"^6.0.1",esbuild:"^0.28.2",ink:"^7.1.1",knip:"^6.38.0",react:"^19.3.0","react-devtools-core":"^8.0.0",typescript:"^7.0.2",vite:"^8.3.1",vitest:"^5.0.0"},engines:{node:">=22.12.0"}};function m(e=ao()){let t=Nn(e),n=Nn("/");for(;t!==n;){if(so(io(t,".tdk","project.json")))return t;let r=oo(t);if(r===t)break;t=r}return null}var _e=null;function co(){if(_e)return _e;let e=Dn;if(!e||typeof e!="object"||Array.isArray(e))throw new Error("Invalid package.json: expected object");let t=e;return _e={name:String(t.name??"@tdk-landscape/tdk-cli-core"),version:String(t.version??"0.0.0"),fullPackage:t},_e}function Cn(){return co().version}import{readFileSync as uo}from"node:fs";import{join as lo}from"node:path";function Ae(){let e=m();if(e)try{let t=uo(lo(e,".tdk","project.json"),"utf-8"),n=JSON.parse(t);if(n?.project?.name)return n.project.name}catch{}return"tdk-project"}function ct(e){let t=Ae(),n=process.env.TDK_SERVICE_BASE_URL??`http://${t}.localhost${e?`:${e}`:""}`;try{let r=new URL(n.includes("://")?n:`http://${n}`),s=r.hostname,o=r.port||(e?String(e):"");if(s==="localhost"||/^\d+\.\d+\.\d+\.\d+$/.test(s))return{appBase:`${r.protocol}//${s}${o?`:${o}`:""}`,apiBase:`${r.protocol}//${s}${o?`:${o}`:""}`};let i=s.replace(/^(app|api)\./,"");return{appBase:`${r.protocol}//app.${i}${o?`:${o}`:""}`,apiBase:`${r.protocol}//api.${i}${o?`:${o}`:""}`}}catch{return{appBase:`http://app.${t}.localhost`,apiBase:`http://api.${t}.localhost`}}}function po(e){return`${e.replace(/\/+$/,"")}/health`}function ut(e){if(P(e.config?.appType)){let t=e.name.replace(/-api$/,"");return e.config?.apiPath??`/api/${t}`}return e.config?.basePath??`/${e.name}`}function jn(e,t){let{appBase:n,apiBase:r}=ct(t);return e.filter(s=>s.config?.appType==="frontend"||P(s.config?.appType)).map(s=>{let o=P(s.config.appType)?r:n;return{name:s.name,appType:s.config.appType,url:`${o}${po(ut(s))}`}})}async function fo(e,t){try{let n=await fetch(e.url,{method:"GET",redirect:"manual",signal:AbortSignal.timeout(t)});return{...e,ok:n.ok,status:n.status}}catch(n){let r=n instanceof Error&&n.name==="TimeoutError"?`no response within ${t}ms`:n instanceof Error?n.message:String(n);return{...e,ok:!1,error:r}}}async function In(e,t){return Promise.all(e.map(n=>fo(n,t)))}import{existsSync as X,readdirSync as ir,readFileSync as ar,statSync as kt}from"node:fs";import{dirname as Zo,join as W}from"node:path";var le=class{data;options;constructor(t){this.data=new Map,this.options=t}has(t){let n=this.data.get(t);return n?Date.now()-n.timestamp>this.options.ttlMs?(this.data.delete(t),!1):!0:!1}get(t){if(this.has(t))return this.data.get(t)?.value}set(t,n){this.data.set(t,{value:n,timestamp:Date.now()})}delete(t){this.data.delete(t)}clear(){this.data.clear()}keys(){let t=[];for(let n of this.data.keys())this.has(n)&&t.push(n);return t}size(){return this.keys().length}};function Fn(e){let t=0;return{isValid(){return Date.now()-t<e},markUpdated(){t=Date.now()},reset(){t=0}}}import{execFileSync as xo,execSync as vo}from"node:child_process";import{existsSync as yo}from"node:fs";import{delimiter as So,extname as bo,join as To}from"node:path";import{delimiter as Hu,extname as mo}from"node:path";function Oe(){return process.platform==="win32"}function ho(e){return e==="linux"?"linux":e==="darwin"?"darwin":e==="win32"?"windows":null}function go(e){return e==="x64"?"amd64":e==="arm64"?"arm64":null}function ko(e,t){let n=ho(e),r=go(t);if(!n||!r||n==="windows"&&r!=="amd64")return null;let s=`tdk-${n}-${r}`;return n==="windows"?`${s}.exe`:s}function Vu(){return ko(process.platform,process.arch)}function Wu(){return Oe()?"tdk.exe":"tdk"}function Mn(e,t=Oe()){return t?mo(e)?[e]:[e,`${e}.exe`,`${e}.cmd`,`${e}.bat`]:[e]}function $(e){let t=process.env.PATH??process.env.Path??"",n=Oe(),r=Mn(e,n);if(n&&!bo(e))for(let s of(process.env.PATHEXT??".EXE;.CMD;.BAT;.COM").split(";")){let o=s.toLowerCase();o&&!r.includes(`${e}${o}`)&&r.push(`${e}${o}`)}for(let s of t.split(So))if(s)for(let o of r){let i=To(s,o);if(yo(i))return i}return null}var Ln=1e4;function Bn(){let e=!1;if(process.platform==="win32")try{return xo($("docker")??"docker",["ps"],{stdio:"ignore",timeout:Ln,windowsHide:!0}),"running"}catch(t){return t.code==="ETIMEDOUT"?"unresponsive":"missing"}for(let t of["docker ps","colima status","podman ps"])try{return vo(t,{stdio:"ignore",timeout:Ln}),"running"}catch(n){n.code==="ETIMEDOUT"&&(e=!0)}return e?"unresponsive":"missing"}function wo(e,t){let n=Array.from({length:t.length+1},(r,s)=>s);for(let r=1;r<=e.length;r++){let s=[r];for(let o=1;o<=t.length;o++){let i=e[r-1]===t[o-1]?0:1;s[o]=Math.min(s[o-1]+1,n[o]+1,n[o-1]+i)}n=s}return n[t.length]}function Po(e,t){if(e.length!==t.length)return!1;for(let n=0;n<e.length-1;n++)if(e[n]!==t[n]&&e[n]===t[n+1]&&e[n+1]===t[n]&&e.slice(0,n)===t.slice(0,n)&&e.slice(n+2)===t.slice(n+2))return!0;return!1}function Un(e,t){if(e.length<2||t.length===0||t.includes(e))return;let n=e.toLowerCase(),r,s=Number.POSITIVE_INFINITY;for(let o of t){if(o.length===0)continue;let i=o.toLowerCase(),a=Po(n,i)?1:wo(n,i),c=Math.max(1,Math.min(2,Math.floor(Math.max(n.length,i.length)/3)));a>c||(a<s||a===s&&(r===void 0||o<r))&&(r=o,s=a)}return r}import{spawn as $o}from"node:child_process";import{join as Eo}from"node:path";function Ro(e,t=[],n={}){return new Promise((r,s)=>{let o=[e,...t];n.verbose&&console.log(`Executing: tilt ${o.join(" ")}`);let i=$o($("tilt")??"tilt",o,{stdio:n.inheritStdio?"inherit":"pipe",shell:!1,windowsHide:process.platform==="win32",timeout:n.timeoutMs}),a="",c="";n.inheritStdio||(i.stdout?.on("data",u=>{a+=u.toString()}),i.stderr?.on("data",u=>{c+=u.toString()})),i.on("close",u=>{r({exitCode:u??1,stdout:a,stderr:c})}),i.on("error",u=>{s(new Error(`Failed to spawn tilt: ${u.message}`))})})}async function Hn(){try{return(await Ro("version",[],{inheritStdio:!1,timeoutMs:1e4})).exitCode===0}catch{return!1}}function _o(){let e=m();if(!e)throw L.notInProject();return Eo(e,".tdk",".tdk-out","Tiltfile")}function Vn(e){let t=_o();e.push("-f",t)}function od(e,t={}){let n=[];return Vn(n),t.focusTargets&&t.focusTargets.length>0&&n.push("--",`--focus=${t.focusTargets.join(",")}`),n.push(...e),t.verbose&&!t.quiet&&n.push("--verbose"),t.watch&&n.push("--watch"),n}function id(e={}){let t=[];return Vn(t),e.force&&t.push("--force"),e.focusTargets&&e.focusTargets.length>0&&t.push("--",`--focus=${e.focusTargets.join(",")}`),t}function Wn(e){return e instanceof Error?e.message:String(e)}function md(e,t){if(process.env.TDK_VERBOSE){let n=t!==void 0?`: ${Wn(t)}`:"";console.warn(f.gray(`${e}${n}`))}}var E=class extends Error{suggestions;exitCode;constructor(t,n=[],r=1){super(t),this.name="TdkError",this.suggestions=n,this.exitCode=r}display(){Do(this.message,void 0,this.suggestions)}exit(){this.display(),process.exit(this.exitCode)}};function dt(e,t,n=!1){let r=new Set;for(let s of e){let o=Un(s,t);o&&r.add(n?`Did you mean "${o}" for "${s}"?`:`Did you mean "${o}"?`)}return[...r]}var L={tiltNotInstalled:()=>new E("Tilt CLI is not installed",["Install Tilt: `brew install tilt` (macOS)","Or download from: https://docs.tilt.dev/install.html","Verify with: `tilt version`",`Setup guide: ${rt}`]),dockerNotAvailable:()=>new E("Docker (or a compatible container runtime) is not running",["Start Docker Desktop, then verify with: `docker ps`","Or start Colima: `colima start`","Or start the Docker service on Linux: `sudo systemctl start docker`",`Setup guide: ${rt}`]),dockerNotResponding:()=>new E("Docker is running but not responding (`docker ps` hung for 10s)",["Quit and reopen Docker Desktop, or run `colima restart`","Then verify with: `docker ps`"]),stackNotFound:(e,t=[])=>new E(`Stack "${e}" not found`,[...dt([e],t),"Run `tdk stacks` to see available stacks","Run `tdk stack` to assign resources to a stack"]),resourceNotFound:(e,t=[])=>new E(`Resource "${e}" not found`,[...dt([e],t),"Run `tdk resources` to list all resources","Check the resource name spelling"]),unknownServices:(e,t)=>{let n=dt(e,t,e.length>1);return new E(`Unknown service ${e.join(", ")}. Valid names: ${t.join(", ")}`,n,2)},directoryExists:e=>new E(`Directory already exists: ${e}`,["Use `--path` to specify a different location","Remove the existing directory if no longer needed"]),invalidPath:e=>new E(`Invalid path: ${e}`,["Path must be within the project directory",'Path cannot contain special characters like <>:"|?*']),notInProject:()=>new E("Could not find project root (no .tdk/project.json found)",["Run this from within a TDK project","Run `tdk project --yes` to initialize a new project"])};function hd(){let e=m();return e||L.notInProject().exit()}function Ao(e){e instanceof E&&e.exit(),console.error(f.red(`Error: ${Wn(e)}`)),process.exit(1)}async function Oo(e,t){try{return await e()}catch(n){return t?.verbose&&n instanceof Error&&n.stack&&console.error(f.gray(n.stack)),Ao(n)}}async function gd(e,t){let n=[],r=Bn();return r==="unresponsive"?n.push(L.dockerNotResponding()):r==="missing"&&n.push(L.dockerNotAvailable()),await Hn()||n.push(L.tiltNotInstalled()),n.length>0&&(console.error(f.red(`
|
|
13
13
|
TDK can't start - missing prerequisites:
|
|
14
14
|
`)),n.forEach((s,o)=>{o>0&&console.error(""),s.display()}),console.error(f.gray("\nRun `tdk doctor` for a full environment check.")),process.exit(1)),Oo(e,t)}function kd(e,t=1){console.error(f.red(`Error: ${e}`)),process.exit(t)}function Do(e,t,n){console.error(f.red(`\u274C ${e}`)),t&&console.error(f.gray(` ${t}`)),n&&n.length>0&&(console.error(f.yellow(`
|
|
15
15
|
\u{1F4A1} Suggestions:`)),n.forEach(r=>{console.error(f.cyan(` \u2192 ${r}`))}))}function yd(e,t){console.error(f.red(`
|