@treeseed/sdk 0.1.2 → 0.3.1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +97 -506
- package/dist/{src/cli-tools.d.ts → cli-tools.d.ts} +1 -1
- package/dist/cli-tools.js +5 -3
- package/dist/{src/content-store.d.ts → content-store.d.ts} +3 -2
- package/dist/content-store.js +52 -20
- package/dist/{src/d1-store.d.ts → d1-store.d.ts} +62 -1
- package/dist/d1-store.js +625 -65
- package/dist/field-aliases.d.ts +11 -0
- package/dist/field-aliases.js +41 -0
- package/dist/graph/build.d.ts +19 -0
- package/dist/graph/build.js +949 -0
- package/dist/graph/dsl.d.ts +2 -0
- package/dist/graph/dsl.js +243 -0
- package/dist/graph/query.d.ts +47 -0
- package/dist/graph/query.js +447 -0
- package/dist/graph/ranking.d.ts +3 -0
- package/dist/graph/ranking.js +483 -0
- package/dist/graph/schema.d.ts +142 -0
- package/dist/graph/schema.js +133 -0
- package/dist/graph.d.ts +52 -0
- package/dist/graph.js +133 -0
- package/dist/index.d.ts +28 -0
- package/dist/index.js +91 -2
- package/dist/model-registry.d.ts +8 -0
- package/dist/model-registry.js +351 -25
- package/dist/operations/providers/default.d.ts +10 -0
- package/dist/operations/providers/default.js +514 -0
- package/dist/operations/runtime.d.ts +7 -0
- package/dist/operations/runtime.js +60 -0
- package/dist/operations/services/config-runtime.d.ts +269 -0
- package/dist/operations/services/config-runtime.js +1397 -0
- package/dist/operations/services/d1-migration.d.ts +6 -0
- package/dist/operations/services/d1-migration.js +89 -0
- package/dist/operations/services/deploy.d.ts +371 -0
- package/dist/operations/services/deploy.js +981 -0
- package/dist/operations/services/git-workflow.d.ts +49 -0
- package/dist/operations/services/git-workflow.js +218 -0
- package/dist/operations/services/github-automation.d.ts +156 -0
- package/dist/operations/services/github-automation.js +256 -0
- package/dist/operations/services/local-dev.d.ts +9 -0
- package/dist/operations/services/local-dev.js +106 -0
- package/dist/operations/services/mailpit-runtime.d.ts +4 -0
- package/dist/operations/services/mailpit-runtime.js +59 -0
- package/dist/operations/services/railway-deploy.d.ts +53 -0
- package/dist/operations/services/railway-deploy.js +123 -0
- package/dist/operations/services/runtime-paths.d.ts +19 -0
- package/dist/operations/services/runtime-paths.js +54 -0
- package/dist/operations/services/runtime-tools.d.ts +117 -0
- package/dist/operations/services/runtime-tools.js +358 -0
- package/dist/operations/services/save-deploy-preflight.d.ts +34 -0
- package/dist/operations/services/save-deploy-preflight.js +76 -0
- package/dist/operations/services/template-registry.d.ts +88 -0
- package/dist/operations/services/template-registry.js +407 -0
- package/dist/operations/services/watch-dev.d.ts +21 -0
- package/dist/operations/services/watch-dev.js +284 -0
- package/dist/operations/services/workspace-preflight.d.ts +40 -0
- package/dist/operations/services/workspace-preflight.js +165 -0
- package/dist/operations/services/workspace-save.d.ts +42 -0
- package/dist/operations/services/workspace-save.js +235 -0
- package/dist/operations/services/workspace-tools.d.ts +16 -0
- package/dist/operations/services/workspace-tools.js +270 -0
- package/dist/operations-registry.d.ts +5 -0
- package/dist/operations-registry.js +68 -0
- package/dist/operations-types.d.ts +71 -0
- package/dist/operations-types.js +17 -0
- package/dist/operations.d.ts +6 -0
- package/dist/operations.js +16 -0
- package/dist/platform/books-data.d.ts +1 -0
- package/dist/platform/books-data.js +1 -0
- package/dist/platform/contracts.d.ts +158 -0
- package/dist/platform/contracts.js +0 -0
- package/dist/platform/deploy/config.d.ts +4 -0
- package/dist/platform/deploy/config.js +222 -0
- package/dist/platform/deploy-config.d.ts +1 -0
- package/dist/platform/deploy-config.js +1 -0
- package/dist/platform/deploy-runtime.d.ts +18 -0
- package/dist/platform/deploy-runtime.js +78 -0
- package/dist/platform/env.yaml +394 -0
- package/dist/platform/environment.d.ts +130 -0
- package/dist/platform/environment.js +331 -0
- package/dist/platform/plugin.d.ts +2 -0
- package/dist/platform/plugin.js +4 -0
- package/dist/platform/plugins/constants.d.ts +22 -0
- package/dist/platform/plugins/constants.js +29 -0
- package/dist/platform/plugins/plugin.d.ts +51 -0
- package/dist/platform/plugins/plugin.js +6 -0
- package/dist/platform/plugins/runtime.d.ts +35 -0
- package/dist/platform/plugins/runtime.js +161 -0
- package/dist/platform/plugins.d.ts +6 -0
- package/dist/platform/plugins.js +38 -0
- package/dist/platform/site-config-schema.js +1 -0
- package/dist/platform/tenant/config.d.ts +9 -0
- package/dist/platform/tenant/config.js +154 -0
- package/dist/platform/tenant/runtime-config.d.ts +4 -0
- package/dist/platform/tenant/runtime-config.js +20 -0
- package/dist/platform/tenant-config.d.ts +1 -0
- package/dist/platform/tenant-config.js +1 -0
- package/dist/platform/utils/books-data.d.ts +29 -0
- package/dist/platform/utils/books-data.js +82 -0
- package/dist/platform/utils/site-config-schema.js +321 -0
- package/dist/remote.d.ts +175 -0
- package/dist/remote.js +202 -0
- package/dist/runtime.js +35 -22
- package/dist/scripts/aggregate-book.js +121 -0
- package/dist/scripts/build-dist.js +54 -13
- package/dist/scripts/build-tenant-worker.js +36 -0
- package/dist/scripts/cleanup-markdown.js +373 -0
- package/dist/scripts/cli-test-fixtures.js +48 -0
- package/dist/scripts/config-treeseed.js +95 -0
- package/dist/scripts/ensure-mailpit.js +29 -0
- package/dist/scripts/local-dev.js +129 -0
- package/dist/scripts/logs-mailpit.js +2 -0
- package/dist/scripts/patch-starlight-content-path.js +172 -0
- package/dist/scripts/release-verify.js +34 -6
- package/dist/scripts/run-fixture-astro-command.js +18 -0
- package/dist/scripts/scaffold-site.js +65 -0
- package/dist/scripts/stop-mailpit.js +5 -0
- package/dist/scripts/sync-dev-vars.js +6 -0
- package/dist/scripts/sync-template.js +20 -0
- package/dist/scripts/template-catalog.test.js +100 -0
- package/dist/scripts/template-command.js +31 -0
- package/dist/scripts/tenant-astro-command.js +3 -0
- package/dist/scripts/tenant-build.js +16 -0
- package/dist/scripts/tenant-check.js +7 -0
- package/dist/scripts/tenant-d1-migrate-local.js +11 -0
- package/dist/scripts/tenant-deploy.js +180 -0
- package/dist/scripts/tenant-destroy.js +104 -0
- package/dist/scripts/tenant-dev.js +171 -0
- package/dist/scripts/tenant-lint.js +4 -0
- package/dist/scripts/tenant-test.js +4 -0
- package/dist/scripts/test-cloudflare-local.js +212 -0
- package/dist/scripts/test-scaffold.js +314 -0
- package/dist/scripts/test-smoke.js +71 -13
- package/dist/scripts/treeseed-assert-release-tag-version.js +21 -0
- package/dist/scripts/treeseed-build-dist.js +134 -0
- package/dist/scripts/treeseed-publish-package.js +19 -0
- package/dist/scripts/treeseed-release-verify.js +131 -0
- package/dist/scripts/treeseed-run-ts.js +45 -0
- package/dist/scripts/validate-templates.js +6 -0
- package/dist/scripts/verify-driver.js +29 -0
- package/dist/scripts/workflow-commands.test.js +39 -0
- package/dist/scripts/workspace-close.js +24 -0
- package/dist/scripts/workspace-command-e2e.js +718 -0
- package/dist/scripts/workspace-lint.js +9 -0
- package/dist/scripts/workspace-preflight.js +22 -0
- package/dist/scripts/workspace-publish-changed-packages.js +16 -0
- package/dist/scripts/workspace-release-verify.js +81 -0
- package/dist/scripts/workspace-release.js +42 -0
- package/dist/scripts/workspace-save.js +124 -0
- package/dist/scripts/workspace-start-warning.js +3 -0
- package/dist/scripts/workspace-start.js +71 -0
- package/dist/scripts/workspace-test-unit.js +4 -0
- package/dist/scripts/workspace-test.js +11 -0
- package/dist/sdk-fields.d.ts +11 -0
- package/dist/sdk-fields.js +169 -0
- package/dist/sdk-filters.d.ts +4 -0
- package/dist/sdk-filters.js +12 -15
- package/dist/sdk-types.d.ts +796 -0
- package/dist/sdk-types.js +7 -1
- package/dist/sdk-version.d.ts +2 -0
- package/dist/sdk-version.js +42 -0
- package/dist/sdk.d.ts +215 -0
- package/dist/sdk.js +235 -11
- package/dist/stores/cursor-store.js +9 -3
- package/dist/stores/lease-store.js +8 -2
- package/dist/{src/stores → stores}/message-store.d.ts +1 -1
- package/dist/stores/message-store.js +27 -3
- package/dist/stores/operational-store.d.ts +24 -0
- package/dist/stores/operational-store.js +279 -0
- package/dist/stores/run-store.js +8 -1
- package/dist/stores/subscription-store.js +7 -5
- package/dist/template-catalog.d.ts +13 -0
- package/dist/template-catalog.js +141 -0
- package/dist/treeseed/services/compose.yml +7 -0
- package/dist/treeseed/template-catalog/catalog.fixture.json +55 -0
- package/dist/treeseed/template-catalog/templates/starter-basic/template/astro.config.d.ts +2 -0
- package/dist/treeseed/template-catalog/templates/starter-basic/template/astro.config.ts +3 -0
- package/dist/treeseed/template-catalog/templates/starter-basic/template/package.json +32 -0
- package/dist/treeseed/template-catalog/templates/starter-basic/template/src/config.yaml +40 -0
- package/dist/treeseed/template-catalog/templates/starter-basic/template/src/content/empty/.gitkeep +1 -0
- package/dist/treeseed/template-catalog/templates/starter-basic/template/src/content/knowledge/handbook/index.mdx +11 -0
- package/dist/treeseed/template-catalog/templates/starter-basic/template/src/content/pages/welcome.mdx +11 -0
- package/dist/treeseed/template-catalog/templates/starter-basic/template/src/content.config.d.ts +1 -0
- package/dist/treeseed/template-catalog/templates/starter-basic/template/src/content.config.ts +3 -0
- package/dist/treeseed/template-catalog/templates/starter-basic/template/src/env.yaml +1 -0
- package/dist/treeseed/template-catalog/templates/starter-basic/template/src/manifest.yaml +19 -0
- package/dist/treeseed/template-catalog/templates/starter-basic/template/treeseed.site.yaml +26 -0
- package/dist/treeseed/template-catalog/templates/starter-basic/template/tsconfig.json +9 -0
- package/dist/treeseed/template-catalog/templates/starter-basic/template.config.json +90 -0
- package/dist/utils/agents/contracts/messages.d.ts +88 -0
- package/dist/utils/agents/contracts/messages.js +138 -0
- package/dist/utils/agents/contracts/run.d.ts +20 -0
- package/dist/utils/agents/contracts/run.js +0 -0
- package/dist/utils/agents/runtime-types.d.ts +117 -0
- package/dist/utils/agents/runtime-types.js +4 -0
- package/dist/verification.d.ts +20 -0
- package/dist/verification.js +98 -0
- package/dist/workflow/operations.d.ts +396 -0
- package/dist/workflow/operations.js +841 -0
- package/dist/workflow-state.d.ts +56 -0
- package/dist/workflow-state.js +195 -0
- package/dist/workflow-support.d.ts +9 -0
- package/dist/workflow-support.js +176 -0
- package/dist/workflow.d.ts +111 -0
- package/dist/workflow.js +97 -0
- package/package.json +111 -5
- package/scripts/verify-driver.mjs +29 -0
- package/dist/scripts/.ts-run-1775630384291-crtqr3izsa.js +0 -22
- package/dist/scripts/.ts-run-1775630388025-vnjle0z75a.js +0 -129
- package/dist/scripts/assert-release-tag-version.d.ts +0 -1
- package/dist/scripts/build-dist.d.ts +0 -1
- package/dist/scripts/fixture-tools.d.ts +0 -5
- package/dist/scripts/package-tools.d.ts +0 -15
- package/dist/scripts/publish-package.d.ts +0 -1
- package/dist/scripts/release-verify.d.ts +0 -1
- package/dist/scripts/test-smoke.d.ts +0 -1
- package/dist/src/index.d.ts +0 -6
- package/dist/src/model-registry.d.ts +0 -4
- package/dist/src/sdk-filters.d.ts +0 -4
- package/dist/src/sdk-types.d.ts +0 -285
- package/dist/src/sdk.d.ts +0 -109
- package/dist/test/test-fixture.d.ts +0 -1
- package/dist/test/utils/envelopes.test.d.ts +0 -1
- package/dist/test/utils/sdk.test.d.ts +0 -1
- package/dist/vitest.config.d.ts +0 -2
- /package/dist/{src/frontmatter.d.ts → frontmatter.d.ts} +0 -0
- /package/dist/{src/git-runtime.d.ts → git-runtime.d.ts} +0 -0
- /package/dist/{src/runtime.d.ts → runtime.d.ts} +0 -0
- /package/dist/{src/stores → stores}/cursor-store.d.ts +0 -0
- /package/dist/{src/stores → stores}/envelopes.d.ts +0 -0
- /package/dist/{src/stores → stores}/helpers.d.ts +0 -0
- /package/dist/{src/stores → stores}/lease-store.d.ts +0 -0
- /package/dist/{src/stores → stores}/run-store.d.ts +0 -0
- /package/dist/{src/stores → stores}/subscription-store.d.ts +0 -0
- /package/dist/{src/types → types}/agents.d.ts +0 -0
- /package/dist/{src/types → types}/cloudflare.d.ts +0 -0
- /package/dist/{src/wrangler-d1.d.ts → wrangler-d1.d.ts} +0 -0
|
@@ -0,0 +1,7 @@
|
|
|
1
|
+
import { resolveAstroBin, createProductionBuildEnv, packageScriptPath, runNodeBinary, runNodeScript } from '../operations/services/runtime-tools.js';
|
|
2
|
+
runNodeScript(packageScriptPath('patch-starlight-content-path'), [], { cwd: process.cwd() });
|
|
3
|
+
runNodeScript(packageScriptPath('aggregate-book'), [], { cwd: process.cwd() });
|
|
4
|
+
runNodeBinary(resolveAstroBin(), ['check'], {
|
|
5
|
+
cwd: process.cwd(),
|
|
6
|
+
env: createProductionBuildEnv(),
|
|
7
|
+
});
|
|
@@ -0,0 +1,11 @@
|
|
|
1
|
+
import { resolve } from 'node:path';
|
|
2
|
+
import { runLocalD1Migrations } from '../operations/services/d1-migration.js';
|
|
3
|
+
import { ensureGeneratedWranglerConfig } from '../operations/services/deploy.js';
|
|
4
|
+
const tenantRoot = process.cwd();
|
|
5
|
+
const migrationsRoot = resolve(tenantRoot, 'migrations');
|
|
6
|
+
const { wranglerPath: wranglerConfig } = ensureGeneratedWranglerConfig(tenantRoot);
|
|
7
|
+
runLocalD1Migrations({
|
|
8
|
+
cwd: tenantRoot,
|
|
9
|
+
wranglerConfig,
|
|
10
|
+
migrationsRoot,
|
|
11
|
+
});
|
|
@@ -0,0 +1,180 @@
|
|
|
1
|
+
#!/usr/bin/env node
|
|
2
|
+
import { spawnSync } from 'node:child_process';
|
|
3
|
+
import { mkdirSync, writeFileSync } from 'node:fs';
|
|
4
|
+
import { dirname, resolve } from 'node:path';
|
|
5
|
+
import { applyTreeseedEnvironmentToProcess } from '../operations/services/config-runtime.js';
|
|
6
|
+
import { assertDeploymentInitialized, createBranchPreviewDeployTarget, createPersistentDeployTarget, deployTargetLabel, ensureGeneratedWranglerConfig, finalizeDeploymentState, runRemoteD1Migrations, } from '../operations/services/deploy.js';
|
|
7
|
+
import { currentManagedBranch, PRODUCTION_BRANCH, STAGING_BRANCH } from '../operations/services/git-workflow.js';
|
|
8
|
+
import { packageScriptPath, resolveWranglerBin } from '../operations/services/runtime-tools.js';
|
|
9
|
+
import { runTenantDeployPreflight } from '../operations/services/save-deploy-preflight.js';
|
|
10
|
+
const tenantRoot = process.cwd();
|
|
11
|
+
const args = process.argv.slice(2);
|
|
12
|
+
function writeDeployReport(payload) {
|
|
13
|
+
const target = process.env.TREESEED_DEPLOY_REPORT_PATH;
|
|
14
|
+
if (!target) {
|
|
15
|
+
return;
|
|
16
|
+
}
|
|
17
|
+
const filePath = resolve(target);
|
|
18
|
+
mkdirSync(dirname(filePath), { recursive: true });
|
|
19
|
+
writeFileSync(filePath, `${JSON.stringify(payload, null, 2)}\n`, 'utf8');
|
|
20
|
+
}
|
|
21
|
+
function parseArgs(argv) {
|
|
22
|
+
const parsed = {
|
|
23
|
+
dryRun: false,
|
|
24
|
+
only: null,
|
|
25
|
+
name: null,
|
|
26
|
+
environment: null,
|
|
27
|
+
targetBranch: null,
|
|
28
|
+
};
|
|
29
|
+
const rest = [...argv];
|
|
30
|
+
while (rest.length) {
|
|
31
|
+
const current = rest.shift();
|
|
32
|
+
if (!current)
|
|
33
|
+
continue;
|
|
34
|
+
if (current === '--dry-run') {
|
|
35
|
+
parsed.dryRun = true;
|
|
36
|
+
continue;
|
|
37
|
+
}
|
|
38
|
+
if (current === '--only') {
|
|
39
|
+
parsed.only = rest.shift() ?? null;
|
|
40
|
+
continue;
|
|
41
|
+
}
|
|
42
|
+
if (current === '--name') {
|
|
43
|
+
parsed.name = rest.shift() ?? null;
|
|
44
|
+
continue;
|
|
45
|
+
}
|
|
46
|
+
if (current === '--environment') {
|
|
47
|
+
parsed.environment = rest.shift() ?? null;
|
|
48
|
+
continue;
|
|
49
|
+
}
|
|
50
|
+
if (current.startsWith('--environment=')) {
|
|
51
|
+
parsed.environment = current.split('=', 2)[1] ?? null;
|
|
52
|
+
continue;
|
|
53
|
+
}
|
|
54
|
+
if (current === '--target-branch') {
|
|
55
|
+
parsed.targetBranch = rest.shift() ?? null;
|
|
56
|
+
continue;
|
|
57
|
+
}
|
|
58
|
+
if (current.startsWith('--target-branch=')) {
|
|
59
|
+
parsed.targetBranch = current.split('=', 2)[1] ?? null;
|
|
60
|
+
continue;
|
|
61
|
+
}
|
|
62
|
+
throw new Error(`Unknown deploy argument: ${current}`);
|
|
63
|
+
}
|
|
64
|
+
return parsed;
|
|
65
|
+
}
|
|
66
|
+
function inferEnvironmentFromBranch() {
|
|
67
|
+
const branch = currentManagedBranch(tenantRoot);
|
|
68
|
+
if (branch === STAGING_BRANCH) {
|
|
69
|
+
return 'staging';
|
|
70
|
+
}
|
|
71
|
+
if (branch === PRODUCTION_BRANCH) {
|
|
72
|
+
return 'prod';
|
|
73
|
+
}
|
|
74
|
+
return null;
|
|
75
|
+
}
|
|
76
|
+
function resolveTarget(options) {
|
|
77
|
+
if (options.targetBranch) {
|
|
78
|
+
return {
|
|
79
|
+
target: createBranchPreviewDeployTarget(options.targetBranch),
|
|
80
|
+
scope: 'staging',
|
|
81
|
+
};
|
|
82
|
+
}
|
|
83
|
+
const environment = options.environment ?? (process.env.CI ? inferEnvironmentFromBranch() : null);
|
|
84
|
+
if (!environment) {
|
|
85
|
+
throw new Error('Treeseed deploy requires `--environment local|staging|prod` outside CI.');
|
|
86
|
+
}
|
|
87
|
+
return {
|
|
88
|
+
target: createPersistentDeployTarget(environment),
|
|
89
|
+
scope: environment,
|
|
90
|
+
};
|
|
91
|
+
}
|
|
92
|
+
function runNodeScript(scriptPath, scriptArgs = [], env = {}) {
|
|
93
|
+
const result = spawnSync(process.execPath, [scriptPath, ...scriptArgs], {
|
|
94
|
+
stdio: 'inherit',
|
|
95
|
+
cwd: tenantRoot,
|
|
96
|
+
env: { ...process.env, ...env },
|
|
97
|
+
});
|
|
98
|
+
if (result.status !== 0) {
|
|
99
|
+
process.exit(result.status ?? 1);
|
|
100
|
+
}
|
|
101
|
+
}
|
|
102
|
+
function runWranglerDeploy(configPath) {
|
|
103
|
+
const result = spawnSync(process.execPath, [resolveWranglerBin(), 'deploy', '--config', configPath], {
|
|
104
|
+
stdio: 'inherit',
|
|
105
|
+
cwd: tenantRoot,
|
|
106
|
+
env: { ...process.env },
|
|
107
|
+
});
|
|
108
|
+
if (result.status !== 0) {
|
|
109
|
+
process.exit(result.status ?? 1);
|
|
110
|
+
}
|
|
111
|
+
}
|
|
112
|
+
async function main() {
|
|
113
|
+
const options = parseArgs(args);
|
|
114
|
+
const { target, scope } = resolveTarget(options);
|
|
115
|
+
applyTreeseedEnvironmentToProcess({ tenantRoot, scope, override: true });
|
|
116
|
+
const allowedSteps = new Set(['migrate', 'build', 'publish']);
|
|
117
|
+
if (options.only && !allowedSteps.has(options.only)) {
|
|
118
|
+
throw new Error(`Unsupported deploy step "${options.only}". Expected one of ${[...allowedSteps].join(', ')}.`);
|
|
119
|
+
}
|
|
120
|
+
const shouldRun = (step) => !options.only || options.only === step;
|
|
121
|
+
if (options.name) {
|
|
122
|
+
console.log(`Deploy target label: ${options.name}`);
|
|
123
|
+
}
|
|
124
|
+
if (scope === 'local') {
|
|
125
|
+
runTenantDeployPreflight({ cwd: tenantRoot, scope: 'local' });
|
|
126
|
+
runNodeScript(packageScriptPath('tenant-build'));
|
|
127
|
+
writeDeployReport({ ok: true, kind: 'success', scope, dryRun: options.dryRun, target: deployTargetLabel(target) });
|
|
128
|
+
console.log('Treeseed local deploy completed as a build-only publish target.');
|
|
129
|
+
return;
|
|
130
|
+
}
|
|
131
|
+
try {
|
|
132
|
+
assertDeploymentInitialized(tenantRoot, { target });
|
|
133
|
+
runTenantDeployPreflight({ cwd: tenantRoot, scope });
|
|
134
|
+
}
|
|
135
|
+
catch (error) {
|
|
136
|
+
writeDeployReport({
|
|
137
|
+
ok: false,
|
|
138
|
+
kind: 'preflight_failed',
|
|
139
|
+
target: deployTargetLabel(target),
|
|
140
|
+
message: error instanceof Error ? error.message : String(error),
|
|
141
|
+
});
|
|
142
|
+
throw error;
|
|
143
|
+
}
|
|
144
|
+
const { wranglerPath } = ensureGeneratedWranglerConfig(tenantRoot, { target });
|
|
145
|
+
if (shouldRun('migrate')) {
|
|
146
|
+
const result = runRemoteD1Migrations(tenantRoot, { dryRun: options.dryRun, target });
|
|
147
|
+
console.log(`${options.dryRun ? 'Planned' : 'Applied'} remote migrations for ${result.databaseName}.`);
|
|
148
|
+
}
|
|
149
|
+
if (shouldRun('build')) {
|
|
150
|
+
if (options.dryRun) {
|
|
151
|
+
console.log('Dry run: skipped tenant build.');
|
|
152
|
+
}
|
|
153
|
+
else {
|
|
154
|
+
runNodeScript(packageScriptPath('tenant-build'));
|
|
155
|
+
}
|
|
156
|
+
}
|
|
157
|
+
if (shouldRun('publish')) {
|
|
158
|
+
if (options.dryRun) {
|
|
159
|
+
console.log(`Dry run: would deploy ${deployTargetLabel(target)} with generated Wrangler config at ${resolve(wranglerPath)}.`);
|
|
160
|
+
}
|
|
161
|
+
else {
|
|
162
|
+
runWranglerDeploy(wranglerPath);
|
|
163
|
+
finalizeDeploymentState(tenantRoot, { target });
|
|
164
|
+
}
|
|
165
|
+
}
|
|
166
|
+
writeDeployReport({
|
|
167
|
+
ok: true,
|
|
168
|
+
kind: 'success',
|
|
169
|
+
dryRun: options.dryRun,
|
|
170
|
+
only: options.only,
|
|
171
|
+
target: deployTargetLabel(target),
|
|
172
|
+
});
|
|
173
|
+
}
|
|
174
|
+
try {
|
|
175
|
+
await main();
|
|
176
|
+
}
|
|
177
|
+
catch (error) {
|
|
178
|
+
console.error(error instanceof Error ? error.message : String(error));
|
|
179
|
+
process.exit(1);
|
|
180
|
+
}
|
|
@@ -0,0 +1,104 @@
|
|
|
1
|
+
#!/usr/bin/env node
|
|
2
|
+
import readline from 'node:readline/promises';
|
|
3
|
+
import { stdin as input, stdout as output } from 'node:process';
|
|
4
|
+
import { applyTreeseedEnvironmentToProcess, assertTreeseedCommandEnvironment } from '../operations/services/config-runtime.js';
|
|
5
|
+
import { cleanupDestroyedState, createPersistentDeployTarget, destroyCloudflareResources, loadDeployState, printDestroySummary, validateDestroyPrerequisites, } from '../operations/services/deploy.js';
|
|
6
|
+
import { deriveCloudflareWorkerName } from '../platform/deploy/config.js';
|
|
7
|
+
const tenantRoot = process.cwd();
|
|
8
|
+
function parseArgs(argv) {
|
|
9
|
+
const parsed = {
|
|
10
|
+
dryRun: false,
|
|
11
|
+
force: false,
|
|
12
|
+
skipConfirmation: false,
|
|
13
|
+
confirm: null,
|
|
14
|
+
removeBuildArtifacts: false,
|
|
15
|
+
environment: null,
|
|
16
|
+
};
|
|
17
|
+
const rest = [...argv];
|
|
18
|
+
while (rest.length) {
|
|
19
|
+
const current = rest.shift();
|
|
20
|
+
if (!current)
|
|
21
|
+
continue;
|
|
22
|
+
if (current === '--dry-run') {
|
|
23
|
+
parsed.dryRun = true;
|
|
24
|
+
continue;
|
|
25
|
+
}
|
|
26
|
+
if (current === '--force') {
|
|
27
|
+
parsed.force = true;
|
|
28
|
+
continue;
|
|
29
|
+
}
|
|
30
|
+
if (current === '--skip-confirmation') {
|
|
31
|
+
parsed.skipConfirmation = true;
|
|
32
|
+
continue;
|
|
33
|
+
}
|
|
34
|
+
if (current === '--confirm') {
|
|
35
|
+
parsed.confirm = rest.shift() ?? null;
|
|
36
|
+
continue;
|
|
37
|
+
}
|
|
38
|
+
if (current === '--remove-build-artifacts') {
|
|
39
|
+
parsed.removeBuildArtifacts = true;
|
|
40
|
+
continue;
|
|
41
|
+
}
|
|
42
|
+
if (current === '--environment') {
|
|
43
|
+
parsed.environment = rest.shift() ?? null;
|
|
44
|
+
continue;
|
|
45
|
+
}
|
|
46
|
+
if (current.startsWith('--environment=')) {
|
|
47
|
+
parsed.environment = current.split('=', 2)[1] ?? null;
|
|
48
|
+
continue;
|
|
49
|
+
}
|
|
50
|
+
throw new Error(`Unknown destroy argument: ${current}`);
|
|
51
|
+
}
|
|
52
|
+
return parsed;
|
|
53
|
+
}
|
|
54
|
+
function getExpectedConfirmation(deployConfig) {
|
|
55
|
+
return deployConfig.slug;
|
|
56
|
+
}
|
|
57
|
+
function printDangerMessage(deployConfig, state, expectedConfirmation) {
|
|
58
|
+
console.error('DANGER: treeseed destroy will permanently delete this site and its Cloudflare resources.');
|
|
59
|
+
console.error(` Site: ${deployConfig.name}`);
|
|
60
|
+
console.error(` Slug: ${deployConfig.slug}`);
|
|
61
|
+
console.error(` Worker: ${state.workerName ?? deriveCloudflareWorkerName(deployConfig)}`);
|
|
62
|
+
console.error(` D1: ${state.d1Databases.SITE_DATA_DB.databaseName}`);
|
|
63
|
+
console.error(` KV FORM_GUARD_KV: ${state.kvNamespaces.FORM_GUARD_KV.name}`);
|
|
64
|
+
console.error(` KV SESSION: ${state.kvNamespaces.SESSION.name}`);
|
|
65
|
+
console.error(' This action is irreversible.');
|
|
66
|
+
console.error(` To continue, type exactly: ${expectedConfirmation}`);
|
|
67
|
+
}
|
|
68
|
+
async function readConfirmation(expectedConfirmation) {
|
|
69
|
+
const rl = readline.createInterface({ input, output });
|
|
70
|
+
try {
|
|
71
|
+
return (await rl.question('Confirmation: ')).trim() === expectedConfirmation;
|
|
72
|
+
}
|
|
73
|
+
finally {
|
|
74
|
+
rl.close();
|
|
75
|
+
}
|
|
76
|
+
}
|
|
77
|
+
const options = parseArgs(process.argv.slice(2));
|
|
78
|
+
const scope = options.environment ?? 'prod';
|
|
79
|
+
const target = createPersistentDeployTarget(scope);
|
|
80
|
+
applyTreeseedEnvironmentToProcess({ tenantRoot, scope, override: true });
|
|
81
|
+
assertTreeseedCommandEnvironment({ tenantRoot, scope, purpose: 'destroy' });
|
|
82
|
+
const deployConfig = validateDestroyPrerequisites(tenantRoot, { requireRemote: !options.dryRun });
|
|
83
|
+
const state = loadDeployState(tenantRoot, deployConfig, { target });
|
|
84
|
+
const expectedConfirmation = getExpectedConfirmation(deployConfig);
|
|
85
|
+
if (!options.skipConfirmation) {
|
|
86
|
+
printDangerMessage(deployConfig, state, expectedConfirmation);
|
|
87
|
+
const confirmed = options.confirm !== null ? options.confirm === expectedConfirmation : await readConfirmation(expectedConfirmation);
|
|
88
|
+
if (!confirmed) {
|
|
89
|
+
console.error('Destroy aborted: confirmation text did not match.');
|
|
90
|
+
process.exit(1);
|
|
91
|
+
}
|
|
92
|
+
}
|
|
93
|
+
const result = destroyCloudflareResources(tenantRoot, {
|
|
94
|
+
dryRun: options.dryRun,
|
|
95
|
+
force: options.force,
|
|
96
|
+
target,
|
|
97
|
+
});
|
|
98
|
+
printDestroySummary(result);
|
|
99
|
+
if (options.dryRun) {
|
|
100
|
+
console.log('Dry run: no remote resources were deleted.');
|
|
101
|
+
process.exit(0);
|
|
102
|
+
}
|
|
103
|
+
cleanupDestroyedState(tenantRoot, { target, removeBuildArtifacts: options.removeBuildArtifacts });
|
|
104
|
+
console.log('Treeseed destroy completed and local deployment state was removed.');
|
|
@@ -0,0 +1,171 @@
|
|
|
1
|
+
import { spawnSync } from 'node:child_process';
|
|
2
|
+
import { corePackageRoot, packageScriptPath, spawnNodeBinary, resolveWranglerBin } from '../operations/services/runtime-tools.js';
|
|
3
|
+
import { applyTreeseedEnvironmentToProcess, assertTreeseedCommandEnvironment } from '../operations/services/config-runtime.js';
|
|
4
|
+
import { ensureGeneratedWranglerConfig } from '../operations/services/deploy.js';
|
|
5
|
+
import { loadTreeseedDeployConfig } from '../platform/deploy/config.js';
|
|
6
|
+
import { createTenantWatchEntries, isEditablePackageWorkspace, startPollingWatch, stopManagedProcess, writeDevReloadStamp, workspaceSdkRoot, } from '../operations/services/watch-dev.js';
|
|
7
|
+
const tenantRoot = process.cwd();
|
|
8
|
+
const cliArgs = process.argv.slice(2);
|
|
9
|
+
const watchMode = cliArgs.includes('--watch');
|
|
10
|
+
const wranglerArgs = cliArgs.filter((arg) => arg !== '--watch');
|
|
11
|
+
let wranglerChild = null;
|
|
12
|
+
let stopWatching = null;
|
|
13
|
+
let isStoppingForRebuild = false;
|
|
14
|
+
let shuttingDown = false;
|
|
15
|
+
function shouldEnsureMailpit() {
|
|
16
|
+
if (process.env.TREESEED_DEV_FORCE_MAILPIT === '1') {
|
|
17
|
+
return true;
|
|
18
|
+
}
|
|
19
|
+
return loadTreeseedDeployConfig().smtp?.enabled === true;
|
|
20
|
+
}
|
|
21
|
+
function runStep(command, args, { cwd = tenantRoot, env = {}, fatal = true } = {}) {
|
|
22
|
+
const result = spawnSync(command, args, {
|
|
23
|
+
stdio: 'inherit',
|
|
24
|
+
cwd,
|
|
25
|
+
env: { ...process.env, ...env },
|
|
26
|
+
});
|
|
27
|
+
if (result.status !== 0 && fatal) {
|
|
28
|
+
process.exit(result.status ?? 1);
|
|
29
|
+
}
|
|
30
|
+
return result.status === 0;
|
|
31
|
+
}
|
|
32
|
+
function runNodeScript(scriptPath, args = [], options = {}) {
|
|
33
|
+
return runStep(process.execPath, [scriptPath, ...args], options);
|
|
34
|
+
}
|
|
35
|
+
function runTenantBuildCycle({ includePackageBuild = false, includeSdkBuild = false, fatal = true } = {}) {
|
|
36
|
+
const envOverrides = ['TREESEED_LOCAL_DEV_MODE=cloudflare'];
|
|
37
|
+
if (watchMode) {
|
|
38
|
+
envOverrides.push('TREESEED_PUBLIC_DEV_WATCH_RELOAD=true');
|
|
39
|
+
}
|
|
40
|
+
if (includeSdkBuild && isEditablePackageWorkspace()) {
|
|
41
|
+
const sdkRoot = workspaceSdkRoot();
|
|
42
|
+
if (sdkRoot) {
|
|
43
|
+
const sdkBuilt = runStep('npm', ['run', 'build:dist'], {
|
|
44
|
+
cwd: sdkRoot,
|
|
45
|
+
fatal,
|
|
46
|
+
});
|
|
47
|
+
if (!sdkBuilt) {
|
|
48
|
+
return false;
|
|
49
|
+
}
|
|
50
|
+
}
|
|
51
|
+
}
|
|
52
|
+
if (includePackageBuild && isEditablePackageWorkspace()) {
|
|
53
|
+
const distBuilt = runStep('npm', ['run', 'build:dist'], {
|
|
54
|
+
cwd: corePackageRoot,
|
|
55
|
+
fatal,
|
|
56
|
+
});
|
|
57
|
+
if (!distBuilt) {
|
|
58
|
+
return false;
|
|
59
|
+
}
|
|
60
|
+
}
|
|
61
|
+
const buildScripts = [
|
|
62
|
+
['patch-starlight-content-path', []],
|
|
63
|
+
['aggregate-book', []],
|
|
64
|
+
['sync-dev-vars', envOverrides],
|
|
65
|
+
['tenant-d1-migrate-local', []],
|
|
66
|
+
];
|
|
67
|
+
if (shouldEnsureMailpit()) {
|
|
68
|
+
buildScripts.splice(2, 0, ['ensure-mailpit', []]);
|
|
69
|
+
}
|
|
70
|
+
for (const [scriptName, args] of buildScripts) {
|
|
71
|
+
const ok = runNodeScript(packageScriptPath(scriptName), args, { fatal });
|
|
72
|
+
if (!ok) {
|
|
73
|
+
return false;
|
|
74
|
+
}
|
|
75
|
+
}
|
|
76
|
+
ensureGeneratedWranglerConfig(tenantRoot);
|
|
77
|
+
if (watchMode) {
|
|
78
|
+
writeDevReloadStamp(tenantRoot);
|
|
79
|
+
}
|
|
80
|
+
const built = runNodeScript(packageScriptPath('tenant-build'), [], {
|
|
81
|
+
fatal,
|
|
82
|
+
env: watchMode ? { TREESEED_PUBLIC_DEV_WATCH_RELOAD: 'true' } : {},
|
|
83
|
+
});
|
|
84
|
+
if (!built) {
|
|
85
|
+
return false;
|
|
86
|
+
}
|
|
87
|
+
return true;
|
|
88
|
+
}
|
|
89
|
+
function startWrangler() {
|
|
90
|
+
const { wranglerPath } = ensureGeneratedWranglerConfig(tenantRoot);
|
|
91
|
+
const child = spawnNodeBinary(resolveWranglerBin(), ['dev', '--local', '--config', wranglerPath, ...wranglerArgs], {
|
|
92
|
+
cwd: tenantRoot,
|
|
93
|
+
env: watchMode ? { TREESEED_PUBLIC_DEV_WATCH_RELOAD: 'true' } : {},
|
|
94
|
+
detached: process.platform !== 'win32',
|
|
95
|
+
});
|
|
96
|
+
wranglerChild = child;
|
|
97
|
+
child.on('exit', (code, signal) => {
|
|
98
|
+
if (child !== wranglerChild) {
|
|
99
|
+
return;
|
|
100
|
+
}
|
|
101
|
+
wranglerChild = null;
|
|
102
|
+
if (isStoppingForRebuild || shuttingDown) {
|
|
103
|
+
return;
|
|
104
|
+
}
|
|
105
|
+
if (stopWatching) {
|
|
106
|
+
stopWatching();
|
|
107
|
+
}
|
|
108
|
+
if (signal) {
|
|
109
|
+
process.kill(process.pid, signal);
|
|
110
|
+
return;
|
|
111
|
+
}
|
|
112
|
+
process.exit(code ?? 0);
|
|
113
|
+
});
|
|
114
|
+
}
|
|
115
|
+
async function restartWranglerAfterBuild() {
|
|
116
|
+
if (wranglerChild) {
|
|
117
|
+
isStoppingForRebuild = true;
|
|
118
|
+
await stopManagedProcess(wranglerChild);
|
|
119
|
+
isStoppingForRebuild = false;
|
|
120
|
+
}
|
|
121
|
+
if (!shuttingDown) {
|
|
122
|
+
startWrangler();
|
|
123
|
+
}
|
|
124
|
+
}
|
|
125
|
+
async function shutdownAndExit(code = 0) {
|
|
126
|
+
shuttingDown = true;
|
|
127
|
+
if (stopWatching) {
|
|
128
|
+
stopWatching();
|
|
129
|
+
}
|
|
130
|
+
await stopManagedProcess(wranglerChild);
|
|
131
|
+
process.exit(code);
|
|
132
|
+
}
|
|
133
|
+
process.on('SIGINT', () => {
|
|
134
|
+
void shutdownAndExit(130);
|
|
135
|
+
});
|
|
136
|
+
process.on('SIGTERM', () => {
|
|
137
|
+
void shutdownAndExit(143);
|
|
138
|
+
});
|
|
139
|
+
process.env.TREESEED_LOCAL_DEV_MODE = process.env.TREESEED_LOCAL_DEV_MODE ?? 'cloudflare';
|
|
140
|
+
applyTreeseedEnvironmentToProcess({ tenantRoot, scope: 'local', override: true });
|
|
141
|
+
assertTreeseedCommandEnvironment({ tenantRoot, scope: 'local', purpose: 'dev' });
|
|
142
|
+
runTenantBuildCycle({
|
|
143
|
+
includeSdkBuild: isEditablePackageWorkspace(),
|
|
144
|
+
includePackageBuild: isEditablePackageWorkspace(),
|
|
145
|
+
fatal: true,
|
|
146
|
+
});
|
|
147
|
+
startWrangler();
|
|
148
|
+
if (watchMode) {
|
|
149
|
+
console.log('Starting unified Wrangler watch mode. Changes will rebuild the app and refresh the browser.');
|
|
150
|
+
stopWatching = startPollingWatch({
|
|
151
|
+
watchEntries: createTenantWatchEntries(tenantRoot),
|
|
152
|
+
onChange: async ({ changedPaths, packageChanged, sdkChanged }) => {
|
|
153
|
+
console.log(`Detected ${changedPaths.length} change${changedPaths.length === 1 ? '' : 's'}; rebuilding ${sdkChanged ? 'sdk, core, and tenant' : packageChanged ? 'core and tenant' : 'tenant'} output...`);
|
|
154
|
+
isStoppingForRebuild = true;
|
|
155
|
+
await stopManagedProcess(wranglerChild);
|
|
156
|
+
isStoppingForRebuild = false;
|
|
157
|
+
const ok = runTenantBuildCycle({
|
|
158
|
+
includeSdkBuild: sdkChanged,
|
|
159
|
+
includePackageBuild: packageChanged || sdkChanged,
|
|
160
|
+
fatal: false,
|
|
161
|
+
});
|
|
162
|
+
if (ok) {
|
|
163
|
+
startWrangler();
|
|
164
|
+
console.log('Rebuild complete. Wrangler restarted with the updated output.');
|
|
165
|
+
}
|
|
166
|
+
else {
|
|
167
|
+
console.error('Rebuild failed. Wrangler remains stopped until the next successful save.');
|
|
168
|
+
}
|
|
169
|
+
},
|
|
170
|
+
});
|
|
171
|
+
}
|