primitive-admin 1.0.61 → 1.0.63
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 +125 -69
- package/assets/skill/skills/primitive-platform/SKILL.md +336 -37
- package/dist/bin/primitive.js +25 -14
- package/dist/bin/primitive.js.map +1 -1
- package/dist/src/commands/analytics.js +36 -16
- package/dist/src/commands/analytics.js.map +1 -1
- package/dist/src/commands/apps.js +52 -188
- package/dist/src/commands/apps.js.map +1 -1
- package/dist/src/commands/blob-buckets.js +13 -153
- package/dist/src/commands/blob-buckets.js.map +1 -1
- package/dist/src/commands/collection-type-configs.js +14 -100
- package/dist/src/commands/collection-type-configs.js.map +1 -1
- package/dist/src/commands/collections.js +47 -8
- package/dist/src/commands/collections.js.map +1 -1
- package/dist/src/commands/config.d.ts +46 -0
- package/dist/src/commands/config.js +479 -0
- package/dist/src/commands/config.js.map +1 -0
- package/dist/src/commands/connections.js +12 -7
- package/dist/src/commands/connections.js.map +1 -1
- package/dist/src/commands/cron-triggers.js +84 -176
- package/dist/src/commands/cron-triggers.js.map +1 -1
- package/dist/src/commands/database-type-configs.d.ts +2 -0
- package/dist/src/commands/database-type-configs.js +171 -0
- package/dist/src/commands/database-type-configs.js.map +1 -0
- package/dist/src/commands/database-types.js +4 -4
- package/dist/src/commands/database-types.js.map +1 -1
- package/dist/src/commands/databases.d.ts +63 -0
- package/dist/src/commands/databases.js +649 -87
- package/dist/src/commands/databases.js.map +1 -1
- package/dist/src/commands/documents.js +869 -12
- package/dist/src/commands/documents.js.map +1 -1
- package/dist/src/commands/email-templates.js +21 -128
- package/dist/src/commands/email-templates.js.map +1 -1
- package/dist/src/commands/env.d.ts +12 -1
- package/dist/src/commands/env.js +115 -26
- package/dist/src/commands/env.js.map +1 -1
- package/dist/src/commands/feature-flags.d.ts +14 -0
- package/dist/src/commands/feature-flags.js +116 -0
- package/dist/src/commands/feature-flags.js.map +1 -0
- package/dist/src/commands/group-type-configs.js +14 -109
- package/dist/src/commands/group-type-configs.js.map +1 -1
- package/dist/src/commands/init.d.ts +24 -1
- package/dist/src/commands/init.js +1194 -279
- package/dist/src/commands/init.js.map +1 -1
- package/dist/src/commands/integrations.js +166 -435
- package/dist/src/commands/integrations.js.map +1 -1
- package/dist/src/commands/metadata-category-configs.d.ts +12 -0
- package/dist/src/commands/metadata-category-configs.js +112 -0
- package/dist/src/commands/metadata-category-configs.js.map +1 -0
- package/dist/src/commands/metadata.js +33 -141
- package/dist/src/commands/metadata.js.map +1 -1
- package/dist/src/commands/prompts.js +206 -563
- package/dist/src/commands/prompts.js.map +1 -1
- package/dist/src/commands/rule-sets.d.ts +1 -1
- package/dist/src/commands/rule-sets.js +16 -132
- package/dist/src/commands/rule-sets.js.map +1 -1
- package/dist/src/commands/scripts.d.ts +10 -0
- package/dist/src/commands/scripts.js +203 -241
- package/dist/src/commands/scripts.js.map +1 -1
- package/dist/src/commands/sessions.js +17 -5
- package/dist/src/commands/sessions.js.map +1 -1
- package/dist/src/commands/sync-app-settings.d.ts +113 -70
- package/dist/src/commands/sync-app-settings.js +193 -242
- package/dist/src/commands/sync-app-settings.js.map +1 -1
- package/dist/src/commands/sync.d.ts +1904 -51
- package/dist/src/commands/sync.js +9468 -1790
- package/dist/src/commands/sync.js.map +1 -1
- package/dist/src/commands/tokens.js +8 -2
- package/dist/src/commands/tokens.js.map +1 -1
- package/dist/src/commands/users.js +92 -1
- package/dist/src/commands/users.js.map +1 -1
- package/dist/src/commands/vars.js +44 -58
- package/dist/src/commands/vars.js.map +1 -1
- package/dist/src/commands/webhooks.js +318 -156
- package/dist/src/commands/webhooks.js.map +1 -1
- package/dist/src/commands/workflows.d.ts +49 -12
- package/dist/src/commands/workflows.js +652 -1086
- package/dist/src/commands/workflows.js.map +1 -1
- package/dist/src/lib/access-rule-display.d.ts +21 -0
- package/dist/src/lib/access-rule-display.js +34 -0
- package/dist/src/lib/access-rule-display.js.map +1 -0
- package/dist/src/lib/api-client.d.ts +541 -61
- package/dist/src/lib/api-client.js +559 -102
- package/dist/src/lib/api-client.js.map +1 -1
- package/dist/src/lib/app-settings-descriptor.d.ts +180 -25
- package/dist/src/lib/app-settings-descriptor.js +403 -82
- package/dist/src/lib/app-settings-descriptor.js.map +1 -1
- package/dist/src/lib/canonical-json.d.ts +12 -0
- package/dist/src/lib/canonical-json.js +35 -0
- package/dist/src/lib/canonical-json.js.map +1 -0
- package/dist/src/lib/cli-manifest.d.ts +8 -0
- package/dist/src/lib/cli-manifest.js +1 -0
- package/dist/src/lib/cli-manifest.js.map +1 -1
- package/dist/src/lib/codegen-shared/generatedFiles.d.ts +6 -2
- package/dist/src/lib/codegen-shared/generatedFiles.js +9 -2
- package/dist/src/lib/codegen-shared/generatedFiles.js.map +1 -1
- package/dist/src/lib/codegen-shared/resolveCodegenSourceDir.d.ts +6 -6
- package/dist/src/lib/codegen-shared/resolveCodegenSourceDir.js +8 -8
- package/dist/src/lib/codegen-shared/resolveCodegenSourceDir.js.map +1 -1
- package/dist/src/lib/config-object-descriptor.d.ts +127 -0
- package/dist/src/lib/config-object-descriptor.js +658 -0
- package/dist/src/lib/config-object-descriptor.js.map +1 -0
- package/dist/src/lib/config-payload.d.ts +85 -0
- package/dist/src/lib/config-payload.js +116 -0
- package/dist/src/lib/config-payload.js.map +1 -0
- package/dist/src/lib/config-surface.d.ts +130 -0
- package/dist/src/lib/config-surface.js +300 -0
- package/dist/src/lib/config-surface.js.map +1 -0
- package/dist/src/lib/credentials-store.d.ts +10 -0
- package/dist/src/lib/credentials-store.js +23 -0
- package/dist/src/lib/credentials-store.js.map +1 -1
- package/dist/src/lib/data-input.d.ts +23 -0
- package/dist/src/lib/data-input.js +50 -0
- package/dist/src/lib/data-input.js.map +1 -0
- package/dist/src/lib/db-codegen/dbTemplates.js +1 -1
- package/dist/src/lib/db-codegen/dbTemplates.js.map +1 -1
- package/dist/src/lib/db-codegen/dbTypeIR.d.ts +1 -1
- package/dist/src/lib/env-resolver-core.d.ts +187 -0
- package/dist/src/lib/env-resolver-core.js +325 -0
- package/dist/src/lib/env-resolver-core.js.map +1 -0
- package/dist/src/lib/env-resolver.d.ts +28 -6
- package/dist/src/lib/env-resolver.js +44 -32
- package/dist/src/lib/env-resolver.js.map +1 -1
- package/dist/src/lib/generated-allowlist.js +12 -0
- package/dist/src/lib/generated-allowlist.js.map +1 -1
- package/dist/src/lib/generated-config-surfaces.d.ts +682 -0
- package/dist/src/lib/generated-config-surfaces.js +4058 -0
- package/dist/src/lib/generated-config-surfaces.js.map +1 -0
- package/dist/src/lib/generated-template-lint.d.ts +212 -0
- package/dist/src/lib/generated-template-lint.js +624 -0
- package/dist/src/lib/generated-template-lint.js.map +1 -0
- package/dist/src/lib/init-adopt.d.ts +16 -0
- package/dist/src/lib/init-adopt.js +34 -0
- package/dist/src/lib/init-adopt.js.map +1 -0
- package/dist/src/lib/init-assets.d.ts +39 -0
- package/dist/src/lib/init-assets.js +97 -0
- package/dist/src/lib/init-assets.js.map +1 -0
- package/dist/src/lib/init-client-platforms.d.ts +14 -0
- package/dist/src/lib/init-client-platforms.js +71 -0
- package/dist/src/lib/init-client-platforms.js.map +1 -0
- package/dist/src/lib/init-config.d.ts +44 -5
- package/dist/src/lib/init-config.js +80 -7
- package/dist/src/lib/init-config.js.map +1 -1
- package/dist/src/lib/init-email-redirect-uris.d.ts +37 -0
- package/dist/src/lib/init-email-redirect-uris.js +46 -0
- package/dist/src/lib/init-email-redirect-uris.js.map +1 -0
- package/dist/src/lib/init-ios-links.d.ts +90 -0
- package/dist/src/lib/init-ios-links.js +218 -0
- package/dist/src/lib/init-ios-links.js.map +1 -0
- package/dist/src/lib/init-plan.d.ts +80 -0
- package/dist/src/lib/init-plan.js +95 -0
- package/dist/src/lib/init-plan.js.map +1 -0
- package/dist/src/lib/init-production-env.d.ts +48 -0
- package/dist/src/lib/init-production-env.js +59 -0
- package/dist/src/lib/init-production-env.js.map +1 -0
- package/dist/src/lib/init-schema.d.ts +74 -0
- package/dist/src/lib/init-schema.js +358 -0
- package/dist/src/lib/init-schema.js.map +1 -0
- package/dist/src/lib/init-xcode.d.ts +33 -0
- package/dist/src/lib/init-xcode.js +114 -0
- package/dist/src/lib/init-xcode.js.map +1 -0
- package/dist/src/lib/integration-request-config.d.ts +30 -0
- package/dist/src/lib/integration-request-config.js +145 -0
- package/dist/src/lib/integration-request-config.js.map +1 -0
- package/dist/src/lib/integration-selector.d.ts +42 -0
- package/dist/src/lib/integration-selector.js +46 -0
- package/dist/src/lib/integration-selector.js.map +1 -0
- package/dist/src/lib/local-state.d.ts +55 -0
- package/dist/src/lib/local-state.js +167 -0
- package/dist/src/lib/local-state.js.map +1 -0
- package/dist/src/lib/local-test-cases.d.ts +63 -0
- package/dist/src/lib/local-test-cases.js +135 -0
- package/dist/src/lib/local-test-cases.js.map +1 -0
- package/dist/src/lib/log-inspection.d.ts +568 -0
- package/dist/src/lib/log-inspection.js +639 -0
- package/dist/src/lib/log-inspection.js.map +1 -0
- package/dist/src/lib/migration-nag.d.ts +2 -2
- package/dist/src/lib/migration-nag.js +3 -3
- package/dist/src/lib/object-status-filter.d.ts +22 -0
- package/dist/src/lib/object-status-filter.js +45 -0
- package/dist/src/lib/object-status-filter.js.map +1 -0
- package/dist/src/lib/output.d.ts +24 -1
- package/dist/src/lib/output.js +42 -1
- package/dist/src/lib/output.js.map +1 -1
- package/dist/src/lib/package-manager.d.ts +140 -0
- package/dist/src/lib/package-manager.js +305 -0
- package/dist/src/lib/package-manager.js.map +1 -0
- package/dist/src/lib/paginate.d.ts +50 -0
- package/dist/src/lib/paginate.js +53 -0
- package/dist/src/lib/paginate.js.map +1 -1
- package/dist/src/lib/platform-owned.d.ts +29 -3
- package/dist/src/lib/platform-owned.js +42 -3
- package/dist/src/lib/platform-owned.js.map +1 -1
- package/dist/src/lib/project-config.d.ts +8 -0
- package/dist/src/lib/project-config.js +30 -5
- package/dist/src/lib/project-config.js.map +1 -1
- package/dist/src/lib/query-operators.d.ts +1 -1
- package/dist/src/lib/query-operators.js +1 -1
- package/dist/src/lib/record-filter.d.ts +18 -0
- package/dist/src/lib/record-filter.js +55 -0
- package/dist/src/lib/record-filter.js.map +1 -0
- package/dist/src/lib/resolve-init-dev-port.d.ts +56 -0
- package/dist/src/lib/resolve-init-dev-port.js +55 -0
- package/dist/src/lib/resolve-init-dev-port.js.map +1 -0
- package/dist/src/lib/resolve-init-server.d.ts +64 -0
- package/dist/src/lib/resolve-init-server.js +77 -0
- package/dist/src/lib/resolve-init-server.js.map +1 -0
- package/dist/src/lib/resolve-platform.d.ts +43 -14
- package/dist/src/lib/resolve-platform.js +74 -12
- package/dist/src/lib/resolve-platform.js.map +1 -1
- package/dist/src/lib/run-status.d.ts +19 -0
- package/dist/src/lib/run-status.generated.d.ts +39 -0
- package/dist/src/lib/run-status.generated.js +66 -0
- package/dist/src/lib/run-status.generated.js.map +1 -0
- package/dist/src/lib/run-status.js +19 -0
- package/dist/src/lib/run-status.js.map +1 -0
- package/dist/src/lib/server-text-normalization.d.ts +51 -0
- package/dist/src/lib/server-text-normalization.js +90 -0
- package/dist/src/lib/server-text-normalization.js.map +1 -0
- package/dist/src/lib/server-url.d.ts +22 -0
- package/dist/src/lib/server-url.js +33 -0
- package/dist/src/lib/server-url.js.map +1 -0
- package/dist/src/lib/signing-secret-status.d.ts +81 -0
- package/dist/src/lib/signing-secret-status.js +116 -0
- package/dist/src/lib/signing-secret-status.js.map +1 -0
- package/dist/src/lib/skill-installer.js +6 -3
- package/dist/src/lib/skill-installer.js.map +1 -1
- package/dist/src/lib/snapshots.d.ts +2 -2
- package/dist/src/lib/snapshots.js +2 -2
- package/dist/src/lib/swift-codegen/dbGenerator.d.ts +15 -2
- package/dist/src/lib/swift-codegen/dbGenerator.js +250 -18
- package/dist/src/lib/swift-codegen/dbGenerator.js.map +1 -1
- package/dist/src/lib/swift-codegen/generator.d.ts +11 -2
- package/dist/src/lib/swift-codegen/generator.js +181 -7
- package/dist/src/lib/swift-codegen/generator.js.map +1 -1
- package/dist/src/lib/swift-codegen/siblingSymbols.d.ts +7 -3
- package/dist/src/lib/swift-codegen/siblingSymbols.js +4 -1
- package/dist/src/lib/swift-codegen/siblingSymbols.js.map +1 -1
- package/dist/src/lib/sync-dir-selector.d.ts +21 -0
- package/dist/src/lib/sync-dir-selector.js +30 -0
- package/dist/src/lib/sync-dir-selector.js.map +1 -0
- package/dist/src/lib/sync-paths.d.ts +39 -0
- package/dist/src/lib/sync-paths.js +70 -2
- package/dist/src/lib/sync-paths.js.map +1 -1
- package/dist/src/lib/sync-resource-types.d.ts +138 -31
- package/dist/src/lib/sync-resource-types.js +241 -47
- package/dist/src/lib/sync-resource-types.js.map +1 -1
- package/dist/src/lib/sync-selectors.d.ts +95 -0
- package/dist/src/lib/sync-selectors.js +228 -0
- package/dist/src/lib/sync-selectors.js.map +1 -0
- package/dist/src/lib/template.d.ts +62 -4
- package/dist/src/lib/template.js +147 -39
- package/dist/src/lib/template.js.map +1 -1
- package/dist/src/lib/test-case-file-names.d.ts +40 -0
- package/dist/src/lib/test-case-file-names.js +91 -0
- package/dist/src/lib/test-case-file-names.js.map +1 -0
- package/dist/src/lib/test-case-keys.d.ts +29 -0
- package/dist/src/lib/test-case-keys.js +55 -0
- package/dist/src/lib/test-case-keys.js.map +1 -0
- package/dist/src/lib/test-case-variables.d.ts +15 -0
- package/dist/src/lib/test-case-variables.js +29 -0
- package/dist/src/lib/test-case-variables.js.map +1 -0
- package/dist/src/lib/toml-database-config.d.ts +4 -4
- package/dist/src/lib/toml-database-config.js +27 -34
- package/dist/src/lib/toml-database-config.js.map +1 -1
- package/dist/src/lib/toml-metadata-config.d.ts +9 -5
- package/dist/src/lib/toml-metadata-config.js +40 -45
- package/dist/src/lib/toml-metadata-config.js.map +1 -1
- package/dist/src/lib/toml-native-form.d.ts +1 -1
- package/dist/src/lib/toml-native-form.js +1 -1
- package/dist/src/lib/toml-params-validator.d.ts +1 -1
- package/dist/src/lib/toml-params-validator.js +1 -1
- package/dist/src/lib/toml-scalar-edit.d.ts +43 -0
- package/dist/src/lib/toml-scalar-edit.js +283 -0
- package/dist/src/lib/toml-scalar-edit.js.map +1 -0
- package/dist/src/lib/user-selector.d.ts +24 -0
- package/dist/src/lib/user-selector.js +33 -0
- package/dist/src/lib/user-selector.js.map +1 -0
- package/dist/src/lib/version-check.d.ts +25 -0
- package/dist/src/lib/version-check.js +77 -8
- package/dist/src/lib/version-check.js.map +1 -1
- package/dist/src/lib/watch.d.ts +121 -0
- package/dist/src/lib/watch.js +169 -0
- package/dist/src/lib/watch.js.map +1 -0
- package/dist/src/lib/web-url.d.ts +40 -0
- package/dist/src/lib/web-url.js +76 -0
- package/dist/src/lib/web-url.js.map +1 -0
- package/dist/src/lib/workflow-apply.d.ts +69 -45
- package/dist/src/lib/workflow-apply.js +99 -72
- package/dist/src/lib/workflow-apply.js.map +1 -1
- package/dist/src/lib/workflow-codegen/generator.js +4 -4
- package/dist/src/lib/workflow-codegen/generator.js.map +1 -1
- package/dist/src/lib/workflow-codegen/invokerIR.d.ts +11 -0
- package/dist/src/lib/workflow-codegen/invokerIR.js +5 -0
- package/dist/src/lib/workflow-codegen/invokerIR.js.map +1 -1
- package/dist/src/lib/workflow-config-apply.d.ts +70 -0
- package/dist/src/lib/workflow-config-apply.js +137 -0
- package/dist/src/lib/workflow-config-apply.js.map +1 -0
- package/dist/src/lib/workflow-config-sidecar.d.ts +63 -0
- package/dist/src/lib/workflow-config-sidecar.js +96 -0
- package/dist/src/lib/workflow-config-sidecar.js.map +1 -0
- package/dist/src/lib/workflow-defaults.d.ts +29 -0
- package/dist/src/lib/workflow-defaults.js +41 -0
- package/dist/src/lib/workflow-defaults.js.map +1 -0
- package/dist/src/lib/workflow-include-preserve.d.ts +76 -0
- package/dist/src/lib/workflow-include-preserve.js +286 -0
- package/dist/src/lib/workflow-include-preserve.js.map +1 -0
- package/dist/src/lib/workflow-payload.d.ts +31 -20
- package/dist/src/lib/workflow-payload.js +100 -110
- package/dist/src/lib/workflow-payload.js.map +1 -1
- package/dist/src/lib/workflow-toml-validator.d.ts +37 -16
- package/dist/src/lib/workflow-toml-validator.js +141 -16
- package/dist/src/lib/workflow-toml-validator.js.map +1 -1
- package/dist/src/types/index.d.ts +78 -22
- package/dist/src/validators.d.ts +7 -7
- package/dist/src/validators.js +6 -6
- package/package.json +11 -6
- package/dist/src/commands/settings.d.ts +0 -15
- package/dist/src/commands/settings.js +0 -102
- package/dist/src/commands/settings.js.map +0 -1
|
@@ -0,0 +1,187 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* The shared Primitive environment resolver (#2873).
|
|
3
|
+
*
|
|
4
|
+
* Three surfaces have to agree on which backend/app a project is pointed at:
|
|
5
|
+
* the CLI, the Vue build (`primitive-app`'s `primitiveEnv()` plugin), and the
|
|
6
|
+
* Swift template's pre-build script. This module is the single algorithm they
|
|
7
|
+
* share. The CLI owns it; `packages/primitive-app` carries a byte-identical
|
|
8
|
+
* GENERATED copy (`cli/scripts/gen-primitive-env-resolver.mjs`, checked for
|
|
9
|
+
* freshness by `cli/tests/unit/env-resolver-copy-drift-guard.test.ts`); the
|
|
10
|
+
* Swift script is an independent bash+python3 port pinned by a parity test.
|
|
11
|
+
*
|
|
12
|
+
* ── COPYABILITY (load-bearing) ────────────────────────────────────────────
|
|
13
|
+
* This file MUST stay self-contained: node builtins only, ZERO relative
|
|
14
|
+
* imports. The generator copies it verbatim into a package that cannot depend
|
|
15
|
+
* on the CLI, so any `./x.js` import here would break that copy at runtime.
|
|
16
|
+
* The drift guard asserts this.
|
|
17
|
+
*
|
|
18
|
+
* Scope: config discovery, the schema `version` check, structural validation,
|
|
19
|
+
* the local selection, the precedence, and the http→ws scheme swap. It
|
|
20
|
+
* deliberately does NOT duplicate the CLI's full field-level validation
|
|
21
|
+
* (`validateProjectConfig` in `project-config.ts`) — the CLI wrapper runs that
|
|
22
|
+
* first, and the other readers only need "version understood, shape sane, fail
|
|
23
|
+
* loudly otherwise".
|
|
24
|
+
*
|
|
25
|
+
* Precedence (one order, everywhere):
|
|
26
|
+
* 1. an explicit name (`--env` / `--primitive-env`)
|
|
27
|
+
* 2. PRIMITIVE_ENV (per-invocation intent, keeps CI working)
|
|
28
|
+
* 3. .primitive/local.json (this machine's `primitive env use`)
|
|
29
|
+
* 4. defaultEnvironment (the committed team default)
|
|
30
|
+
* 5. the sole environment, if there is exactly one
|
|
31
|
+
*/
|
|
32
|
+
/** Schema version of `.primitive/config.json` this core understands. */
|
|
33
|
+
export declare const PRIMITIVE_CONFIG_VERSION = 1;
|
|
34
|
+
/** Schema version of `.primitive/local.json` this core writes and reads. */
|
|
35
|
+
export declare const PRIMITIVE_LOCAL_STATE_VERSION = 1;
|
|
36
|
+
export declare const PROJECT_CONFIG_DIR = ".primitive";
|
|
37
|
+
export declare const PROJECT_CONFIG_FILENAME = "config.json";
|
|
38
|
+
export declare const LOCAL_STATE_FILENAME = "local.json";
|
|
39
|
+
export declare const PROJECT_CONFIG_DISPLAY_NAME = ".primitive/config.json";
|
|
40
|
+
export declare const LOCAL_STATE_DISPLAY_NAME = ".primitive/local.json";
|
|
41
|
+
/**
|
|
42
|
+
* Error kinds callers branch on. Every failure is one of these — no reader is
|
|
43
|
+
* ever left guessing what a broken config meant.
|
|
44
|
+
*/
|
|
45
|
+
export type PrimitiveEnvErrorKind = "missing-config" | "malformed-config" | "unsupported-version" | "corrupt-local-state" | "unknown-environment" | "no-selection" | "missing-app-id";
|
|
46
|
+
export declare class PrimitiveEnvError extends Error {
|
|
47
|
+
readonly kind: PrimitiveEnvErrorKind;
|
|
48
|
+
readonly path?: string;
|
|
49
|
+
constructor(kind: PrimitiveEnvErrorKind, message: string, path?: string);
|
|
50
|
+
}
|
|
51
|
+
export interface CoreEnvironmentEntry {
|
|
52
|
+
apiUrl: string;
|
|
53
|
+
appId?: string;
|
|
54
|
+
appName?: string;
|
|
55
|
+
/**
|
|
56
|
+
* The app's web counterpart for this environment, as a normalized origin
|
|
57
|
+
* (#2982). Read through `normalizeWebOrigin`, so a value this reader carries
|
|
58
|
+
* is always an origin — see that function for why the typed read other
|
|
59
|
+
* fields get is not enough here.
|
|
60
|
+
*/
|
|
61
|
+
webUrl?: string;
|
|
62
|
+
description?: string;
|
|
63
|
+
}
|
|
64
|
+
/**
|
|
65
|
+
* The app's web counterpart as a normalized ORIGIN, or undefined when the
|
|
66
|
+
* value cannot be one (#2982).
|
|
67
|
+
*
|
|
68
|
+
* Unlike `appId`/`appName`, a typed read is not enough. This value is not
|
|
69
|
+
* merely carried: the Swift app points its emailed sign-in link at
|
|
70
|
+
* `<webUrl>/oauth/callback` and trusts incoming universal links from the same
|
|
71
|
+
* origin, and BOTH jobs need an origin —
|
|
72
|
+
*
|
|
73
|
+
* - https except loopback, the rule the server applies to every redirect URI
|
|
74
|
+
* (`src/auth/redirect-uri.ts`): an origin that cannot be allow-listed turns
|
|
75
|
+
* every sign-in request into a 400, and a plain-http link would carry the
|
|
76
|
+
* magic token in clear;
|
|
77
|
+
* - no path, query or fragment: the web client serves its callback on its own
|
|
78
|
+
* origin plus `/oauth/callback`, which is also the exact path the
|
|
79
|
+
* `apple-app-site-association` component claims;
|
|
80
|
+
* - no credentials, which have no business in a link that goes out by email.
|
|
81
|
+
*
|
|
82
|
+
* `primitive env add --web-url` and the project-config validation reject those
|
|
83
|
+
* shapes with a field-named error, but neither is on the path from a
|
|
84
|
+
* hand-edited `.primitive/config.json` to an Xcode build: the Swift template's
|
|
85
|
+
* pre-build script reads the file directly. So every reader that feeds
|
|
86
|
+
* `primitive.json` applies the contract, and a value that misses it is read as
|
|
87
|
+
* "this environment has no web counterpart" — code-only email, no trusted
|
|
88
|
+
* origin, nothing silently pointed at the wrong URL.
|
|
89
|
+
*
|
|
90
|
+
* The message-producing twin of this rule lives in `cli/src/lib/web-url.ts`;
|
|
91
|
+
* this file cannot import it (see COPYABILITY above), and a test pins that the
|
|
92
|
+
* two agree.
|
|
93
|
+
*/
|
|
94
|
+
export declare function normalizeWebOrigin(value: unknown): string | undefined;
|
|
95
|
+
export interface CoreProjectConfig {
|
|
96
|
+
version: number;
|
|
97
|
+
defaultEnvironment?: string;
|
|
98
|
+
environments: Record<string, CoreEnvironmentEntry>;
|
|
99
|
+
}
|
|
100
|
+
/** Which precedence step picked the environment. Printed in the build banner. */
|
|
101
|
+
export type PrimitiveEnvSource = "explicit" | "env-var" | "local" | "default" | "sole";
|
|
102
|
+
export interface ResolvedPrimitiveEnv {
|
|
103
|
+
name: string;
|
|
104
|
+
apiUrl: string;
|
|
105
|
+
/** Derived from apiUrl by scheme swap — never authored separately. */
|
|
106
|
+
wsUrl: string;
|
|
107
|
+
appId?: string;
|
|
108
|
+
appName?: string;
|
|
109
|
+
/** The app's web counterpart for the SELECTED environment, if it has one. */
|
|
110
|
+
webUrl?: string;
|
|
111
|
+
description?: string;
|
|
112
|
+
source: PrimitiveEnvSource;
|
|
113
|
+
configPath: string;
|
|
114
|
+
localStatePath: string;
|
|
115
|
+
projectRoot: string;
|
|
116
|
+
}
|
|
117
|
+
export interface ResolveOptions {
|
|
118
|
+
/** Directory to start the upward walk from. Defaults to process.cwd(). */
|
|
119
|
+
cwd?: string;
|
|
120
|
+
/** Environment variables to read. Defaults to process.env. */
|
|
121
|
+
env?: Record<string, string | undefined>;
|
|
122
|
+
/** An explicit `--env` / `--primitive-env` value, if the caller has one. */
|
|
123
|
+
explicitEnvName?: string | null;
|
|
124
|
+
/** Use this config file instead of discovering one. */
|
|
125
|
+
configPath?: string;
|
|
126
|
+
/**
|
|
127
|
+
* Identity consumers (the Vite plugin, cf-deploy, the Swift script) cannot
|
|
128
|
+
* work without an app ID; plain CLI resolution can, and always could.
|
|
129
|
+
*/
|
|
130
|
+
requireAppId?: boolean;
|
|
131
|
+
}
|
|
132
|
+
/**
|
|
133
|
+
* Derives the WebSocket URL from the API URL. Every apiUrl/wsUrl pair in
|
|
134
|
+
* practice is the same host with the scheme swapped, so it is derived rather
|
|
135
|
+
* than authored — one less thing to get out of sync.
|
|
136
|
+
*/
|
|
137
|
+
export declare function deriveWsUrl(apiUrl: string): string;
|
|
138
|
+
/**
|
|
139
|
+
* Finds `.primitive/config.json` by walking up from `cwd`, or returns the
|
|
140
|
+
* PRIMITIVE_PROJECT_CONFIG override when it is set (and exists).
|
|
141
|
+
*/
|
|
142
|
+
export declare function findPrimitiveConfigPath(options?: {
|
|
143
|
+
cwd?: string;
|
|
144
|
+
env?: Record<string, string | undefined>;
|
|
145
|
+
}): string | null;
|
|
146
|
+
/**
|
|
147
|
+
* The project root for a config path: the parent of `.primitive/`, or the
|
|
148
|
+
* containing directory when the config was pointed at directly (a fixture via
|
|
149
|
+
* PRIMITIVE_PROJECT_CONFIG, which is not inside a `.primitive/` directory).
|
|
150
|
+
*/
|
|
151
|
+
export declare function projectRootForConfigPath(configPath: string): string;
|
|
152
|
+
/**
|
|
153
|
+
* Local state lives beside the config it belongs to, so a fixture-pointed
|
|
154
|
+
* config never picks up a real project's selection and vice versa.
|
|
155
|
+
*/
|
|
156
|
+
export declare function localStatePathForConfigPath(configPath: string): string;
|
|
157
|
+
/**
|
|
158
|
+
* Reads and structurally validates `.primitive/config.json`. Throws rather
|
|
159
|
+
* than guessing: a config that cannot be understood is always louder than a
|
|
160
|
+
* silent fallback to the wrong backend.
|
|
161
|
+
*/
|
|
162
|
+
export declare function readCoreProjectConfig(configPath: string): CoreProjectConfig;
|
|
163
|
+
/**
|
|
164
|
+
* Reads this machine's selection from `.primitive/local.json`. Returns null
|
|
165
|
+
* when there is no file or no selection in it; throws when the file exists but
|
|
166
|
+
* cannot be read as the shape `primitive env use` writes.
|
|
167
|
+
*/
|
|
168
|
+
export declare function readLocalSelection(configPath: string): string | null;
|
|
169
|
+
/**
|
|
170
|
+
* Applies the precedence to an already-loaded config. Exposed separately so
|
|
171
|
+
* the CLI wrapper can run its own field-level validation first and still share
|
|
172
|
+
* one ordering with every other reader.
|
|
173
|
+
*/
|
|
174
|
+
export declare function selectEnvironmentName(config: CoreProjectConfig, options: {
|
|
175
|
+
explicitEnvName?: string | null;
|
|
176
|
+
envVarName?: string | null;
|
|
177
|
+
localSelection?: string | null;
|
|
178
|
+
configPath?: string;
|
|
179
|
+
}): {
|
|
180
|
+
name: string;
|
|
181
|
+
source: PrimitiveEnvSource;
|
|
182
|
+
};
|
|
183
|
+
/**
|
|
184
|
+
* The whole algorithm end to end: discover the config, read the selection,
|
|
185
|
+
* apply the precedence, derive the WebSocket URL.
|
|
186
|
+
*/
|
|
187
|
+
export declare function resolvePrimitiveEnv(options?: ResolveOptions): ResolvedPrimitiveEnv;
|
|
@@ -0,0 +1,325 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* The shared Primitive environment resolver (#2873).
|
|
3
|
+
*
|
|
4
|
+
* Three surfaces have to agree on which backend/app a project is pointed at:
|
|
5
|
+
* the CLI, the Vue build (`primitive-app`'s `primitiveEnv()` plugin), and the
|
|
6
|
+
* Swift template's pre-build script. This module is the single algorithm they
|
|
7
|
+
* share. The CLI owns it; `packages/primitive-app` carries a byte-identical
|
|
8
|
+
* GENERATED copy (`cli/scripts/gen-primitive-env-resolver.mjs`, checked for
|
|
9
|
+
* freshness by `cli/tests/unit/env-resolver-copy-drift-guard.test.ts`); the
|
|
10
|
+
* Swift script is an independent bash+python3 port pinned by a parity test.
|
|
11
|
+
*
|
|
12
|
+
* ── COPYABILITY (load-bearing) ────────────────────────────────────────────
|
|
13
|
+
* This file MUST stay self-contained: node builtins only, ZERO relative
|
|
14
|
+
* imports. The generator copies it verbatim into a package that cannot depend
|
|
15
|
+
* on the CLI, so any `./x.js` import here would break that copy at runtime.
|
|
16
|
+
* The drift guard asserts this.
|
|
17
|
+
*
|
|
18
|
+
* Scope: config discovery, the schema `version` check, structural validation,
|
|
19
|
+
* the local selection, the precedence, and the http→ws scheme swap. It
|
|
20
|
+
* deliberately does NOT duplicate the CLI's full field-level validation
|
|
21
|
+
* (`validateProjectConfig` in `project-config.ts`) — the CLI wrapper runs that
|
|
22
|
+
* first, and the other readers only need "version understood, shape sane, fail
|
|
23
|
+
* loudly otherwise".
|
|
24
|
+
*
|
|
25
|
+
* Precedence (one order, everywhere):
|
|
26
|
+
* 1. an explicit name (`--env` / `--primitive-env`)
|
|
27
|
+
* 2. PRIMITIVE_ENV (per-invocation intent, keeps CI working)
|
|
28
|
+
* 3. .primitive/local.json (this machine's `primitive env use`)
|
|
29
|
+
* 4. defaultEnvironment (the committed team default)
|
|
30
|
+
* 5. the sole environment, if there is exactly one
|
|
31
|
+
*/
|
|
32
|
+
import { existsSync, readFileSync } from "node:fs";
|
|
33
|
+
import { basename, dirname, join, resolve } from "node:path";
|
|
34
|
+
/** Schema version of `.primitive/config.json` this core understands. */
|
|
35
|
+
export const PRIMITIVE_CONFIG_VERSION = 1;
|
|
36
|
+
/** Schema version of `.primitive/local.json` this core writes and reads. */
|
|
37
|
+
export const PRIMITIVE_LOCAL_STATE_VERSION = 1;
|
|
38
|
+
export const PROJECT_CONFIG_DIR = ".primitive";
|
|
39
|
+
export const PROJECT_CONFIG_FILENAME = "config.json";
|
|
40
|
+
export const LOCAL_STATE_FILENAME = "local.json";
|
|
41
|
+
export const PROJECT_CONFIG_DISPLAY_NAME = ".primitive/config.json";
|
|
42
|
+
export const LOCAL_STATE_DISPLAY_NAME = ".primitive/local.json";
|
|
43
|
+
export class PrimitiveEnvError extends Error {
|
|
44
|
+
kind;
|
|
45
|
+
path;
|
|
46
|
+
constructor(kind, message, path) {
|
|
47
|
+
super(message);
|
|
48
|
+
this.name = "PrimitiveEnvError";
|
|
49
|
+
this.kind = kind;
|
|
50
|
+
this.path = path;
|
|
51
|
+
}
|
|
52
|
+
}
|
|
53
|
+
/**
|
|
54
|
+
* The app's web counterpart as a normalized ORIGIN, or undefined when the
|
|
55
|
+
* value cannot be one (#2982).
|
|
56
|
+
*
|
|
57
|
+
* Unlike `appId`/`appName`, a typed read is not enough. This value is not
|
|
58
|
+
* merely carried: the Swift app points its emailed sign-in link at
|
|
59
|
+
* `<webUrl>/oauth/callback` and trusts incoming universal links from the same
|
|
60
|
+
* origin, and BOTH jobs need an origin —
|
|
61
|
+
*
|
|
62
|
+
* - https except loopback, the rule the server applies to every redirect URI
|
|
63
|
+
* (`src/auth/redirect-uri.ts`): an origin that cannot be allow-listed turns
|
|
64
|
+
* every sign-in request into a 400, and a plain-http link would carry the
|
|
65
|
+
* magic token in clear;
|
|
66
|
+
* - no path, query or fragment: the web client serves its callback on its own
|
|
67
|
+
* origin plus `/oauth/callback`, which is also the exact path the
|
|
68
|
+
* `apple-app-site-association` component claims;
|
|
69
|
+
* - no credentials, which have no business in a link that goes out by email.
|
|
70
|
+
*
|
|
71
|
+
* `primitive env add --web-url` and the project-config validation reject those
|
|
72
|
+
* shapes with a field-named error, but neither is on the path from a
|
|
73
|
+
* hand-edited `.primitive/config.json` to an Xcode build: the Swift template's
|
|
74
|
+
* pre-build script reads the file directly. So every reader that feeds
|
|
75
|
+
* `primitive.json` applies the contract, and a value that misses it is read as
|
|
76
|
+
* "this environment has no web counterpart" — code-only email, no trusted
|
|
77
|
+
* origin, nothing silently pointed at the wrong URL.
|
|
78
|
+
*
|
|
79
|
+
* The message-producing twin of this rule lives in `cli/src/lib/web-url.ts`;
|
|
80
|
+
* this file cannot import it (see COPYABILITY above), and a test pins that the
|
|
81
|
+
* two agree.
|
|
82
|
+
*/
|
|
83
|
+
export function normalizeWebOrigin(value) {
|
|
84
|
+
if (typeof value !== "string")
|
|
85
|
+
return undefined;
|
|
86
|
+
const trimmed = value.trim();
|
|
87
|
+
if (!trimmed)
|
|
88
|
+
return undefined;
|
|
89
|
+
let url;
|
|
90
|
+
try {
|
|
91
|
+
url = new URL(trimmed);
|
|
92
|
+
}
|
|
93
|
+
catch {
|
|
94
|
+
return undefined;
|
|
95
|
+
}
|
|
96
|
+
if (url.protocol !== "https:" && url.protocol !== "http:")
|
|
97
|
+
return undefined;
|
|
98
|
+
if (url.protocol === "http:" &&
|
|
99
|
+
url.hostname !== "localhost" &&
|
|
100
|
+
url.hostname !== "127.0.0.1") {
|
|
101
|
+
return undefined;
|
|
102
|
+
}
|
|
103
|
+
if (url.username || url.password)
|
|
104
|
+
return undefined;
|
|
105
|
+
if (url.pathname !== "/" && url.pathname !== "")
|
|
106
|
+
return undefined;
|
|
107
|
+
if (url.search || url.hash)
|
|
108
|
+
return undefined;
|
|
109
|
+
return url.origin;
|
|
110
|
+
}
|
|
111
|
+
/**
|
|
112
|
+
* Derives the WebSocket URL from the API URL. Every apiUrl/wsUrl pair in
|
|
113
|
+
* practice is the same host with the scheme swapped, so it is derived rather
|
|
114
|
+
* than authored — one less thing to get out of sync.
|
|
115
|
+
*/
|
|
116
|
+
export function deriveWsUrl(apiUrl) {
|
|
117
|
+
if (apiUrl.startsWith("https://"))
|
|
118
|
+
return "wss://" + apiUrl.slice("https://".length);
|
|
119
|
+
if (apiUrl.startsWith("http://"))
|
|
120
|
+
return "ws://" + apiUrl.slice("http://".length);
|
|
121
|
+
return apiUrl;
|
|
122
|
+
}
|
|
123
|
+
/**
|
|
124
|
+
* Finds `.primitive/config.json` by walking up from `cwd`, or returns the
|
|
125
|
+
* PRIMITIVE_PROJECT_CONFIG override when it is set (and exists).
|
|
126
|
+
*/
|
|
127
|
+
export function findPrimitiveConfigPath(options = {}) {
|
|
128
|
+
const env = options.env ?? process.env;
|
|
129
|
+
const override = env.PRIMITIVE_PROJECT_CONFIG;
|
|
130
|
+
if (override) {
|
|
131
|
+
const forced = resolve(override);
|
|
132
|
+
return existsSync(forced) ? forced : null;
|
|
133
|
+
}
|
|
134
|
+
let current = resolve(options.cwd ?? process.cwd());
|
|
135
|
+
while (true) {
|
|
136
|
+
const candidate = join(current, PROJECT_CONFIG_DIR, PROJECT_CONFIG_FILENAME);
|
|
137
|
+
if (existsSync(candidate))
|
|
138
|
+
return candidate;
|
|
139
|
+
const parent = dirname(current);
|
|
140
|
+
if (parent === current)
|
|
141
|
+
return null;
|
|
142
|
+
current = parent;
|
|
143
|
+
}
|
|
144
|
+
}
|
|
145
|
+
/**
|
|
146
|
+
* The project root for a config path: the parent of `.primitive/`, or the
|
|
147
|
+
* containing directory when the config was pointed at directly (a fixture via
|
|
148
|
+
* PRIMITIVE_PROJECT_CONFIG, which is not inside a `.primitive/` directory).
|
|
149
|
+
*/
|
|
150
|
+
export function projectRootForConfigPath(configPath) {
|
|
151
|
+
const dir = dirname(configPath);
|
|
152
|
+
return basename(dir) === PROJECT_CONFIG_DIR ? dirname(dir) : dir;
|
|
153
|
+
}
|
|
154
|
+
/**
|
|
155
|
+
* Local state lives beside the config it belongs to, so a fixture-pointed
|
|
156
|
+
* config never picks up a real project's selection and vice versa.
|
|
157
|
+
*/
|
|
158
|
+
export function localStatePathForConfigPath(configPath) {
|
|
159
|
+
return join(dirname(configPath), LOCAL_STATE_FILENAME);
|
|
160
|
+
}
|
|
161
|
+
/**
|
|
162
|
+
* Reads and structurally validates `.primitive/config.json`. Throws rather
|
|
163
|
+
* than guessing: a config that cannot be understood is always louder than a
|
|
164
|
+
* silent fallback to the wrong backend.
|
|
165
|
+
*/
|
|
166
|
+
export function readCoreProjectConfig(configPath) {
|
|
167
|
+
if (!existsSync(configPath)) {
|
|
168
|
+
throw new PrimitiveEnvError("missing-config", `No ${PROJECT_CONFIG_DISPLAY_NAME} found at ${configPath}. Run 'primitive init' to create one.`, configPath);
|
|
169
|
+
}
|
|
170
|
+
let raw;
|
|
171
|
+
try {
|
|
172
|
+
raw = readFileSync(configPath, "utf-8");
|
|
173
|
+
}
|
|
174
|
+
catch (err) {
|
|
175
|
+
throw new PrimitiveEnvError("malformed-config", `Failed to read ${PROJECT_CONFIG_DISPLAY_NAME} (${configPath}): ${err.message}`, configPath);
|
|
176
|
+
}
|
|
177
|
+
let parsed;
|
|
178
|
+
try {
|
|
179
|
+
parsed = JSON.parse(raw);
|
|
180
|
+
}
|
|
181
|
+
catch (err) {
|
|
182
|
+
throw new PrimitiveEnvError("malformed-config", `Failed to parse ${PROJECT_CONFIG_DISPLAY_NAME} (${configPath}): ${err.message}`, configPath);
|
|
183
|
+
}
|
|
184
|
+
if (!parsed || typeof parsed !== "object" || Array.isArray(parsed)) {
|
|
185
|
+
throw new PrimitiveEnvError("malformed-config", `${PROJECT_CONFIG_DISPLAY_NAME} (${configPath}) must contain a JSON object at the top level.`, configPath);
|
|
186
|
+
}
|
|
187
|
+
const obj = parsed;
|
|
188
|
+
if (typeof obj.version !== "number" || !Number.isInteger(obj.version)) {
|
|
189
|
+
throw new PrimitiveEnvError("malformed-config", `${PROJECT_CONFIG_DISPLAY_NAME} (${configPath}) is missing required integer field "version".`, configPath);
|
|
190
|
+
}
|
|
191
|
+
if (obj.version !== PRIMITIVE_CONFIG_VERSION) {
|
|
192
|
+
throw new PrimitiveEnvError("unsupported-version", `${PROJECT_CONFIG_DISPLAY_NAME} (${configPath}) has version ${obj.version}, but this tool understands version ${PRIMITIVE_CONFIG_VERSION}.`, configPath);
|
|
193
|
+
}
|
|
194
|
+
if (!obj.environments || typeof obj.environments !== "object" || Array.isArray(obj.environments)) {
|
|
195
|
+
throw new PrimitiveEnvError("malformed-config", `${PROJECT_CONFIG_DISPLAY_NAME} (${configPath}) is missing required "environments" object.`, configPath);
|
|
196
|
+
}
|
|
197
|
+
const environments = {};
|
|
198
|
+
for (const [name, entry] of Object.entries(obj.environments)) {
|
|
199
|
+
if (!entry || typeof entry !== "object" || Array.isArray(entry)) {
|
|
200
|
+
throw new PrimitiveEnvError("malformed-config", `Environment "${name}" must be an object in ${PROJECT_CONFIG_DISPLAY_NAME} (${configPath}).`, configPath);
|
|
201
|
+
}
|
|
202
|
+
const e = entry;
|
|
203
|
+
if (typeof e.apiUrl !== "string" || !e.apiUrl) {
|
|
204
|
+
throw new PrimitiveEnvError("malformed-config", `Environment "${name}" must have a non-empty "apiUrl" string in ${PROJECT_CONFIG_DISPLAY_NAME} (${configPath}).`, configPath);
|
|
205
|
+
}
|
|
206
|
+
environments[name] = {
|
|
207
|
+
apiUrl: e.apiUrl.replace(/\/$/, ""),
|
|
208
|
+
appId: typeof e.appId === "string" ? e.appId : undefined,
|
|
209
|
+
appName: typeof e.appName === "string" ? e.appName : undefined,
|
|
210
|
+
webUrl: normalizeWebOrigin(e.webUrl),
|
|
211
|
+
description: typeof e.description === "string" ? e.description : undefined,
|
|
212
|
+
};
|
|
213
|
+
}
|
|
214
|
+
return {
|
|
215
|
+
version: obj.version,
|
|
216
|
+
defaultEnvironment: typeof obj.defaultEnvironment === "string" && obj.defaultEnvironment
|
|
217
|
+
? obj.defaultEnvironment
|
|
218
|
+
: undefined,
|
|
219
|
+
environments,
|
|
220
|
+
};
|
|
221
|
+
}
|
|
222
|
+
/**
|
|
223
|
+
* Reads this machine's selection from `.primitive/local.json`. Returns null
|
|
224
|
+
* when there is no file or no selection in it; throws when the file exists but
|
|
225
|
+
* cannot be read as the shape `primitive env use` writes.
|
|
226
|
+
*/
|
|
227
|
+
export function readLocalSelection(configPath) {
|
|
228
|
+
const path = localStatePathForConfigPath(configPath);
|
|
229
|
+
if (!existsSync(path))
|
|
230
|
+
return null;
|
|
231
|
+
const corrupt = (detail) => {
|
|
232
|
+
throw new PrimitiveEnvError("corrupt-local-state", `${LOCAL_STATE_DISPLAY_NAME} (${path}) is unreadable: ${detail}. Delete the file or re-run 'primitive env use <name>'.`, path);
|
|
233
|
+
};
|
|
234
|
+
let parsed;
|
|
235
|
+
try {
|
|
236
|
+
parsed = JSON.parse(readFileSync(path, "utf-8"));
|
|
237
|
+
}
|
|
238
|
+
catch (err) {
|
|
239
|
+
return corrupt(err.message);
|
|
240
|
+
}
|
|
241
|
+
if (!parsed || typeof parsed !== "object" || Array.isArray(parsed)) {
|
|
242
|
+
return corrupt("expected a JSON object");
|
|
243
|
+
}
|
|
244
|
+
const obj = parsed;
|
|
245
|
+
const selected = obj.selectedEnvironment;
|
|
246
|
+
if (selected === undefined || selected === null || selected === "")
|
|
247
|
+
return null;
|
|
248
|
+
if (typeof selected !== "string") {
|
|
249
|
+
return corrupt(`"selectedEnvironment" must be a string`);
|
|
250
|
+
}
|
|
251
|
+
return selected;
|
|
252
|
+
}
|
|
253
|
+
/**
|
|
254
|
+
* Applies the precedence to an already-loaded config. Exposed separately so
|
|
255
|
+
* the CLI wrapper can run its own field-level validation first and still share
|
|
256
|
+
* one ordering with every other reader.
|
|
257
|
+
*/
|
|
258
|
+
export function selectEnvironmentName(config, options) {
|
|
259
|
+
const available = Object.keys(config.environments);
|
|
260
|
+
const list = available.join(", ") || "(none)";
|
|
261
|
+
const where = options.configPath
|
|
262
|
+
? `${PROJECT_CONFIG_DISPLAY_NAME} (${options.configPath})`
|
|
263
|
+
: PROJECT_CONFIG_DISPLAY_NAME;
|
|
264
|
+
const requireKnown = (name, source, origin) => {
|
|
265
|
+
if (!config.environments[name]) {
|
|
266
|
+
throw new PrimitiveEnvError("unknown-environment", `Environment "${name}" is not defined in ${where} (selected ${origin}). Available: ${list}`, options.configPath);
|
|
267
|
+
}
|
|
268
|
+
return { name, source };
|
|
269
|
+
};
|
|
270
|
+
if (options.explicitEnvName) {
|
|
271
|
+
return requireKnown(options.explicitEnvName, "explicit", "explicitly");
|
|
272
|
+
}
|
|
273
|
+
if (options.envVarName) {
|
|
274
|
+
return requireKnown(options.envVarName, "env-var", "via PRIMITIVE_ENV");
|
|
275
|
+
}
|
|
276
|
+
if (options.localSelection) {
|
|
277
|
+
return requireKnown(options.localSelection, "local", `in ${LOCAL_STATE_DISPLAY_NAME}`);
|
|
278
|
+
}
|
|
279
|
+
if (config.defaultEnvironment) {
|
|
280
|
+
return requireKnown(config.defaultEnvironment, "default", `as "defaultEnvironment"`);
|
|
281
|
+
}
|
|
282
|
+
if (available.length === 1) {
|
|
283
|
+
return { name: available[0], source: "sole" };
|
|
284
|
+
}
|
|
285
|
+
if (available.length === 0) {
|
|
286
|
+
throw new PrimitiveEnvError("no-selection", `${where} has no environments defined. Run 'primitive env add <name>' or 'primitive init'.`, options.configPath);
|
|
287
|
+
}
|
|
288
|
+
throw new PrimitiveEnvError("no-selection", `No environment selected. Run 'primitive env use <name>', set "defaultEnvironment" in ${where}, or export PRIMITIVE_ENV. Available: ${list}`, options.configPath);
|
|
289
|
+
}
|
|
290
|
+
/**
|
|
291
|
+
* The whole algorithm end to end: discover the config, read the selection,
|
|
292
|
+
* apply the precedence, derive the WebSocket URL.
|
|
293
|
+
*/
|
|
294
|
+
export function resolvePrimitiveEnv(options = {}) {
|
|
295
|
+
const env = options.env ?? process.env;
|
|
296
|
+
const configPath = options.configPath ?? findPrimitiveConfigPath({ cwd: options.cwd, env });
|
|
297
|
+
if (!configPath) {
|
|
298
|
+
throw new PrimitiveEnvError("missing-config", `No ${PROJECT_CONFIG_DISPLAY_NAME} found in ${options.cwd ?? process.cwd()} or any parent directory. Run 'primitive init' to create one, or 'primitive env add <name>' to add an environment.`);
|
|
299
|
+
}
|
|
300
|
+
const config = readCoreProjectConfig(configPath);
|
|
301
|
+
const { name, source } = selectEnvironmentName(config, {
|
|
302
|
+
explicitEnvName: options.explicitEnvName || null,
|
|
303
|
+
envVarName: env.PRIMITIVE_ENV || null,
|
|
304
|
+
localSelection: readLocalSelection(configPath),
|
|
305
|
+
configPath,
|
|
306
|
+
});
|
|
307
|
+
const entry = config.environments[name];
|
|
308
|
+
if (options.requireAppId && !entry.appId) {
|
|
309
|
+
throw new PrimitiveEnvError("missing-app-id", `Environment "${name}" in ${PROJECT_CONFIG_DISPLAY_NAME} (${configPath}) has no "appId", which this build needs. Add one with 'primitive env add ${name} --api-url ${entry.apiUrl} --app-id <id>' or edit the config.`, configPath);
|
|
310
|
+
}
|
|
311
|
+
return {
|
|
312
|
+
name,
|
|
313
|
+
apiUrl: entry.apiUrl,
|
|
314
|
+
wsUrl: deriveWsUrl(entry.apiUrl),
|
|
315
|
+
appId: entry.appId,
|
|
316
|
+
appName: entry.appName,
|
|
317
|
+
webUrl: entry.webUrl,
|
|
318
|
+
description: entry.description,
|
|
319
|
+
source,
|
|
320
|
+
configPath,
|
|
321
|
+
localStatePath: localStatePathForConfigPath(configPath),
|
|
322
|
+
projectRoot: projectRootForConfigPath(configPath),
|
|
323
|
+
};
|
|
324
|
+
}
|
|
325
|
+
//# sourceMappingURL=env-resolver-core.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"env-resolver-core.js","sourceRoot":"","sources":["../../../src/lib/env-resolver-core.ts"],"names":[],"mappings":"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"}
|
|
@@ -1,19 +1,29 @@
|
|
|
1
1
|
/**
|
|
2
|
-
* Environment resolution.
|
|
2
|
+
* Environment resolution (CLI side).
|
|
3
3
|
*
|
|
4
|
-
*
|
|
5
|
-
*
|
|
4
|
+
* The algorithm itself lives in `env-resolver-core.ts` — the one copy the Vite
|
|
5
|
+
* plugin and the Swift pre-build script also run (#2873). This module is the
|
|
6
|
+
* CLI's thin wrapper around it: process-lifetime caching, the `--env` override
|
|
7
|
+
* commander sets, and — load-bearing — the CLI's own FULL field-level
|
|
8
|
+
* validation via `validateProjectConfig()`. The core carries only the version
|
|
9
|
+
* and structural checks the other readers need; running the CLI's validation
|
|
10
|
+
* first is what keeps `getProjectConfig()` and `getCurrentEnvironment()` from
|
|
11
|
+
* ever disagreeing about the same file.
|
|
12
|
+
*
|
|
13
|
+
* The resolution order is:
|
|
6
14
|
*
|
|
7
15
|
* 1. Explicit --env <name> flag (set via setCurrentEnvName from bin/primitive.ts)
|
|
8
16
|
* 2. PRIMITIVE_ENV environment variable
|
|
9
|
-
* 3. The
|
|
10
|
-
* 4.
|
|
11
|
-
* 5.
|
|
17
|
+
* 3. The per-machine selection in .primitive/local.json (`primitive env use`)
|
|
18
|
+
* 4. The project config's committed defaultEnvironment
|
|
19
|
+
* 5. If the project has exactly one environment, that one
|
|
20
|
+
* 6. null (legacy mode — fall back to ~/.primitive/credentials.json)
|
|
12
21
|
*
|
|
13
22
|
* Commands read the resolved environment once via getCurrentEnvironment().
|
|
14
23
|
* The resolution is cached for the lifetime of the process.
|
|
15
24
|
*/
|
|
16
25
|
import { type ProjectConfig, type ProjectEnvironment } from "./project-config.js";
|
|
26
|
+
import { PrimitiveEnvError, type PrimitiveEnvSource } from "./env-resolver-core.js";
|
|
17
27
|
export interface ResolvedEnvironment {
|
|
18
28
|
/** The environment name (e.g. "dev", "prod"). */
|
|
19
29
|
name: string;
|
|
@@ -23,6 +33,8 @@ export interface ResolvedEnvironment {
|
|
|
23
33
|
projectConfigPath: string;
|
|
24
34
|
/** Absolute path to the project root (the parent of .primitive/). */
|
|
25
35
|
projectRoot: string;
|
|
36
|
+
/** Which precedence step chose this environment. */
|
|
37
|
+
source: PrimitiveEnvSource;
|
|
26
38
|
}
|
|
27
39
|
/**
|
|
28
40
|
* Called by bin/primitive.ts when the user passes --env <name> on the command
|
|
@@ -40,6 +52,15 @@ export declare function resetEnvResolver(): void;
|
|
|
40
52
|
* .primitive/config.json is present. Throws ProjectConfigError on a broken config.
|
|
41
53
|
*/
|
|
42
54
|
export declare function getProjectConfig(): ProjectConfig | null;
|
|
55
|
+
/**
|
|
56
|
+
* Reads this machine's environment selection (`primitive env use`), or null
|
|
57
|
+
* when nothing is selected. Throws PrimitiveEnvError on corrupt local state —
|
|
58
|
+
* `env list` / `env show` surface that distinctly instead of quietly falling
|
|
59
|
+
* back to the committed default.
|
|
60
|
+
*/
|
|
61
|
+
export declare function getLocalSelection(): string | null;
|
|
62
|
+
/** Absolute path of the local-state file for the current project, if any. */
|
|
63
|
+
export declare function getLocalStatePath(): string | null;
|
|
43
64
|
/**
|
|
44
65
|
* Resolves the current environment, or returns null if we're running in
|
|
45
66
|
* legacy mode (no .primitive/config.json present).
|
|
@@ -60,3 +81,4 @@ export declare function getCurrentEnvNameSafe(): string | null;
|
|
|
60
81
|
* need to know whether the user passed --env vs. relying on defaults.
|
|
61
82
|
*/
|
|
62
83
|
export declare function getExplicitEnvName(): string | null;
|
|
84
|
+
export { PrimitiveEnvError };
|