@barekey/cli 0.3.2 → 0.4.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/bun.lock CHANGED
@@ -5,7 +5,7 @@
5
5
  "": {
6
6
  "name": "@barekey/cli",
7
7
  "dependencies": {
8
- "@barekey/sdk": "^0.3.1",
8
+ "@barekey/sdk": "^0.5.0",
9
9
  "@clack/prompts": "^0.11.0",
10
10
  "commander": "^14.0.1",
11
11
  "open": "^10.2.0",
@@ -18,7 +18,7 @@
18
18
  },
19
19
  },
20
20
  "packages": {
21
- "@barekey/sdk": ["@barekey/sdk@0.3.1", "", {}, "sha512-IrVFvOzHYr/PVcW4VTJtbB05X9alQadrYNntQx3Uy3KUNs6IEI6CndV/roeT2A9nS7FxaHjfpOEBkEULpALPiA=="],
21
+ "@barekey/sdk": ["@barekey/sdk@0.5.0", "", {}, "sha512-+8RoKix9DZee3ZheGP5wJLnet6XaEGHTfcJOuvtJLmfQKRBllUy+wevsvELi1wOjw42pWaG3DYyb68XHznZRQw=="],
22
22
 
23
23
  "@clack/core": ["@clack/core@0.5.0", "", { "dependencies": { "picocolors": "^1.0.0", "sisteransi": "^1.0.5" } }, "sha512-p3y0FIOwaYRUPRcMO7+dlmLh8PSRcrjuTndsiA0WAFbWES0mLZlrjVoBRZ9DzkPFJZG6KGkJmoEAY0ZcVWTkow=="],
24
24
 
@@ -13,7 +13,7 @@ export type EnvTargetOptions = {
13
13
  export declare function toJsonOutput(enabled: boolean, value: unknown): void;
14
14
  export declare function resolveBaseUrl(explicit: string | undefined): Promise<string>;
15
15
  export declare function requireLocalSession(): Promise<LocalSession>;
16
- export declare function resolveTarget(options: EnvTargetOptions, local: LocalSession): Promise<{
16
+ export declare function resolveTarget(options: EnvTargetOptions, local?: LocalSession | null): Promise<{
17
17
  projectSlug: string;
18
18
  stageSlug: string;
19
19
  orgSlug?: string;
@@ -39,10 +39,11 @@ export async function requireLocalSession() {
39
39
  }
40
40
  export async function resolveTarget(options, local) {
41
41
  const runtime = await loadRuntimeConfig();
42
+ const isStandalone = runtime?.config.config?.mode === "standalone";
42
43
  const projectSlug = options.project?.trim() || runtime?.config.project || "";
43
44
  const stageSlug = options.stage?.trim() || runtime?.config.environment || "";
44
- const orgSlug = options.org?.trim() || runtime?.config.org || local.credentials.orgSlug;
45
- if (projectSlug.length === 0 || stageSlug.length === 0) {
45
+ const orgSlug = options.org?.trim() || runtime?.config.org || local?.credentials.orgSlug || "";
46
+ if (!isStandalone && (projectSlug.length === 0 || stageSlug.length === 0)) {
46
47
  const hint = runtime
47
48
  ? `Found ${runtime.path} but project/environment is incomplete.`
48
49
  : "No barekey.json found in current directory tree.";
@@ -5,8 +5,32 @@ import pc from "picocolors";
5
5
  import { createCliAuthProvider } from "../auth-provider.js";
6
6
  import { addTargetOptions, dotenvEscape, parseChance, requireLocalSession, resolveTarget, toJsonOutput, } from "../command-utils.js";
7
7
  import { postJson } from "../http.js";
8
+ import { loadRuntimeConfig } from "../runtime-config.js";
8
9
  import { collectOptionValues, parseRolloutFunction, parseRolloutMilestones, parseVisibility, } from "./env-helpers.js";
9
10
  function createEnvClient(input) {
11
+ if (input.runtimeConfig !== null) {
12
+ const organization = input.organization?.trim();
13
+ const isStandalone = input.runtimeConfig.config.config?.mode === "standalone";
14
+ if (!organization && !isStandalone) {
15
+ throw new Error("Organization slug is required.");
16
+ }
17
+ const jsonConfig = {
18
+ ...(organization ? { organization } : {}),
19
+ ...(input.project.trim().length > 0 ? { project: input.project } : {}),
20
+ ...(input.environment.trim().length > 0 ? { environment: input.environment } : {}),
21
+ ...(input.runtimeConfig.config.config === undefined
22
+ ? {}
23
+ : {
24
+ config: {
25
+ typegen: input.runtimeConfig.config.config.typegen,
26
+ mode: input.runtimeConfig.config.config.mode,
27
+ },
28
+ }),
29
+ };
30
+ return new BarekeyClient({
31
+ json: jsonConfig,
32
+ });
33
+ }
10
34
  const organization = input.organization?.trim();
11
35
  if (!organization) {
12
36
  throw new Error("Organization slug is required.");
@@ -18,12 +42,14 @@ function createEnvClient(input) {
18
42
  });
19
43
  }
20
44
  async function runEnvGet(name, options) {
21
- const local = await requireLocalSession();
45
+ const runtime = await loadRuntimeConfig();
46
+ const local = runtime?.config.config?.mode === "standalone" ? null : await requireLocalSession();
22
47
  const target = await resolveTarget(options, local);
23
48
  const client = createEnvClient({
24
- organization: target.orgSlug ?? local.credentials.orgSlug,
49
+ organization: target.orgSlug ?? local?.credentials.orgSlug,
25
50
  project: target.projectSlug,
26
51
  environment: target.stageSlug,
52
+ runtimeConfig: runtime,
27
53
  });
28
54
  const value = await client.get(name, {
29
55
  seed: options.seed,
@@ -39,12 +65,14 @@ async function runEnvGet(name, options) {
39
65
  console.log(String(value));
40
66
  }
41
67
  async function runEnvGetMany(options) {
42
- const local = await requireLocalSession();
68
+ const runtime = await loadRuntimeConfig();
69
+ const local = runtime?.config.config?.mode === "standalone" ? null : await requireLocalSession();
43
70
  const target = await resolveTarget(options, local);
44
71
  const client = createEnvClient({
45
- organization: target.orgSlug ?? local.credentials.orgSlug,
72
+ organization: target.orgSlug ?? local?.credentials.orgSlug,
46
73
  project: target.projectSlug,
47
74
  environment: target.stageSlug,
75
+ runtimeConfig: runtime,
48
76
  });
49
77
  const names = options.names
50
78
  .split(",")
@@ -1,6 +1,7 @@
1
1
  import { BarekeyClient } from "@barekey/sdk/server";
2
2
  import pc from "picocolors";
3
3
  import { addTargetOptions, requireLocalSession, resolveTarget, } from "../command-utils.js";
4
+ import { loadRuntimeConfig } from "../runtime-config.js";
4
5
  const DEFAULT_TYPEGEN_WATCH_INTERVAL_MS = 5_000;
5
6
  export function formatTypegenResultMessage(result) {
6
7
  const title = result.written
@@ -39,22 +40,35 @@ function sleep(milliseconds) {
39
40
  });
40
41
  }
41
42
  async function resolveTypegenClient(options) {
42
- const local = await requireLocalSession();
43
+ const runtime = await loadRuntimeConfig();
44
+ const local = runtime?.config.config?.mode === "standalone" ? null : await requireLocalSession();
43
45
  const target = await resolveTarget(options, local);
44
- const organization = target.orgSlug ?? local.credentials.orgSlug;
45
- if (!organization || organization.trim().length === 0) {
46
+ const isStandalone = runtime?.config.config?.mode === "standalone";
47
+ const organization = target.orgSlug ?? local?.credentials.orgSlug;
48
+ if ((!organization || organization.trim().length === 0) && !isStandalone) {
46
49
  throw new Error("Organization slug is required.");
47
50
  }
51
+ const jsonConfig = {
52
+ ...(organization && organization.trim().length > 0 ? { organization } : {}),
53
+ ...(target.projectSlug.trim().length > 0 ? { project: target.projectSlug } : {}),
54
+ ...(target.stageSlug.trim().length > 0 ? { environment: target.stageSlug } : {}),
55
+ ...(runtime?.config.config?.typegen === undefined
56
+ ? {}
57
+ : {
58
+ config: {
59
+ typegen: runtime.config.config.typegen,
60
+ mode: runtime.config.config.mode,
61
+ },
62
+ }),
63
+ };
48
64
  return {
49
65
  client: new BarekeyClient({
50
- organization,
51
- project: target.projectSlug,
52
- environment: target.stageSlug,
66
+ json: jsonConfig,
53
67
  typegen: false,
54
68
  }),
55
- organization,
56
- project: target.projectSlug,
57
- environment: target.stageSlug,
69
+ organization: organization && organization.trim().length > 0 ? organization : "local",
70
+ project: target.projectSlug.trim().length > 0 ? target.projectSlug : "standalone",
71
+ environment: target.stageSlug.trim().length > 0 ? target.stageSlug : "local",
58
72
  };
59
73
  }
60
74
  async function runTypegen(options) {
@@ -1,4 +1,4 @@
1
1
  export declare const CLI_NAME = "barekey";
2
2
  export declare const CLI_DESCRIPTION = "Barekey CLI";
3
- export declare const CLI_VERSION = "0.3.2";
3
+ export declare const CLI_VERSION = "0.4.0";
4
4
  export declare const DEFAULT_BAREKEY_API_URL = "https://api.barekey.dev";
package/dist/constants.js CHANGED
@@ -1,4 +1,4 @@
1
1
  export const CLI_NAME = "barekey";
2
2
  export const CLI_DESCRIPTION = "Barekey CLI";
3
- export const CLI_VERSION = "0.3.2";
3
+ export const CLI_VERSION = "0.4.0";
4
4
  export const DEFAULT_BAREKEY_API_URL = "https://api.barekey.dev";
@@ -2,6 +2,10 @@ export type BarekeyRuntimeConfig = {
2
2
  org?: string;
3
3
  project?: string;
4
4
  environment?: string;
5
+ config?: {
6
+ typegen?: "semantic" | "minimal";
7
+ mode?: "centralized" | "standalone";
8
+ };
5
9
  };
6
10
  export type BarekeyRuntimeConfigResult = {
7
11
  config: BarekeyRuntimeConfig;
@@ -30,6 +30,9 @@ export async function loadRuntimeConfig() {
30
30
  }
31
31
  const raw = await readFile(configPath, "utf8");
32
32
  const parsed = JSON.parse(raw);
33
+ const config = typeof parsed.config === "object" && parsed.config !== null
34
+ ? parsed.config
35
+ : undefined;
33
36
  return {
34
37
  path: configPath,
35
38
  config: {
@@ -44,6 +47,20 @@ export async function loadRuntimeConfig() {
44
47
  : typeof parsed.stage === "string"
45
48
  ? parsed.stage.trim()
46
49
  : undefined,
50
+ config: {
51
+ mode: config?.mode === "centralized" || config?.mode === "standalone"
52
+ ? config.mode
53
+ : "centralized",
54
+ typegen: (config?.mode === "centralized" || config?.mode === "standalone"
55
+ ? config.mode
56
+ : "centralized") === "standalone"
57
+ ? "minimal"
58
+ : config?.typegen === "semantic" || config?.typegen === "minimal"
59
+ ? config.typegen
60
+ : parsed.typegen === "semantic" || parsed.typegen === "minimal"
61
+ ? parsed.typegen
62
+ : "semantic",
63
+ },
47
64
  },
48
65
  };
49
66
  }
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@barekey/cli",
3
- "version": "0.3.2",
3
+ "version": "0.4.0",
4
4
  "description": "Barekey command line interface",
5
5
  "type": "module",
6
6
  "bin": {
@@ -15,7 +15,7 @@
15
15
  "packageManager": "bun@1.2.22",
16
16
  "dependencies": {
17
17
  "@clack/prompts": "^0.11.0",
18
- "@barekey/sdk": "^0.3.1",
18
+ "@barekey/sdk": "^0.5.0",
19
19
  "commander": "^14.0.1",
20
20
  "open": "^10.2.0",
21
21
  "picocolors": "^1.1.1"
@@ -63,19 +63,20 @@ export async function requireLocalSession(): Promise<LocalSession> {
63
63
 
64
64
  export async function resolveTarget(
65
65
  options: EnvTargetOptions,
66
- local: LocalSession,
66
+ local?: LocalSession | null,
67
67
  ): Promise<{
68
68
  projectSlug: string;
69
69
  stageSlug: string;
70
70
  orgSlug?: string;
71
71
  }> {
72
72
  const runtime = await loadRuntimeConfig();
73
+ const isStandalone = runtime?.config.config?.mode === "standalone";
73
74
 
74
75
  const projectSlug = options.project?.trim() || runtime?.config.project || "";
75
76
  const stageSlug = options.stage?.trim() || runtime?.config.environment || "";
76
- const orgSlug = options.org?.trim() || runtime?.config.org || local.credentials.orgSlug;
77
+ const orgSlug = options.org?.trim() || runtime?.config.org || local?.credentials.orgSlug || "";
77
78
 
78
- if (projectSlug.length === 0 || stageSlug.length === 0) {
79
+ if (!isStandalone && (projectSlug.length === 0 || stageSlug.length === 0)) {
79
80
  const hint = runtime
80
81
  ? `Found ${runtime.path} but project/environment is incomplete.`
81
82
  : "No barekey.json found in current directory tree.";
@@ -2,6 +2,7 @@ import { writeFile } from "node:fs/promises";
2
2
 
3
3
  import { cancel, confirm, isCancel } from "@clack/prompts";
4
4
  import { BarekeyClient } from "@barekey/sdk/server";
5
+ import type { BarekeyJsonConfig } from "@barekey/sdk/server";
5
6
  import { Command } from "commander";
6
7
  import pc from "picocolors";
7
8
 
@@ -16,6 +17,7 @@ import {
16
17
  type EnvTargetOptions,
17
18
  } from "../command-utils.js";
18
19
  import { postJson } from "../http.js";
20
+ import { loadRuntimeConfig } from "../runtime-config.js";
19
21
  import {
20
22
  collectOptionValues,
21
23
  parseRolloutFunction,
@@ -29,7 +31,34 @@ function createEnvClient(input: {
29
31
  organization: string | undefined;
30
32
  project: string;
31
33
  environment: string;
34
+ runtimeConfig: Awaited<ReturnType<typeof loadRuntimeConfig>> | null;
32
35
  }): BarekeyClient {
36
+ if (input.runtimeConfig !== null) {
37
+ const organization = input.organization?.trim();
38
+ const isStandalone = input.runtimeConfig.config.config?.mode === "standalone";
39
+ if (!organization && !isStandalone) {
40
+ throw new Error("Organization slug is required.");
41
+ }
42
+
43
+ const jsonConfig: BarekeyJsonConfig = {
44
+ ...(organization ? { organization } : {}),
45
+ ...(input.project.trim().length > 0 ? { project: input.project } : {}),
46
+ ...(input.environment.trim().length > 0 ? { environment: input.environment } : {}),
47
+ ...(input.runtimeConfig.config.config === undefined
48
+ ? {}
49
+ : {
50
+ config: {
51
+ typegen: input.runtimeConfig.config.config.typegen,
52
+ mode: input.runtimeConfig.config.config.mode,
53
+ },
54
+ }),
55
+ };
56
+
57
+ return new BarekeyClient({
58
+ json: jsonConfig,
59
+ });
60
+ }
61
+
33
62
  const organization = input.organization?.trim();
34
63
  if (!organization) {
35
64
  throw new Error("Organization slug is required.");
@@ -50,12 +79,14 @@ async function runEnvGet(
50
79
  json?: boolean;
51
80
  },
52
81
  ): Promise<void> {
53
- const local = await requireLocalSession();
82
+ const runtime = await loadRuntimeConfig();
83
+ const local = runtime?.config.config?.mode === "standalone" ? null : await requireLocalSession();
54
84
  const target = await resolveTarget(options, local);
55
85
  const client = createEnvClient({
56
- organization: target.orgSlug ?? local.credentials.orgSlug,
86
+ organization: target.orgSlug ?? local?.credentials.orgSlug,
57
87
  project: target.projectSlug,
58
88
  environment: target.stageSlug,
89
+ runtimeConfig: runtime,
59
90
  });
60
91
  const value = await client.get(name, {
61
92
  seed: options.seed,
@@ -81,12 +112,14 @@ async function runEnvGetMany(
81
112
  json?: boolean;
82
113
  },
83
114
  ): Promise<void> {
84
- const local = await requireLocalSession();
115
+ const runtime = await loadRuntimeConfig();
116
+ const local = runtime?.config.config?.mode === "standalone" ? null : await requireLocalSession();
85
117
  const target = await resolveTarget(options, local);
86
118
  const client = createEnvClient({
87
- organization: target.orgSlug ?? local.credentials.orgSlug,
119
+ organization: target.orgSlug ?? local?.credentials.orgSlug,
88
120
  project: target.projectSlug,
89
121
  environment: target.stageSlug,
122
+ runtimeConfig: runtime,
90
123
  });
91
124
 
92
125
  const names = options.names
@@ -1,5 +1,5 @@
1
1
  import { BarekeyClient } from "@barekey/sdk/server";
2
- import type { BarekeyTypegenResult } from "@barekey/sdk/server";
2
+ import type { BarekeyJsonConfig, BarekeyTypegenResult } from "@barekey/sdk/server";
3
3
  import { Command } from "commander";
4
4
  import pc from "picocolors";
5
5
 
@@ -9,6 +9,7 @@ import {
9
9
  resolveTarget,
10
10
  type EnvTargetOptions,
11
11
  } from "../command-utils.js";
12
+ import { loadRuntimeConfig } from "../runtime-config.js";
12
13
 
13
14
  const DEFAULT_TYPEGEN_WATCH_INTERVAL_MS = 5_000;
14
15
 
@@ -66,23 +67,42 @@ async function resolveTypegenClient(options: EnvTargetOptions): Promise<{
66
67
  project: string;
67
68
  environment: string;
68
69
  }> {
69
- const local = await requireLocalSession();
70
+ const runtime = await loadRuntimeConfig();
71
+ const local = runtime?.config.config?.mode === "standalone" ? null : await requireLocalSession();
70
72
  const target = await resolveTarget(options, local);
71
- const organization = target.orgSlug ?? local.credentials.orgSlug;
72
- if (!organization || organization.trim().length === 0) {
73
+ const isStandalone = runtime?.config.config?.mode === "standalone";
74
+ const organization = target.orgSlug ?? local?.credentials.orgSlug;
75
+ if ((!organization || organization.trim().length === 0) && !isStandalone) {
73
76
  throw new Error("Organization slug is required.");
74
77
  }
75
78
 
79
+ const jsonConfig = {
80
+ ...(organization && organization.trim().length > 0 ? { organization } : {}),
81
+ ...(target.projectSlug.trim().length > 0 ? { project: target.projectSlug } : {}),
82
+ ...(target.stageSlug.trim().length > 0 ? { environment: target.stageSlug } : {}),
83
+ ...(runtime?.config.config?.typegen === undefined
84
+ ? {}
85
+ : {
86
+ config: {
87
+ typegen: runtime.config.config.typegen,
88
+ mode: runtime.config.config.mode,
89
+ },
90
+ }),
91
+ } as BarekeyJsonConfig & {
92
+ config?: {
93
+ typegen?: "semantic" | "minimal";
94
+ mode?: "centralized" | "standalone";
95
+ };
96
+ };
97
+
76
98
  return {
77
99
  client: new BarekeyClient({
78
- organization,
79
- project: target.projectSlug,
80
- environment: target.stageSlug,
100
+ json: jsonConfig as BarekeyJsonConfig,
81
101
  typegen: false,
82
102
  }),
83
- organization,
84
- project: target.projectSlug,
85
- environment: target.stageSlug,
103
+ organization: organization && organization.trim().length > 0 ? organization : "local",
104
+ project: target.projectSlug.trim().length > 0 ? target.projectSlug : "standalone",
105
+ environment: target.stageSlug.trim().length > 0 ? target.stageSlug : "local",
86
106
  };
87
107
  }
88
108
 
package/src/constants.ts CHANGED
@@ -1,4 +1,4 @@
1
1
  export const CLI_NAME = "barekey";
2
2
  export const CLI_DESCRIPTION = "Barekey CLI";
3
- export const CLI_VERSION = "0.3.2";
3
+ export const CLI_VERSION = "0.4.0";
4
4
  export const DEFAULT_BAREKEY_API_URL = "https://api.barekey.dev";
@@ -5,6 +5,10 @@ export type BarekeyRuntimeConfig = {
5
5
  org?: string;
6
6
  project?: string;
7
7
  environment?: string;
8
+ config?: {
9
+ typegen?: "semantic" | "minimal";
10
+ mode?: "centralized" | "standalone";
11
+ };
8
12
  };
9
13
 
10
14
  export type BarekeyRuntimeConfigResult = {
@@ -45,6 +49,10 @@ export async function loadRuntimeConfig(): Promise<BarekeyRuntimeConfigResult |
45
49
 
46
50
  const raw = await readFile(configPath, "utf8");
47
51
  const parsed = JSON.parse(raw) as Record<string, unknown>;
52
+ const config =
53
+ typeof parsed.config === "object" && parsed.config !== null
54
+ ? (parsed.config as Record<string, unknown>)
55
+ : undefined;
48
56
  return {
49
57
  path: configPath,
50
58
  config: {
@@ -61,6 +69,22 @@ export async function loadRuntimeConfig(): Promise<BarekeyRuntimeConfigResult |
61
69
  : typeof parsed.stage === "string"
62
70
  ? parsed.stage.trim()
63
71
  : undefined,
72
+ config: {
73
+ mode:
74
+ config?.mode === "centralized" || config?.mode === "standalone"
75
+ ? config.mode
76
+ : "centralized",
77
+ typegen:
78
+ (config?.mode === "centralized" || config?.mode === "standalone"
79
+ ? config.mode
80
+ : "centralized") === "standalone"
81
+ ? "minimal"
82
+ : config?.typegen === "semantic" || config?.typegen === "minimal"
83
+ ? config.typegen
84
+ : parsed.typegen === "semantic" || parsed.typegen === "minimal"
85
+ ? parsed.typegen
86
+ : "semantic",
87
+ },
64
88
  },
65
89
  };
66
90
  }
@@ -0,0 +1,125 @@
1
+ import { mkdtemp, mkdir, writeFile } from "node:fs/promises";
2
+ import { tmpdir } from "node:os";
3
+ import path from "node:path";
4
+
5
+ import { describe, expect, test } from "bun:test";
6
+
7
+ import { loadRuntimeConfig } from "../src/runtime-config";
8
+
9
+ async function createTempDir(prefix = "barekey-cli-test-"): Promise<string> {
10
+ return await mkdtemp(path.join(tmpdir(), prefix));
11
+ }
12
+
13
+ async function withWorkingDirectory<TValue>(
14
+ nextCwd: string,
15
+ fn: () => Promise<TValue>,
16
+ ): Promise<TValue> {
17
+ const previousCwd = process.cwd();
18
+ process.chdir(nextCwd);
19
+ try {
20
+ return await fn();
21
+ } finally {
22
+ process.chdir(previousCwd);
23
+ }
24
+ }
25
+
26
+ describe("loadRuntimeConfig", () => {
27
+ test("clamps standalone config.typegen to minimal", async () => {
28
+ const tempDir = await createTempDir();
29
+ const appDir = path.join(tempDir, "apps", "web");
30
+ await mkdir(appDir, {
31
+ recursive: true,
32
+ });
33
+ await writeFile(
34
+ path.join(tempDir, "barekey.json"),
35
+ JSON.stringify(
36
+ {
37
+ organization: "acme",
38
+ project: "api",
39
+ environment: "development",
40
+ config: {
41
+ mode: "standalone",
42
+ typegen: "semantic",
43
+ },
44
+ },
45
+ null,
46
+ 2,
47
+ ),
48
+ "utf8",
49
+ );
50
+
51
+ await withWorkingDirectory(appDir, async () => {
52
+ await expect(loadRuntimeConfig()).resolves.toMatchObject({
53
+ path: path.join(tempDir, "barekey.json"),
54
+ config: {
55
+ org: "acme",
56
+ project: "api",
57
+ environment: "development",
58
+ config: {
59
+ mode: "standalone",
60
+ typegen: "minimal",
61
+ },
62
+ },
63
+ });
64
+ });
65
+ });
66
+
67
+ test("defaults config flags when barekey.json omits them", async () => {
68
+ const tempDir = await createTempDir();
69
+ await writeFile(
70
+ path.join(tempDir, "barekey.json"),
71
+ JSON.stringify(
72
+ {
73
+ organization: "acme",
74
+ project: "api",
75
+ environment: "development",
76
+ },
77
+ null,
78
+ 2,
79
+ ),
80
+ "utf8",
81
+ );
82
+
83
+ await withWorkingDirectory(tempDir, async () => {
84
+ await expect(loadRuntimeConfig()).resolves.toMatchObject({
85
+ config: {
86
+ config: {
87
+ mode: "centralized",
88
+ typegen: "semantic",
89
+ },
90
+ },
91
+ });
92
+ });
93
+ });
94
+
95
+ test("keeps standalone config valid without platform scope fields", async () => {
96
+ const tempDir = await createTempDir();
97
+ await writeFile(
98
+ path.join(tempDir, "barekey.json"),
99
+ JSON.stringify(
100
+ {
101
+ config: {
102
+ mode: "standalone",
103
+ },
104
+ },
105
+ null,
106
+ 2,
107
+ ),
108
+ "utf8",
109
+ );
110
+
111
+ await withWorkingDirectory(tempDir, async () => {
112
+ await expect(loadRuntimeConfig()).resolves.toMatchObject({
113
+ config: {
114
+ org: undefined,
115
+ project: undefined,
116
+ environment: undefined,
117
+ config: {
118
+ mode: "standalone",
119
+ typegen: "minimal",
120
+ },
121
+ },
122
+ });
123
+ });
124
+ });
125
+ });