@smoothbricks/cli 0.10.3 → 0.10.5
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 +9 -13
- package/dist/bun/preload.d.ts +13 -0
- package/dist/bun/preload.d.ts.map +1 -0
- package/dist/bun/preload.js +12 -0
- package/dist/cli.js +13 -5
- package/dist/generate/index.d.ts.map +1 -1
- package/dist/generate/index.js +0 -6
- package/dist/github-ci/index.d.ts.map +1 -1
- package/dist/github-ci/index.js +52 -16
- package/dist/github-ci/outputs.d.ts.map +1 -1
- package/dist/github-ci/outputs.js +1 -2
- package/dist/lib/cli-package.js +2 -2
- package/dist/lib/json.d.ts +120 -11
- package/dist/lib/json.d.ts.map +1 -1
- package/dist/lib/json.js +319 -29
- package/dist/lib/workspace.d.ts +7 -14
- package/dist/lib/workspace.d.ts.map +1 -1
- package/dist/lib/workspace.js +76 -82
- package/dist/monorepo/ci-workflow.d.ts +2 -0
- package/dist/monorepo/ci-workflow.d.ts.map +1 -1
- package/dist/monorepo/ci-workflow.js +27 -1
- package/dist/monorepo/git-config.js +2 -2
- package/dist/monorepo/index.d.ts +4 -2
- package/dist/monorepo/index.d.ts.map +1 -1
- package/dist/monorepo/index.js +19 -3
- package/dist/monorepo/lockfile.d.ts +14 -1
- package/dist/monorepo/lockfile.d.ts.map +1 -1
- package/dist/monorepo/lockfile.js +33 -21
- package/dist/monorepo/managed-files.d.ts +11 -0
- package/dist/monorepo/managed-files.d.ts.map +1 -1
- package/dist/monorepo/managed-files.js +57 -32
- package/dist/monorepo/package-policy.d.ts.map +1 -1
- package/dist/monorepo/package-policy.js +52 -45
- package/dist/monorepo/packed-manifest.d.ts +5 -2
- package/dist/monorepo/packed-manifest.d.ts.map +1 -1
- package/dist/monorepo/packed-manifest.js +16 -47
- package/dist/monorepo/packed-package.d.ts.map +1 -1
- package/dist/monorepo/packed-package.js +28 -16
- package/dist/monorepo/packs/index.d.ts.map +1 -1
- package/dist/monorepo/packs/index.js +14 -5
- package/dist/monorepo/publish-workflow.js +3 -1
- package/dist/monorepo/runtime.d.ts +15 -0
- package/dist/monorepo/runtime.d.ts.map +1 -1
- package/dist/monorepo/runtime.js +66 -12
- package/dist/monorepo/tool-validation.d.ts +2 -2
- package/dist/monorepo/tool-validation.d.ts.map +1 -1
- package/dist/monorepo/tool-validation.js +141 -38
- package/dist/monorepo/wrangler.d.ts.map +1 -1
- package/dist/monorepo/wrangler.js +13 -13
- package/dist/nx/index.d.ts +9 -7
- package/dist/nx/index.d.ts.map +1 -1
- package/dist/nx/index.js +48 -31
- package/dist/pr/index.d.ts.map +1 -1
- package/dist/pr/index.js +28 -32
- package/dist/release/candidates.d.ts +3 -2
- package/dist/release/candidates.d.ts.map +1 -1
- package/dist/release/candidates.js +4 -5
- package/dist/release/index.d.ts +1 -0
- package/dist/release/index.d.ts.map +1 -1
- package/dist/release/index.js +88 -59
- package/dist/wrangler/prepare-env.d.ts +0 -1
- package/dist/wrangler/prepare-env.d.ts.map +1 -1
- package/dist/wrangler/prepare-env.js +100 -51
- package/dist/wrangler/scaffold.d.ts.map +1 -1
- package/dist/wrangler/scaffold.js +12 -12
- package/managed/raw/envrc +5 -3
- package/managed/raw/git-format-staged.yml +19 -1
- package/managed/raw/patches/ttsc@0.19.3.patch +67 -0
- package/managed/raw/tooling/direnv/github-actions-bootstrap.sh +2 -1
- package/managed/raw/tooling/direnv/merge-newer-pins.sh +3 -3
- package/managed/raw/tooling/direnv/setup-environment.ts +170 -19
- package/managed/raw/tooling/git-hooks/pre-commit.sh +0 -6
- package/managed/templates/github/actions/cache-node-modules/action.yml +5 -2
- package/managed/templates/github/actions/cache-ttsc-plugins/action.yml +19 -0
- package/managed/templates/github/actions/setup-devenv/action.yml +5 -0
- package/managed/templates/github/workflows/managed-files.yml +80 -0
- package/package.json +15 -4
- package/src/bun/preload.ts +12 -0
- package/src/cli.ts +20 -8
- package/src/generate/index.ts +0 -6
- package/src/github-ci/index.ts +49 -18
- package/src/github-ci/outputs.ts +1 -2
- package/src/lib/cli-package.ts +2 -2
- package/src/lib/json.ts +293 -32
- package/src/lib/workspace.ts +88 -100
- package/src/monorepo/__tests__/ci-workflow.test.ts +3 -3
- package/src/monorepo/ci-workflow.ts +27 -1
- package/src/monorepo/git-config.ts +2 -2
- package/src/monorepo/index.ts +19 -3
- package/src/monorepo/lockfile.test.ts +35 -36
- package/src/monorepo/lockfile.ts +49 -24
- package/src/monorepo/managed-files.test.ts +1 -0
- package/src/monorepo/managed-files.ts +62 -38
- package/src/monorepo/package-policy.test.ts +20 -50
- package/src/monorepo/package-policy.ts +76 -59
- package/src/monorepo/packed-manifest.ts +18 -52
- package/src/monorepo/packed-package.ts +43 -22
- package/src/monorepo/packs/index.ts +14 -5
- package/src/monorepo/publish-workflow.ts +3 -1
- package/src/monorepo/runtime.test.ts +42 -3
- package/src/monorepo/runtime.ts +90 -12
- package/src/monorepo/tool-validation.test.ts +38 -16
- package/src/monorepo/tool-validation.ts +149 -41
- package/src/monorepo/wrangler.test.ts +11 -15
- package/src/monorepo/wrangler.ts +15 -15
- package/src/nx/index.test.ts +9 -5
- package/src/nx/index.ts +69 -42
- package/src/pr/index.ts +42 -36
- package/src/release/__tests__/candidates.test.ts +5 -4
- package/src/release/__tests__/trust-publisher.test.ts +7 -0
- package/src/release/candidates.ts +10 -17
- package/src/release/index.ts +110 -73
- package/src/wrangler/prepare-env.ts +75 -54
- package/src/wrangler/scaffold.test.ts +9 -12
- package/src/wrangler/scaffold.ts +13 -13
|
@@ -1,11 +1,12 @@
|
|
|
1
1
|
import { describe, expect, test } from 'bun:test';
|
|
2
|
-
import {
|
|
2
|
+
import type { PackageJson } from '../lib/json.js';
|
|
3
|
+
import { runtimeTypesRangeForPublishedVersions, validateRuntimePins } from './runtime.js';
|
|
3
4
|
|
|
4
5
|
describe('runtimeTypesRangeForPublishedVersions', () => {
|
|
5
|
-
test('uses the installed Node major
|
|
6
|
+
test('uses the newest published minor within the installed Node major, never the ~major.0.0 floor', () => {
|
|
6
7
|
expect(
|
|
7
8
|
runtimeTypesRangeForPublishedVersions('@types/node', '24.12.0', 'major', ['24.0.0', '24.12.4', '25.9.1']),
|
|
8
|
-
).toBe('~24.
|
|
9
|
+
).toBe('~24.12.4');
|
|
9
10
|
});
|
|
10
11
|
|
|
11
12
|
test('falls back to latest published @types/node when the Node major is unpublished', () => {
|
|
@@ -28,3 +29,41 @@ describe('runtimeTypesRangeForPublishedVersions', () => {
|
|
|
28
29
|
);
|
|
29
30
|
});
|
|
30
31
|
});
|
|
32
|
+
|
|
33
|
+
describe('validateRuntimePins', () => {
|
|
34
|
+
const runtime = { node: '24.16.0', bun: '1.3.14' };
|
|
35
|
+
const aligned = () => ({
|
|
36
|
+
engines: { node: '>=24.0.0' },
|
|
37
|
+
packageManager: 'bun@1.3.14',
|
|
38
|
+
devDependencies: { '@types/node': '~24.13.0' },
|
|
39
|
+
});
|
|
40
|
+
|
|
41
|
+
test('passes when every pin agrees with the PATH runtimes', () => {
|
|
42
|
+
expect(validateRuntimePins(aligned(), runtime)).toBe(0);
|
|
43
|
+
});
|
|
44
|
+
|
|
45
|
+
test('fails when @types/node tracks a different major than the PATH node', () => {
|
|
46
|
+
const pkg = aligned();
|
|
47
|
+
pkg.devDependencies['@types/node'] = '~26.1.1';
|
|
48
|
+
expect(validateRuntimePins(pkg, runtime)).toBe(1);
|
|
49
|
+
});
|
|
50
|
+
|
|
51
|
+
test('fails the ~major.0.0 floor pin even when the major matches', () => {
|
|
52
|
+
const pkg = aligned();
|
|
53
|
+
pkg.devDependencies['@types/node'] = '~24.0.0';
|
|
54
|
+
expect(validateRuntimePins(pkg, runtime)).toBe(1);
|
|
55
|
+
});
|
|
56
|
+
|
|
57
|
+
test('fails engines.node and packageManager drift against the PATH runtimes', () => {
|
|
58
|
+
const pkg = aligned();
|
|
59
|
+
pkg.engines.node = '>=22.0.0';
|
|
60
|
+
pkg.packageManager = 'bun@1.2.0';
|
|
61
|
+
expect(validateRuntimePins(pkg, runtime)).toBe(2);
|
|
62
|
+
});
|
|
63
|
+
|
|
64
|
+
test('fails a missing @types/node pin', () => {
|
|
65
|
+
const pkg: PackageJson = aligned();
|
|
66
|
+
pkg.devDependencies = {};
|
|
67
|
+
expect(validateRuntimePins(pkg, runtime)).toBe(1);
|
|
68
|
+
});
|
|
69
|
+
});
|
package/src/monorepo/runtime.ts
CHANGED
|
@@ -1,7 +1,31 @@
|
|
|
1
1
|
import { existsSync } from 'node:fs';
|
|
2
2
|
import { join } from 'node:path';
|
|
3
3
|
import { $ } from 'bun';
|
|
4
|
-
import {
|
|
4
|
+
import {
|
|
5
|
+
ensureDependencyMap,
|
|
6
|
+
ensureEngines,
|
|
7
|
+
type PackageJson,
|
|
8
|
+
parseStringArrayText,
|
|
9
|
+
readJsonObject,
|
|
10
|
+
setPackageStringField,
|
|
11
|
+
setStringProperty,
|
|
12
|
+
writeJsonObject,
|
|
13
|
+
} from '../lib/json.js';
|
|
14
|
+
|
|
15
|
+
export interface RuntimeVersions {
|
|
16
|
+
node: string;
|
|
17
|
+
bun: string;
|
|
18
|
+
}
|
|
19
|
+
|
|
20
|
+
/** Live runtime versions from the shell PATH — the single source sync AND validate derive from. */
|
|
21
|
+
export async function runtimeVersionsFromPath(root: string): Promise<RuntimeVersions> {
|
|
22
|
+
const node = runtimeCommand(root, 'node');
|
|
23
|
+
const bun = runtimeCommand(root, 'bun');
|
|
24
|
+
return {
|
|
25
|
+
node: (await $`${node} --version`.cwd(root).text()).trim().replace(/^v/, ''),
|
|
26
|
+
bun: (await $`${bun} --version`.cwd(root).text()).trim(),
|
|
27
|
+
};
|
|
28
|
+
}
|
|
5
29
|
|
|
6
30
|
export async function syncRootRuntimeVersions(root: string): Promise<void> {
|
|
7
31
|
const packageJsonPath = join(root, 'package.json');
|
|
@@ -9,20 +33,17 @@ export async function syncRootRuntimeVersions(root: string): Promise<void> {
|
|
|
9
33
|
if (!packageJson) {
|
|
10
34
|
throw new Error('package.json not found or invalid');
|
|
11
35
|
}
|
|
12
|
-
const node =
|
|
13
|
-
const bun = runtimeCommand(root, 'bun');
|
|
14
|
-
const nodeVersion = (await $`${node} --version`.cwd(root).text()).trim().replace(/^v/, '');
|
|
15
|
-
const bunVersion = (await $`${bun} --version`.cwd(root).text()).trim();
|
|
36
|
+
const { node: nodeVersion, bun: bunVersion } = await runtimeVersionsFromPath(root);
|
|
16
37
|
const nodeMajor = nodeVersion.split('.', 1)[0];
|
|
17
38
|
if (!nodeMajor) {
|
|
18
39
|
throw new Error(`Unable to derive Node major version from ${nodeVersion}`);
|
|
19
40
|
}
|
|
20
41
|
|
|
21
42
|
let changed = false;
|
|
22
|
-
const engines =
|
|
43
|
+
const engines = ensureEngines(packageJson);
|
|
23
44
|
changed = setStringProperty(engines, 'node', `>=${nodeMajor}.0.0`) || changed;
|
|
24
|
-
changed =
|
|
25
|
-
const devDependencies =
|
|
45
|
+
changed = setPackageStringField(packageJson, 'packageManager', `bun@${bunVersion}`) || changed;
|
|
46
|
+
const devDependencies = ensureDependencyMap(packageJson, 'devDependencies');
|
|
26
47
|
changed =
|
|
27
48
|
setStringProperty(
|
|
28
49
|
devDependencies,
|
|
@@ -42,6 +63,58 @@ export async function syncRootRuntimeVersions(root: string): Promise<void> {
|
|
|
42
63
|
}
|
|
43
64
|
}
|
|
44
65
|
|
|
66
|
+
/**
|
|
67
|
+
* Validate that package.json runtime pins agree with the LIVE PATH runtimes,
|
|
68
|
+
* never a stored template. Offline by design: structural alignment only
|
|
69
|
+
* (majors, exact bun pin, no `~major.0.0` floor) — the registry is not
|
|
70
|
+
* consulted. Repair: `smoo monorepo init --runtime-only` inside the devenv shell.
|
|
71
|
+
*/
|
|
72
|
+
export async function validateRootRuntimeVersions(root: string): Promise<number> {
|
|
73
|
+
const packageJson = readJsonObject(join(root, 'package.json'));
|
|
74
|
+
if (!packageJson) {
|
|
75
|
+
console.error('package.json not found or invalid');
|
|
76
|
+
return 1;
|
|
77
|
+
}
|
|
78
|
+
return validateRuntimePins(packageJson, await runtimeVersionsFromPath(root));
|
|
79
|
+
}
|
|
80
|
+
|
|
81
|
+
export function validateRuntimePins(packageJson: PackageJson, runtime: RuntimeVersions): number {
|
|
82
|
+
const nodeMajor = runtime.node.split('.', 1)[0];
|
|
83
|
+
if (!nodeMajor) {
|
|
84
|
+
throw new Error(`Unable to derive Node major version from ${runtime.node}`);
|
|
85
|
+
}
|
|
86
|
+
let failures = 0;
|
|
87
|
+
const repair = 'run `smoo monorepo init --runtime-only` inside the devenv shell';
|
|
88
|
+
const enginesNode = packageJson.engines?.node ?? null;
|
|
89
|
+
if (enginesNode !== `>=${nodeMajor}.0.0`) {
|
|
90
|
+
console.error(
|
|
91
|
+
`package.json engines.node is ${enginesNode ?? 'missing'} but the PATH node is v${runtime.node} — expected >=${nodeMajor}.0.0; ${repair}`,
|
|
92
|
+
);
|
|
93
|
+
failures++;
|
|
94
|
+
}
|
|
95
|
+
const packageManager = packageJson.packageManager ?? null;
|
|
96
|
+
if (packageManager !== `bun@${runtime.bun}`) {
|
|
97
|
+
console.error(
|
|
98
|
+
`package.json packageManager is ${packageManager ?? 'missing'} but the PATH bun is ${runtime.bun} — expected bun@${runtime.bun}; ${repair}`,
|
|
99
|
+
);
|
|
100
|
+
failures++;
|
|
101
|
+
}
|
|
102
|
+
const typesNode = packageJson.devDependencies?.['@types/node'] ?? null;
|
|
103
|
+
const typesNodeParts = typesNode ? /^~(\d+)\.(\d+)\.(\d+)$/.exec(typesNode) : null;
|
|
104
|
+
if (!typesNodeParts || typesNodeParts[1] !== nodeMajor) {
|
|
105
|
+
console.error(
|
|
106
|
+
`package.json @types/node is ${typesNode ?? 'missing'} but the PATH node is v${runtime.node} — types track the runtime major (~${nodeMajor}.x.y, newest published minor); ${repair}`,
|
|
107
|
+
);
|
|
108
|
+
failures++;
|
|
109
|
+
} else if (typesNodeParts[2] === '0' && typesNodeParts[3] === '0') {
|
|
110
|
+
console.error(
|
|
111
|
+
`package.json @types/node is pinned to the ~${nodeMajor}.0.0 floor — tilde locks the first patch line and strands the repo on early broken releases; ${repair} to repin to the newest published ${nodeMajor}.x`,
|
|
112
|
+
);
|
|
113
|
+
failures++;
|
|
114
|
+
}
|
|
115
|
+
return failures;
|
|
116
|
+
}
|
|
117
|
+
|
|
45
118
|
type RuntimeTypesPinMode = 'major' | 'exact';
|
|
46
119
|
|
|
47
120
|
async function runtimeTypesRange(
|
|
@@ -51,8 +124,8 @@ async function runtimeTypesRange(
|
|
|
51
124
|
pinMode: RuntimeTypesPinMode,
|
|
52
125
|
): Promise<string> {
|
|
53
126
|
const versionsText = await $`bun pm view ${packageName} versions --json`.cwd(root).text();
|
|
54
|
-
const versions =
|
|
55
|
-
if (!
|
|
127
|
+
const versions = parseStringArrayText(versionsText);
|
|
128
|
+
if (!versions) {
|
|
56
129
|
throw new Error(`Unable to read published ${packageName} versions`);
|
|
57
130
|
}
|
|
58
131
|
return runtimeTypesRangeForPublishedVersions(packageName, runtimeVersion, pinMode, versions);
|
|
@@ -71,8 +144,13 @@ export function runtimeTypesRangeForPublishedVersions(
|
|
|
71
144
|
|
|
72
145
|
if (pinMode === 'major') {
|
|
73
146
|
const runtimeMajor = parsedRuntimeVersion[0].toString();
|
|
74
|
-
|
|
75
|
-
|
|
147
|
+
// Newest published types WITHIN the runtime major — never the `~major.0.0`
|
|
148
|
+
// floor: tilde locks the patch line, so the floor can strand consumers on a
|
|
149
|
+
// broken early release (e.g. @types/node 24.0.x's URLPattern/DOM TS2403
|
|
150
|
+
// conflict, fixed in 24.13) with no path to the repaired minors.
|
|
151
|
+
const latestInMajor = latestVersion(versions.filter((version) => versionMajor(version) === runtimeMajor));
|
|
152
|
+
if (latestInMajor) {
|
|
153
|
+
return `~${latestInMajor}`;
|
|
76
154
|
}
|
|
77
155
|
} else if (versions.includes(runtimeVersion)) {
|
|
78
156
|
return runtimeVersion;
|
|
@@ -13,13 +13,20 @@ import {
|
|
|
13
13
|
const registryVersions: Record<string, string[]> = {
|
|
14
14
|
'@biomejs/biome': ['2.3.5'],
|
|
15
15
|
'@nx/js': ['23.1.0'],
|
|
16
|
+
'@smoothbricks/cli': ['0.10.3', '0.10.4'],
|
|
16
17
|
'@smoothbricks/nx-plugin': ['0.3.0'],
|
|
17
18
|
eslint: ['9.39.1'],
|
|
18
19
|
'eslint-stdout': ['1.1.1', '1.1.2'],
|
|
19
20
|
nx: ['23.1.0'],
|
|
20
21
|
prettier: ['3.6.1'],
|
|
21
|
-
ttsc: ['0.
|
|
22
|
-
typescript: ['
|
|
22
|
+
ttsc: ['0.19.3'],
|
|
23
|
+
typescript: ['6.0.3'],
|
|
24
|
+
// alias package is not fetched from registry under this name when using fallback
|
|
25
|
+
'@typescript/native': ['7.0.2'],
|
|
26
|
+
};
|
|
27
|
+
|
|
28
|
+
const registryLatestTags: Record<string, string> = {
|
|
29
|
+
'@smoothbricks/cli': '0.10.4',
|
|
23
30
|
};
|
|
24
31
|
|
|
25
32
|
const realFetch = globalThis.fetch;
|
|
@@ -58,9 +65,9 @@ describe('tool configuration validation', () => {
|
|
|
58
65
|
`,
|
|
59
66
|
);
|
|
60
67
|
|
|
61
|
-
expect(validateToolConfig(root)).toBeGreaterThan(0);
|
|
68
|
+
expect(await validateToolConfig(root)).toBeGreaterThan(0);
|
|
62
69
|
await applyToolConfigDefaults(root);
|
|
63
|
-
expect(validateToolConfig(root)).toBe(0);
|
|
70
|
+
expect(await validateToolConfig(root)).toBe(0);
|
|
64
71
|
|
|
65
72
|
const rootPackage = JSON.parse(await readFile(join(root, 'package.json'), 'utf8'));
|
|
66
73
|
const toolingPackage = JSON.parse(await readFile(join(root, 'tooling/package.json'), 'utf8'));
|
|
@@ -69,6 +76,10 @@ describe('tool configuration validation', () => {
|
|
|
69
76
|
expect(rootPackage.devDependencies['@smoothbricks/nx-plugin']).toBe('workspace:*');
|
|
70
77
|
expect(rootPackage.devDependencies['eslint-stdout']).toBe('workspace:*');
|
|
71
78
|
expect(rootPackage.devDependencies.nx).toBe('23.1.0');
|
|
79
|
+
expect(rootPackage.devDependencies.ttsc).toBe('0.19.3');
|
|
80
|
+
expect(rootPackage.devDependencies.typescript).toBe('^6.0.3');
|
|
81
|
+
expect(rootPackage.devDependencies['@typescript/native']).toBe('npm:typescript@^7.0.2');
|
|
82
|
+
expect(rootPackage.patchedDependencies['ttsc@0.19.3']).toBe('patches/ttsc@0.19.3.patch');
|
|
72
83
|
expect(rootPackage.workspaces).toContain('tooling');
|
|
73
84
|
expect(toolingPackage.name).toBe('@smoothbricks/tooling');
|
|
74
85
|
expect(toolingPackage.dependencies['@smoothbricks/cli']).toBe('workspace:*');
|
|
@@ -97,8 +108,12 @@ describe('tool configuration validation', () => {
|
|
|
97
108
|
'eslint-stdout': await currentEslintStdoutRange(),
|
|
98
109
|
nx: '24.0.0',
|
|
99
110
|
prettier: '^3.7.0',
|
|
100
|
-
ttsc: '
|
|
111
|
+
ttsc: '0.19.3',
|
|
101
112
|
typescript: '^6.0.0',
|
|
113
|
+
'@typescript/native': 'npm:typescript@^7.0.2',
|
|
114
|
+
},
|
|
115
|
+
patchedDependencies: {
|
|
116
|
+
'ttsc@0.19.3': 'patches/ttsc@0.19.3.patch',
|
|
102
117
|
},
|
|
103
118
|
});
|
|
104
119
|
await writeJson(join(root, 'tooling/package.json'), {
|
|
@@ -128,18 +143,17 @@ describe('tool configuration validation', () => {
|
|
|
128
143
|
`,
|
|
129
144
|
);
|
|
130
145
|
|
|
131
|
-
expect(validateToolConfig(root)).toBe(0);
|
|
146
|
+
expect(await validateToolConfig(root)).toBe(0);
|
|
132
147
|
} finally {
|
|
133
148
|
await rm(root, { recursive: true, force: true });
|
|
134
149
|
}
|
|
135
150
|
});
|
|
136
151
|
|
|
137
|
-
it('
|
|
152
|
+
it('bumps consumer CLI pin to npm latest even when the running CLI is a linked prerelease', async () => {
|
|
138
153
|
const root = await mkdtemp(join(tmpdir(), 'smoo-tool-validation-'));
|
|
139
154
|
try {
|
|
140
155
|
const configuredRange = '^0.10.1';
|
|
141
|
-
const
|
|
142
|
-
const expectedRange = runningRange.includes('-') ? configuredRange : runningRange;
|
|
156
|
+
const expectedRange = `^${registryLatestTags['@smoothbricks/cli']}`;
|
|
143
157
|
await writeJson(join(root, 'package.json'), {
|
|
144
158
|
name: '@fixture/app',
|
|
145
159
|
version: '0.0.0',
|
|
@@ -152,7 +166,7 @@ describe('tool configuration validation', () => {
|
|
|
152
166
|
dependencies: { '@smoothbricks/cli': configuredRange },
|
|
153
167
|
});
|
|
154
168
|
|
|
155
|
-
const context = readToolContext(root);
|
|
169
|
+
const context = await readToolContext(root);
|
|
156
170
|
expect(context.policy.cliDependencyRange).toBe(expectedRange);
|
|
157
171
|
applyToolingPackageDefaults(root, context.policy);
|
|
158
172
|
|
|
@@ -172,7 +186,7 @@ describe('tool configuration validation', () => {
|
|
|
172
186
|
private: true,
|
|
173
187
|
workspaces: ['packages/*', 'tooling'],
|
|
174
188
|
});
|
|
175
|
-
applyToolingPackageDefaults(root, readToolContext(root).policy);
|
|
189
|
+
applyToolingPackageDefaults(root, (await readToolContext(root)).policy);
|
|
176
190
|
|
|
177
191
|
const toolingPackage = JSON.parse(await readFile(join(root, 'tooling/package.json'), 'utf8'));
|
|
178
192
|
expect(toolingPackage.name).toBe('@smoothbricks/tooling');
|
|
@@ -196,12 +210,12 @@ describe('tool configuration validation', () => {
|
|
|
196
210
|
eslint: '^10.0.0',
|
|
197
211
|
nx: '24.0.0',
|
|
198
212
|
prettier: '^3.7.0',
|
|
199
|
-
ttsc: '
|
|
213
|
+
ttsc: '0.19.3',
|
|
200
214
|
typescript: '^6.0.0',
|
|
201
215
|
},
|
|
202
216
|
});
|
|
203
217
|
|
|
204
|
-
const context = readToolContext(root);
|
|
218
|
+
const context = await readToolContext(root);
|
|
205
219
|
await applyRootDevDependencyDefaults(root, context);
|
|
206
220
|
applyToolingPackageDefaults(root, context.policy);
|
|
207
221
|
|
|
@@ -209,6 +223,8 @@ describe('tool configuration validation', () => {
|
|
|
209
223
|
const toolingPackage = JSON.parse(await readFile(join(root, 'tooling/package.json'), 'utf8'));
|
|
210
224
|
expect(rootPackage.devDependencies['eslint-stdout']).toBe(await currentEslintStdoutRange());
|
|
211
225
|
expect(rootPackage.devDependencies['@smoothbricks/nx-plugin']).toBe(await currentNxPluginRange());
|
|
226
|
+
expect(rootPackage.devDependencies['@typescript/native']).toBe('npm:typescript@^7.0.2');
|
|
227
|
+
expect(rootPackage.patchedDependencies?.['ttsc@0.19.3']).toBe('patches/ttsc@0.19.3.patch');
|
|
212
228
|
expect(toolingPackage.name).toBe('@fixture/tooling');
|
|
213
229
|
expect(toolingPackage.dependencies['@smoothbricks/cli']).toBe(await currentCliRange());
|
|
214
230
|
} finally {
|
|
@@ -218,8 +234,7 @@ describe('tool configuration validation', () => {
|
|
|
218
234
|
});
|
|
219
235
|
|
|
220
236
|
async function currentCliRange(): Promise<string> {
|
|
221
|
-
|
|
222
|
-
return `^${pkg.version}`;
|
|
237
|
+
return `^${registryLatestTags['@smoothbricks/cli']}`;
|
|
223
238
|
}
|
|
224
239
|
|
|
225
240
|
async function currentEslintStdoutRange(): Promise<string> {
|
|
@@ -235,8 +250,15 @@ const mockRegistryFetch = Object.assign(
|
|
|
235
250
|
if (!versions) {
|
|
236
251
|
return Promise.resolve(new Response('{}', { status: 404 }));
|
|
237
252
|
}
|
|
253
|
+
const body: Record<string, unknown> = {
|
|
254
|
+
versions: Object.fromEntries(versions.map((version) => [version, {}])),
|
|
255
|
+
};
|
|
256
|
+
const latest = registryLatestTags[packageName];
|
|
257
|
+
if (latest) {
|
|
258
|
+
body['dist-tags'] = { latest };
|
|
259
|
+
}
|
|
238
260
|
return Promise.resolve(
|
|
239
|
-
new Response(JSON.stringify(
|
|
261
|
+
new Response(JSON.stringify(body), {
|
|
240
262
|
status: 200,
|
|
241
263
|
headers: { 'content-type': 'application/json' },
|
|
242
264
|
}),
|