@intentius/chant-lexicon-terraform 0.124.52 → 0.124.54
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 +7 -6
- package/dist/__fixtures__/pr-loop/estate.component.d.ts +7 -0
- package/dist/__fixtures__/pr-loop/estate.component.d.ts.map +1 -0
- package/dist/__fixtures__/pr-loop/estate.component.js +7 -0
- package/dist/__fixtures__/report/generate.d.ts +26 -0
- package/dist/__fixtures__/report/generate.d.ts.map +1 -0
- package/dist/__fixtures__/report/generate.js +58 -0
- package/dist/applied-state.d.ts +27 -0
- package/dist/applied-state.d.ts.map +1 -0
- package/dist/applied-state.js +44 -0
- package/dist/backend-config.d.ts +53 -0
- package/dist/backend-config.d.ts.map +1 -0
- package/dist/backend-config.js +136 -0
- package/dist/behaviour/kinds.d.ts.map +1 -1
- package/dist/behaviour/kinds.js +4 -0
- package/dist/behaviour/predict.d.ts.map +1 -1
- package/dist/behaviour/predict.js +6 -2
- package/dist/behaviour/reference-catalog.d.ts +16 -5
- package/dist/behaviour/reference-catalog.d.ts.map +1 -1
- package/dist/behaviour/reference-catalog.js +16 -5
- package/dist/behaviour/request.d.ts.map +1 -1
- package/dist/behaviour/request.js +3 -2
- package/dist/changed-roots.d.ts +6 -4
- package/dist/changed-roots.d.ts.map +1 -1
- package/dist/changed-roots.js +14 -18
- package/dist/commands.d.ts.map +1 -1
- package/dist/commands.js +4 -3
- package/dist/components/capability-plugin.d.ts +65 -3
- package/dist/components/capability-plugin.d.ts.map +1 -1
- package/dist/components/capability-plugin.js +197 -13
- package/dist/components/compose-group.d.ts +145 -0
- package/dist/components/compose-group.d.ts.map +1 -0
- package/dist/components/compose-group.js +407 -0
- package/dist/components/placeholder-preview.d.ts +78 -0
- package/dist/components/placeholder-preview.d.ts.map +1 -0
- package/dist/components/placeholder-preview.js +254 -0
- package/dist/compose/apply-events.d.ts +46 -0
- package/dist/compose/apply-events.d.ts.map +1 -0
- package/dist/compose/apply-events.js +77 -0
- package/dist/compose/estate.d.ts +194 -0
- package/dist/compose/estate.d.ts.map +1 -0
- package/dist/compose/estate.js +363 -0
- package/dist/compose/hcl.d.ts +99 -0
- package/dist/compose/hcl.d.ts.map +1 -0
- package/dist/compose/hcl.js +302 -0
- package/dist/compose/module-address.d.ts +24 -0
- package/dist/compose/module-address.d.ts.map +1 -0
- package/dist/compose/module-address.js +43 -0
- package/dist/compose/root.d.ts +127 -0
- package/dist/compose/root.d.ts.map +1 -0
- package/dist/compose/root.js +586 -0
- package/dist/compose/run.d.ts +183 -0
- package/dist/compose/run.d.ts.map +1 -0
- package/dist/compose/run.js +447 -0
- package/dist/compose/slice.d.ts +102 -0
- package/dist/compose/slice.d.ts.map +1 -0
- package/dist/compose/slice.js +249 -0
- package/dist/compose/state-address.d.ts +28 -0
- package/dist/compose/state-address.d.ts.map +1 -0
- package/dist/compose/state-address.js +154 -0
- package/dist/compose/state-merge.d.ts +52 -0
- package/dist/compose/state-merge.d.ts.map +1 -0
- package/dist/compose/state-merge.js +135 -0
- package/dist/compose.d.ts +179 -0
- package/dist/compose.d.ts.map +1 -0
- package/dist/compose.js +482 -0
- package/dist/composites/terraform-apply-op.d.ts.map +1 -1
- package/dist/composites/terraform-apply-op.js +7 -3
- package/dist/config.d.ts +59 -13
- package/dist/config.d.ts.map +1 -1
- package/dist/config.js +43 -9
- package/dist/describe-resources.d.ts +74 -12
- package/dist/describe-resources.d.ts.map +1 -1
- package/dist/describe-resources.js +374 -66
- package/dist/drift-read.d.ts +33 -0
- package/dist/drift-read.d.ts.map +1 -0
- package/dist/drift-read.js +243 -0
- package/dist/drift-record.d.ts +147 -0
- package/dist/drift-record.d.ts.map +1 -0
- package/dist/drift-record.js +383 -0
- package/dist/hcl/edges.d.ts.map +1 -1
- package/dist/hcl/edges.js +24 -1
- package/dist/hcl/files.d.ts +61 -0
- package/dist/hcl/files.d.ts.map +1 -0
- package/dist/hcl/files.js +221 -0
- package/dist/hcl/instances.d.ts +82 -0
- package/dist/hcl/instances.d.ts.map +1 -0
- package/dist/hcl/instances.js +390 -0
- package/dist/hcl/parse.d.ts +81 -9
- package/dist/hcl/parse.d.ts.map +1 -1
- package/dist/hcl/parse.js +114 -16
- package/dist/hcl/roots.d.ts.map +1 -1
- package/dist/hcl/roots.js +5 -0
- package/dist/hcl/suppressions.d.ts.map +1 -1
- package/dist/hcl/suppressions.js +8 -2
- package/dist/index.d.ts +11 -2
- package/dist/index.d.ts.map +1 -1
- package/dist/index.js +21 -2
- package/dist/integrity.json +3 -3
- package/dist/live-plan-reasons.d.ts +21 -0
- package/dist/live-plan-reasons.d.ts.map +1 -0
- package/dist/live-plan-reasons.js +47 -0
- package/dist/lsp/option-keys.d.ts.map +1 -1
- package/dist/lsp/option-keys.js +2 -0
- package/dist/manifest.json +1 -1
- package/dist/op/activities/index.d.ts +6 -2
- package/dist/op/activities/index.d.ts.map +1 -1
- package/dist/op/activities/index.js +5 -1
- package/dist/op/activities/live-detect.d.ts +4 -3
- package/dist/op/activities/live-detect.d.ts.map +1 -1
- package/dist/op/activities/live-detect.js +57 -32
- package/dist/op/activities/pin-rollout.d.ts +2 -0
- package/dist/op/activities/pin-rollout.d.ts.map +1 -1
- package/dist/op/activities/pin-rollout.js +1 -0
- package/dist/op/activities/terraform.d.ts +153 -5
- package/dist/op/activities/terraform.d.ts.map +1 -1
- package/dist/op/activities/terraform.js +205 -20
- package/dist/op/activity-contracts.d.ts +27 -0
- package/dist/op/activity-contracts.d.ts.map +1 -1
- package/dist/op/activity-contracts.js +19 -1
- package/dist/op/builders.d.ts +7 -1
- package/dist/op/builders.d.ts.map +1 -1
- package/dist/op/builders.js +9 -0
- package/dist/pin/edit.d.ts.map +1 -1
- package/dist/pin/edit.js +35 -0
- package/dist/pin/rollout.d.ts +2 -0
- package/dist/pin/rollout.d.ts.map +1 -1
- package/dist/pin/rollout.js +14 -11
- package/dist/plan-shape.d.ts +30 -0
- package/dist/plan-shape.d.ts.map +1 -0
- package/dist/plan-shape.js +125 -0
- package/dist/plugin.d.ts.map +1 -1
- package/dist/plugin.js +32 -18
- package/dist/report.d.ts +15 -6
- package/dist/report.d.ts.map +1 -1
- package/dist/report.js +28 -55
- package/dist/skills/chant-terraform.md +1 -1
- package/dist/state/azure-blob.d.ts +68 -0
- package/dist/state/azure-blob.d.ts.map +1 -0
- package/dist/state/azure-blob.js +201 -0
- package/dist/state/backend.d.ts +158 -0
- package/dist/state/backend.d.ts.map +1 -0
- package/dist/state/backend.js +406 -0
- package/dist/state/exec.d.ts +39 -0
- package/dist/state/exec.d.ts.map +1 -0
- package/dist/state/exec.js +80 -0
- package/dist/state/gcs.d.ts +62 -0
- package/dist/state/gcs.d.ts.map +1 -0
- package/dist/state/gcs.js +224 -0
- package/dist/state/index.d.ts +15 -0
- package/dist/state/index.d.ts.map +1 -0
- package/dist/state/index.js +14 -0
- package/dist/state/locks.d.ts +105 -0
- package/dist/state/locks.d.ts.map +1 -0
- package/dist/state/locks.js +130 -0
- package/dist/state/object-store.d.ts +37 -0
- package/dist/state/object-store.d.ts.map +1 -0
- package/dist/state/object-store.js +20 -0
- package/dist/state/root-states.d.ts +131 -0
- package/dist/state/root-states.d.ts.map +1 -0
- package/dist/state/root-states.js +241 -0
- package/dist/state/s3.d.ts +68 -0
- package/dist/state/s3.d.ts.map +1 -0
- package/dist/state/s3.js +170 -0
- package/dist/state/store.d.ts +51 -0
- package/dist/state/store.d.ts.map +1 -0
- package/dist/state/store.js +185 -0
- package/dist/terragrunt/affected.d.ts.map +1 -1
- package/dist/terragrunt/affected.js +2 -1
- package/package.json +7 -3
- package/src/__fixtures__/ACCEPTANCE.md +69 -7
- package/src/__fixtures__/compose/apply-failed-in-app.jsonl +12 -0
- package/src/__fixtures__/compose/state-app.json +66 -0
- package/src/__fixtures__/compose/state-edge.json +40 -0
- package/src/__fixtures__/compose/state-net.json +58 -0
- package/src/__fixtures__/compose/three-app.plan.json +184 -0
- package/src/__fixtures__/compose/three-composed.plan.json +509 -0
- package/src/__fixtures__/compose/three-edge.plan.json +144 -0
- package/src/__fixtures__/compose/three-net.plan.json +174 -0
- package/src/__fixtures__/compose/unknown-composed.plan.json +228 -0
- package/src/__fixtures__/compose/working-after-apply.json +145 -0
- package/src/__fixtures__/config-blocks/app/main.tf +61 -0
- package/src/__fixtures__/config-blocks/app/modules/network/main.tf +4 -0
- package/src/__fixtures__/config-blocks/app-json/main.tf.json +39 -0
- package/src/__fixtures__/config-files/shadow/main.tf +3 -0
- package/src/__fixtures__/config-files/shadow/main.tofu +3 -0
- package/src/__fixtures__/config-files/shadow/other.tf +3 -0
- package/src/__fixtures__/config-files/tf/main.tf +11 -0
- package/src/__fixtures__/config-files/tf-json/main.tf.json +18 -0
- package/src/__fixtures__/config-files/tofu/main.tofu +11 -0
- package/src/__fixtures__/config-files/tofu-json/main.tofu.json +18 -0
- package/src/__fixtures__/config-files/tofu-only/main.tofu +3 -0
- package/src/__fixtures__/drift-record/README.md +11 -0
- package/src/__fixtures__/drift-record/live-plan-sections.json +27 -0
- package/src/__fixtures__/instance-forms/app/main.tf +110 -0
- package/src/__fixtures__/instance-forms/app/modules/svc/main.tf +3 -0
- package/src/__fixtures__/instance-vars/app/main.tf +52 -0
- package/src/__fixtures__/instance-vars/app/modules/app/main.tf +12 -0
- package/src/__fixtures__/instance-vars/app/modules/edge/main.tf +3 -0
- package/src/__fixtures__/instance-vars/app/terraform.tfvars +1 -0
- package/src/__fixtures__/live-module-keyed/live-graph.json +259 -0
- package/src/__fixtures__/live-module-keyed/live-plan.json +87 -0
- package/src/__fixtures__/live-module-keyed/root/estate.chdf.hcl +1 -0
- package/src/__fixtures__/live-module-keyed/root/main.tf +21 -0
- package/src/__fixtures__/live-module-keyed/root/modules/app/main.tf +17 -0
- package/src/__fixtures__/live-module-keyed/root/modules/edge/main.tf +7 -0
- package/src/__fixtures__/live-module-keyed/root/versions.tf +30 -0
- package/src/__fixtures__/live-module-keyed/show-state.json +146 -0
- package/src/__fixtures__/pr-loop/README.md +50 -0
- package/src/__fixtures__/pr-loop/chant.config.json +13 -0
- package/src/__fixtures__/pr-loop/estate.component.ts +10 -0
- package/src/__fixtures__/pr-loop/roots/a/main.tf +11 -0
- package/src/__fixtures__/pr-loop/roots/app/main.tf +19 -0
- package/src/__fixtures__/pr-loop/roots/b/main.tf +7 -0
- package/src/__fixtures__/pr-loop/roots/dns/main.tf +3 -0
- package/src/__fixtures__/pr-loop/roots/net/main.tf +7 -0
- package/src/__fixtures__/report/applied.show.json +51 -0
- package/src/__fixtures__/report/generate.ts +63 -0
- package/src/__fixtures__/report/plan.show.json +200 -0
- package/src/__fixtures__/report/tf-apply/change-set.json +170 -0
- package/src/__fixtures__/report/tf-apply/report.json +338 -0
- package/src/__fixtures__/report/tf-plan/change-set.json +170 -0
- package/src/__fixtures__/report/tf-plan/report.json +320 -0
- package/src/__fixtures__/three-cloud-azure.graph.json +290 -0
- package/src/applied-state.ts +52 -0
- package/src/backend-config.test.ts +105 -0
- package/src/backend-config.ts +133 -0
- package/src/behaviour/kinds.ts +4 -0
- package/src/behaviour/predict.ts +5 -2
- package/src/behaviour/reference-catalog.plugin.test.ts +65 -0
- package/src/behaviour/reference-catalog.ts +16 -5
- package/src/behaviour/request.ts +3 -2
- package/src/change-set-instances.test.ts +98 -0
- package/src/changed-roots.ts +14 -16
- package/src/commands.ts +4 -3
- package/src/components/capability-plugin.test.ts +172 -5
- package/src/components/capability-plugin.ts +212 -11
- package/src/components/change-set-graph.e2e.test.ts +11 -5
- package/src/components/compose-group.test.ts +486 -0
- package/src/components/compose-group.ts +489 -0
- package/src/components/demo-composed-roots.e2e.test.ts +440 -0
- package/src/components/member-outputs.test.ts +76 -0
- package/src/components/placeholder-preview.test.ts +147 -0
- package/src/components/placeholder-preview.ts +257 -0
- package/src/components/pr-loop-compose.tofu.e2e.test.ts +363 -0
- package/src/components/pr-loop.tofu.test.ts +112 -56
- package/src/compose/apply-events.test.ts +62 -0
- package/src/compose/apply-events.ts +100 -0
- package/src/compose/estate.choudoufu.e2e.test.ts +112 -0
- package/src/compose/estate.test.ts +421 -0
- package/src/compose/estate.ts +443 -0
- package/src/compose/hcl.ts +311 -0
- package/src/compose/module-address.ts +49 -0
- package/src/compose/root.test.ts +416 -0
- package/src/compose/root.ts +592 -0
- package/src/compose/run.test.ts +440 -0
- package/src/compose/run.tofu.test.ts +176 -0
- package/src/compose/run.ts +527 -0
- package/src/compose/slice.test.ts +184 -0
- package/src/compose/slice.ts +290 -0
- package/src/compose/state-address.ts +157 -0
- package/src/compose/state-merge.test.ts +131 -0
- package/src/compose/state-merge.ts +148 -0
- package/src/compose.test.ts +248 -0
- package/src/compose.ts +627 -0
- package/src/composites/terraform-apply-op.test.ts +9 -0
- package/src/composites/terraform-apply-op.ts +7 -3
- package/src/config-file-listers.test.ts +265 -0
- package/src/config.ts +44 -9
- package/src/describe-resources.engine-facts.test.ts +412 -0
- package/src/describe-resources.live-module-keyed.test.ts +290 -0
- package/src/describe-resources.ts +416 -70
- package/src/drift-read.ts +284 -0
- package/src/drift-record.test.ts +223 -0
- package/src/drift-record.ts +455 -0
- package/src/hcl/config-blocks.test.ts +174 -0
- package/src/hcl/edges.ts +21 -1
- package/src/hcl/files.ts +234 -0
- package/src/hcl/instance-forms.test.ts +94 -0
- package/src/hcl/instances.test.ts +137 -0
- package/src/hcl/instances.ts +422 -0
- package/src/hcl/parse.test.ts +139 -1
- package/src/hcl/parse.ts +149 -16
- package/src/hcl/roots.ts +6 -0
- package/src/hcl/suppressions.ts +8 -2
- package/src/index.ts +76 -0
- package/src/live-plan-reasons.ts +54 -0
- package/src/lsp/completions.test.ts +1 -1
- package/src/lsp/option-keys.ts +2 -0
- package/src/op/activities/choudoufu-plan-set-op.test.ts +111 -0
- package/src/op/activities/index.ts +9 -0
- package/src/op/activities/live-detect.ts +55 -26
- package/src/op/activities/pin-rollout.ts +3 -0
- package/src/op/activities/registry.test.ts +2 -1
- package/src/op/activities/terraform.test.ts +55 -0
- package/src/op/activities/terraform.ts +266 -22
- package/src/op/activity-contracts.test.ts +1 -0
- package/src/op/activity-contracts.ts +24 -1
- package/src/op/builders.ts +14 -0
- package/src/pin/bundle.test.ts +2 -0
- package/src/pin/edit.ts +30 -0
- package/src/pin/rollout.ts +16 -11
- package/src/plan-shape.test.ts +148 -0
- package/src/plan-shape.ts +128 -0
- package/src/plugin.ts +33 -19
- package/src/report.test.ts +82 -1
- package/src/report.ts +31 -54
- package/src/signal-only-root.test.ts +72 -0
- package/src/skills/chant-terraform.md +1 -1
- package/src/state/azure-blob.ts +223 -0
- package/src/state/backend-verdict.test.ts +187 -0
- package/src/state/backend.test.ts +127 -0
- package/src/state/backend.ts +488 -0
- package/src/state/exec.ts +111 -0
- package/src/state/gcs.ts +254 -0
- package/src/state/index.ts +15 -0
- package/src/state/locks.test.ts +84 -0
- package/src/state/locks.ts +201 -0
- package/src/state/object-store.ts +35 -0
- package/src/state/root-states-floci.e2e.test.ts +66 -0
- package/src/state/root-states.test.ts +462 -0
- package/src/state/root-states.ts +309 -0
- package/src/state/s3.ts +193 -0
- package/src/state/store.ts +225 -0
- package/src/terragrunt/affected.ts +2 -1
- package/src/workspace-kinds.test.ts +4 -17
- package/workspace-kinds.json +1 -24
- package/dist/workspace-member.d.ts +0 -30
- package/dist/workspace-member.d.ts.map +0 -1
- package/dist/workspace-member.js +0 -91
- package/schemas/pulumi.schema.json +0 -34
- package/src/testdata/pulumi-member/Pulumi.yaml +0 -2
- package/src/testdata/pulumi-member/stack-export.json +0 -53
- package/src/testdata/pulumi-unexported/Pulumi.yaml +0 -2
- package/src/workspace-member.test.ts +0 -89
- package/src/workspace-member.ts +0 -126
|
@@ -0,0 +1,363 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* The composed run of choudoufu estates (chant#4445, epic #4419): when every
|
|
3
|
+
* member runs choudoufu against a `live` estate (`Composition.estate`), one
|
|
4
|
+
* `choudoufu plan` and one `choudoufu apply` from a composed root of `module`
|
|
5
|
+
* calls (choudoufu#2059).
|
|
6
|
+
*
|
|
7
|
+
* An estate has no state file, so nothing is pulled, locked, split or
|
|
8
|
+
* written back: each resource's record goes to its own estate as it applies,
|
|
9
|
+
* and a `terraform_estate_outputs` read of another estate in the run is
|
|
10
|
+
* answered inside the run. The composed root is `writeEstateRoot`'s
|
|
11
|
+
* (./root.ts, #4441). The run takes the job's environment and assumes no
|
|
12
|
+
* role of its own: each estate's provider blocks name its role.
|
|
13
|
+
*
|
|
14
|
+
* choudoufu refuses a bare `show` under a `live` block, so the values the
|
|
15
|
+
* plan left unknown are read after the apply from a second plan of the
|
|
16
|
+
* composed root: its `prior_state`, sliced per module (./slice.ts, #4442) and
|
|
17
|
+
* read through `../applied-state`, the reader `chant terraform report` uses.
|
|
18
|
+
* The same plan says how far a failed apply got: a member whose part plans
|
|
19
|
+
* no change any more applied.
|
|
20
|
+
*
|
|
21
|
+
* Lifted from terragucci's `packages/terragucci/src/compose.ts` at c493e0e
|
|
22
|
+
* (`ComposedRun` with `estate` set: `plan`, `apply`, `finishEstate`,
|
|
23
|
+
* `showEstateMembers`, `composedEnv`). The state-backed run is #4444; this one
|
|
24
|
+
* has the same `plan()`, `apply()` and `release()` and returns the same
|
|
25
|
+
* shapes, and #4447 picks one by `Composition.estate`.
|
|
26
|
+
*/
|
|
27
|
+
import { existsSync, mkdtempSync, readdirSync, rmdirSync, rmSync } from "node:fs";
|
|
28
|
+
import { tmpdir } from "node:os";
|
|
29
|
+
import { join, resolve } from "node:path";
|
|
30
|
+
import { stateOutputs, stateResources } from "../applied-state.js";
|
|
31
|
+
import { terraformPlanDigest } from "../plan-digest.js";
|
|
32
|
+
import { terraformPlannedOutputs } from "../components/capability-plugin.js";
|
|
33
|
+
import { computePlanDigest } from "@intentius/chant/lifecycle/plan-digest";
|
|
34
|
+
import { isOlderVersion, MIN_CHOUDOUFU_ESTATES_VERSION, parseChoudoufuVersion } from "../op/activities/terraform.js";
|
|
35
|
+
import { runBinary } from "../state/exec.js";
|
|
36
|
+
import { memberApply } from "./apply-events.js";
|
|
37
|
+
import { liveEstate } from "./hcl.js";
|
|
38
|
+
import { stripModule, topModule } from "./module-address.js";
|
|
39
|
+
import { COMPOSE_DIR, withoutVarFiles, writeEstateRoot } from "./root.js";
|
|
40
|
+
import { composedMemberPlans, planCounts, slicePlan, sliceText } from "./slice.js";
|
|
41
|
+
const firstLines = (s, n = 20) => s.trim().split("\n").slice(-n).join("\n");
|
|
42
|
+
/**
|
|
43
|
+
* Why a choudoufu's `version` output cannot run a composed run of estates, or
|
|
44
|
+
* undefined when it can. A release older than
|
|
45
|
+
* {@link MIN_CHOUDOUFU_ESTATES_VERSION} falls back; a dev build names no
|
|
46
|
+
* release and passes.
|
|
47
|
+
*/
|
|
48
|
+
export function estateVersionFallback(versionOutput) {
|
|
49
|
+
const version = parseChoudoufuVersion(versionOutput);
|
|
50
|
+
if (version === undefined || !isOlderVersion(version, MIN_CHOUDOUFU_ESTATES_VERSION))
|
|
51
|
+
return undefined;
|
|
52
|
+
return {
|
|
53
|
+
kind: "binary",
|
|
54
|
+
reason: `choudoufu ${version} is older than v${MIN_CHOUDOUFU_ESTATES_VERSION}, the first release that plans and applies several estates as one (choudoufu#2059)`,
|
|
55
|
+
};
|
|
56
|
+
}
|
|
57
|
+
/**
|
|
58
|
+
* What choudoufu's human `apply` output says of each module: the changes
|
|
59
|
+
* that completed (`<addr>: Creation complete`, `Modifications complete`,
|
|
60
|
+
* `Destruction complete`), started (`Creating...` and the rest) or errored
|
|
61
|
+
* (an `Error:` box naming `with <addr>,`). An estate's apply runs under live
|
|
62
|
+
* resource markers and prints no `-json` lines, so this reads the text.
|
|
63
|
+
*/
|
|
64
|
+
export function readEstateApplyText(out, modules) {
|
|
65
|
+
const ev = { done: new Map(), started: new Map(), errored: new Map(), other: [] };
|
|
66
|
+
const known = new Set(modules);
|
|
67
|
+
const moduleOf = (addr) => {
|
|
68
|
+
const m = topModule(addr);
|
|
69
|
+
return m !== undefined && known.has(m) && addr !== `module.${m}` ? m : undefined;
|
|
70
|
+
};
|
|
71
|
+
const bump = (map, m) => {
|
|
72
|
+
map.set(m, (map.get(m) ?? 0) + 1);
|
|
73
|
+
};
|
|
74
|
+
const lines = out.split("\n").map((l) => l.replace(/^[│╷╵\s]+/, "").trimEnd());
|
|
75
|
+
for (let i = 0; i < lines.length; i++) {
|
|
76
|
+
const l = lines[i];
|
|
77
|
+
const hit = l.match(/^(module\.\S+): (Creation|Modifications|Destruction) complete\b/);
|
|
78
|
+
if (hit) {
|
|
79
|
+
const m = moduleOf(hit[1]);
|
|
80
|
+
if (m)
|
|
81
|
+
bump(ev.done, m);
|
|
82
|
+
continue;
|
|
83
|
+
}
|
|
84
|
+
const start = l.match(/^(module\.\S+): (Creating|Modifying|Destroying)\.\.\./);
|
|
85
|
+
if (start) {
|
|
86
|
+
const m = moduleOf(start[1]);
|
|
87
|
+
if (m)
|
|
88
|
+
bump(ev.started, m);
|
|
89
|
+
continue;
|
|
90
|
+
}
|
|
91
|
+
if (l.startsWith("Error: ")) {
|
|
92
|
+
let addr;
|
|
93
|
+
for (let j = i + 1; j < Math.min(lines.length, i + 8) && !lines[j].startsWith("Error: "); j++) {
|
|
94
|
+
const w = lines[j].match(/^with (module\.[^,\s]+),?$/);
|
|
95
|
+
if (w) {
|
|
96
|
+
addr = w[1];
|
|
97
|
+
break;
|
|
98
|
+
}
|
|
99
|
+
}
|
|
100
|
+
const m = addr ? moduleOf(addr) : undefined;
|
|
101
|
+
if (m && !ev.errored.has(m))
|
|
102
|
+
ev.errored.set(m, `${stripModule(addr)}: ${l}`);
|
|
103
|
+
else if (!m)
|
|
104
|
+
ev.other.push(l);
|
|
105
|
+
}
|
|
106
|
+
}
|
|
107
|
+
return ev;
|
|
108
|
+
}
|
|
109
|
+
/**
|
|
110
|
+
* Each member's outcome from its planned changes, what the apply printed, its
|
|
111
|
+
* exit code and, when the post-apply plan was made, the changes each member's
|
|
112
|
+
* part still plans. A clean exit means every planned change applied. After a
|
|
113
|
+
* failure, a member's changes left in the post-apply plan say how many of its
|
|
114
|
+
* planned changes applied; without that plan the printed completions do.
|
|
115
|
+
*/
|
|
116
|
+
export function estateOutcomes(c, planned, out, code, remaining) {
|
|
117
|
+
const ev = readEstateApplyText(out, c.order.map((member) => c.modules.get(member)));
|
|
118
|
+
for (const member of c.order) {
|
|
119
|
+
const m = c.modules.get(member);
|
|
120
|
+
const n = planned.get(member) ?? 0;
|
|
121
|
+
if (code === 0)
|
|
122
|
+
ev.done.set(m, n);
|
|
123
|
+
else if (remaining?.has(member))
|
|
124
|
+
ev.done.set(m, Math.max(0, n - remaining.get(member)));
|
|
125
|
+
}
|
|
126
|
+
const members = {};
|
|
127
|
+
for (const member of c.order) {
|
|
128
|
+
const m = c.modules.get(member);
|
|
129
|
+
const n = planned.get(member) ?? 0;
|
|
130
|
+
const { apply, done } = memberApply(m, n, ev);
|
|
131
|
+
const error = ev.errored.get(m);
|
|
132
|
+
members[member] = { status: apply, done, planned: n, ...(error && apply !== "applied" && apply !== "no-changes" ? { error } : {}) };
|
|
133
|
+
}
|
|
134
|
+
return { members, other: ev.other };
|
|
135
|
+
}
|
|
136
|
+
/**
|
|
137
|
+
* One composed run of estates: `plan()`, then `apply()` once the approval is
|
|
138
|
+
* given, then `release()` whatever happened. No call reads, locks or writes
|
|
139
|
+
* a state.
|
|
140
|
+
*/
|
|
141
|
+
export class EstateRun {
|
|
142
|
+
constructor(o) {
|
|
143
|
+
this.o = o;
|
|
144
|
+
const c = o.composition;
|
|
145
|
+
if (!c.estate || c.fallback || c.members.length < 2)
|
|
146
|
+
throw new Error(`EstateRun runs a composition of estates with two or more members${c.fallback ? `; this one fell back: ${c.fallback.reason}` : ""}`);
|
|
147
|
+
this.exec = o.exec ?? runBinary;
|
|
148
|
+
this.binary = o.binary ?? o.terraform.binary ?? "choudoufu";
|
|
149
|
+
this.composeDir = join(resolve(o.projectRoot), COMPOSE_DIR);
|
|
150
|
+
this.madeWork = o.work === undefined;
|
|
151
|
+
this.work = o.work ?? mkdtempSync(join(tmpdir(), "chant-compose-estate-"));
|
|
152
|
+
}
|
|
153
|
+
get c() {
|
|
154
|
+
return this.o.composition;
|
|
155
|
+
}
|
|
156
|
+
log(line) {
|
|
157
|
+
this.o.log?.(line);
|
|
158
|
+
}
|
|
159
|
+
/**
|
|
160
|
+
* The composed root's environment: the job's, with no role added (each
|
|
161
|
+
* estate's provider blocks name its role) and its `-var-file` flags taken
|
|
162
|
+
* out. With a shared provider cache and no lock file to check a cached
|
|
163
|
+
* provider against, the cache may fill the lock file.
|
|
164
|
+
*/
|
|
165
|
+
env() {
|
|
166
|
+
const env = withoutVarFiles(this.o.env);
|
|
167
|
+
return env.TF_PLUGIN_CACHE_DIR && !existsSync(join(this.composeDir, ".terraform.lock.hcl")) ? { ...env, TF_PLUGIN_CACHE_MAY_BREAK_DEPENDENCY_LOCK_FILE: "true" } : env;
|
|
168
|
+
}
|
|
169
|
+
/** The estate each member's records go to: its root's `estate`, else its `live` block's. */
|
|
170
|
+
estateOf(member) {
|
|
171
|
+
const key = this.c.roots.get(member);
|
|
172
|
+
return (key !== undefined ? this.o.terraform.roots[key]?.estate : undefined) ?? liveEstate(this.c.dirs.get(member), this.binary).estate;
|
|
173
|
+
}
|
|
174
|
+
notPlanned(extra) {
|
|
175
|
+
return {
|
|
176
|
+
members: {},
|
|
177
|
+
digest: "",
|
|
178
|
+
planFile: join(this.work, "composed.tfplan"),
|
|
179
|
+
text: "",
|
|
180
|
+
texts: {},
|
|
181
|
+
generated: [],
|
|
182
|
+
counts: { add: 0, change: 0, destroy: 0, changes: 0, destroys: 0 },
|
|
183
|
+
summary: "",
|
|
184
|
+
...extra,
|
|
185
|
+
};
|
|
186
|
+
}
|
|
187
|
+
/**
|
|
188
|
+
* Why this choudoufu cannot run the composition, or undefined. Runs
|
|
189
|
+
* `choudoufu version`; what #4447's `groupFallback` asks before planning.
|
|
190
|
+
*/
|
|
191
|
+
async fallback() {
|
|
192
|
+
const v = await this.exec(this.binary, ["version"], resolve(this.o.projectRoot), this.o.env);
|
|
193
|
+
// A binary that cannot say its version is left to the plan, which says why it fails.
|
|
194
|
+
return v.code === 0 ? estateVersionFallback(v.stdout) : undefined;
|
|
195
|
+
}
|
|
196
|
+
writeRoot() {
|
|
197
|
+
this.root = writeEstateRoot({ projectRoot: this.o.projectRoot, composition: this.c });
|
|
198
|
+
return this.root;
|
|
199
|
+
}
|
|
200
|
+
restoreRoot() {
|
|
201
|
+
const r = this.root;
|
|
202
|
+
this.root = undefined;
|
|
203
|
+
r?.restore();
|
|
204
|
+
}
|
|
205
|
+
/**
|
|
206
|
+
* Check the binary's version, write the composed root, init it and plan
|
|
207
|
+
* once, then cut the plan into each member's part. The composed root is
|
|
208
|
+
* taken away again before this returns.
|
|
209
|
+
*/
|
|
210
|
+
async plan() {
|
|
211
|
+
const fallback = await this.fallback();
|
|
212
|
+
if (fallback) {
|
|
213
|
+
this.log(`composed: ${fallback.reason}; the estates plan wave by wave`);
|
|
214
|
+
return this.notPlanned({ fallback });
|
|
215
|
+
}
|
|
216
|
+
let root;
|
|
217
|
+
try {
|
|
218
|
+
root = this.writeRoot();
|
|
219
|
+
}
|
|
220
|
+
catch (e) {
|
|
221
|
+
return this.notPlanned({ error: `the composed root could not be written: ${e.message}` });
|
|
222
|
+
}
|
|
223
|
+
const planFile = join(this.work, "composed.tfplan");
|
|
224
|
+
let plan;
|
|
225
|
+
let text = "";
|
|
226
|
+
let summary = "";
|
|
227
|
+
try {
|
|
228
|
+
const env = this.env();
|
|
229
|
+
const init = await this.exec(this.binary, ["init", "-input=false", "-no-color"], this.composeDir, env);
|
|
230
|
+
if (init.code !== 0)
|
|
231
|
+
return this.notPlanned({ error: `the composed root's init failed\n${firstLines(init.out)}` });
|
|
232
|
+
const p = await this.exec(this.binary, ["plan", "-input=false", "-no-color", `-out=${planFile}`], this.composeDir, env);
|
|
233
|
+
if (p.code !== 0)
|
|
234
|
+
return this.notPlanned({ error: `the composed plan failed\n${firstLines(p.out)}` });
|
|
235
|
+
summary = p.stdout.match(/Plan: .*|No changes\..*/)?.[0] ?? "planned";
|
|
236
|
+
const json = await this.exec(this.binary, ["show", "-json", planFile], this.composeDir, env);
|
|
237
|
+
try {
|
|
238
|
+
plan = JSON.parse(json.stdout);
|
|
239
|
+
}
|
|
240
|
+
catch {
|
|
241
|
+
return this.notPlanned({ error: `show -json printed no plan\n${firstLines(json.out, 6)}` });
|
|
242
|
+
}
|
|
243
|
+
text = (await this.exec(this.binary, ["show", "-no-color", planFile], this.composeDir, env)).stdout;
|
|
244
|
+
}
|
|
245
|
+
finally {
|
|
246
|
+
this.restoreRoot();
|
|
247
|
+
}
|
|
248
|
+
const members = composedMemberPlans(this.c, plan, { planner: "choudoufu", scope: (m) => this.estateOf(m) });
|
|
249
|
+
const texts = Object.fromEntries(this.c.order.map((m) => [m, sliceText(text, this.c.modules.get(m), members[m].counts)]));
|
|
250
|
+
const digest = computePlanDigest("terraform-compose-estate", { plan: terraformPlanDigest(plan), modules: this.c.order.map((m) => [m, this.c.modules.get(m)]), generated: root.generated });
|
|
251
|
+
this.planned = { members, digest, plan, planFile, text, texts, generated: root.generated, counts: planCounts(plan), summary };
|
|
252
|
+
return this.planned;
|
|
253
|
+
}
|
|
254
|
+
/**
|
|
255
|
+
* Apply the saved plan from the composed root, then plan again and read
|
|
256
|
+
* each member's values from that plan's `prior_state`. A failed apply
|
|
257
|
+
* leaves what applied applied, and each member's outcome says how far its
|
|
258
|
+
* part got.
|
|
259
|
+
*/
|
|
260
|
+
async apply() {
|
|
261
|
+
const p = this.planned;
|
|
262
|
+
const notStarted = (error) => ({
|
|
263
|
+
ok: false,
|
|
264
|
+
members: Object.fromEntries(this.c.order.map((m) => [m, { status: "not-started", planned: p?.members[m]?.counts.changes ?? 0, done: 0 }])),
|
|
265
|
+
error,
|
|
266
|
+
});
|
|
267
|
+
if (!p?.plan)
|
|
268
|
+
return notStarted("the composed run did not plan");
|
|
269
|
+
let root;
|
|
270
|
+
try {
|
|
271
|
+
root = this.writeRoot();
|
|
272
|
+
}
|
|
273
|
+
catch (e) {
|
|
274
|
+
return notStarted(`the composed root could not be written: ${e.message}`);
|
|
275
|
+
}
|
|
276
|
+
let out = "";
|
|
277
|
+
let code = 1;
|
|
278
|
+
let after;
|
|
279
|
+
try {
|
|
280
|
+
if (JSON.stringify(root.generated) !== JSON.stringify(p.generated))
|
|
281
|
+
return notStarted("the composed root differs from the one planned, so nothing applied");
|
|
282
|
+
const a = await this.exec(this.binary, ["apply", "-input=false", "-no-color", p.planFile], this.composeDir, this.env());
|
|
283
|
+
out = a.out;
|
|
284
|
+
code = a.code;
|
|
285
|
+
for (const line of a.stdout.split("\n"))
|
|
286
|
+
if (line.trim())
|
|
287
|
+
this.log(`composed: ${line}`);
|
|
288
|
+
after = await this.planAfter();
|
|
289
|
+
}
|
|
290
|
+
finally {
|
|
291
|
+
this.restoreRoot();
|
|
292
|
+
}
|
|
293
|
+
const planned = new Map(this.c.order.map((m) => [m, p.members[m].counts.changes]));
|
|
294
|
+
const slices = after !== undefined ? new Map(this.c.order.map((m) => [m, slicePlan(after, this.c.modules.get(m))])) : undefined;
|
|
295
|
+
const remaining = slices ? new Map(this.c.order.map((m) => [m, planCounts(slices.get(m)).changes])) : undefined;
|
|
296
|
+
const ended = estateOutcomes(this.c, planned, out, code, remaining);
|
|
297
|
+
const members = {};
|
|
298
|
+
for (const m of this.c.order) {
|
|
299
|
+
const row = { ...ended.members[m] };
|
|
300
|
+
const slice = slices?.get(m);
|
|
301
|
+
if (slice !== undefined) {
|
|
302
|
+
row.resources = stateResources(slice);
|
|
303
|
+
if (row.status === "applied" || row.status === "no-changes") {
|
|
304
|
+
// A state choudoufu builds from records may carry no root outputs; the same plan's planned outputs, all known after the apply, stand in.
|
|
305
|
+
const outputs = stateOutputs(slice);
|
|
306
|
+
row.outputs = Object.keys(outputs).length > 0 ? outputs : terraformPlannedOutputs(slice).known;
|
|
307
|
+
}
|
|
308
|
+
}
|
|
309
|
+
members[m] = row;
|
|
310
|
+
}
|
|
311
|
+
const ok = code === 0 && Object.values(members).every((x) => x.status === "applied" || x.status === "no-changes");
|
|
312
|
+
const error = ok ? undefined : (ended.other[0] ?? Object.values(members).find((x) => x.error)?.error ?? "the composed apply failed");
|
|
313
|
+
return { ok, members, ...(after !== undefined ? { after } : {}), ...(error ? { error } : {}) };
|
|
314
|
+
}
|
|
315
|
+
/**
|
|
316
|
+
* `show -json` of a plan of the composed root made after the apply, whose
|
|
317
|
+
* `prior_state` choudoufu builds from the records and the live system.
|
|
318
|
+
* Undefined when it cannot be made: the values unknown at plan then stay
|
|
319
|
+
* unknown. Never fails the run.
|
|
320
|
+
*/
|
|
321
|
+
async planAfter() {
|
|
322
|
+
const planFile = join(this.work, "composed-after.tfplan");
|
|
323
|
+
const env = this.env();
|
|
324
|
+
try {
|
|
325
|
+
const p = await this.exec(this.binary, ["plan", "-input=false", "-no-color", `-out=${planFile}`], this.composeDir, env);
|
|
326
|
+
if (p.code !== 0) {
|
|
327
|
+
this.log(`composed: the estates could not be planned after the apply; the values unknown at plan stay unknown\n${firstLines(p.out)}`);
|
|
328
|
+
return undefined;
|
|
329
|
+
}
|
|
330
|
+
const s = await this.exec(this.binary, ["show", "-json", planFile], this.composeDir, env);
|
|
331
|
+
if (s.code !== 0)
|
|
332
|
+
return undefined;
|
|
333
|
+
return JSON.parse(s.stdout);
|
|
334
|
+
}
|
|
335
|
+
catch (e) {
|
|
336
|
+
this.log(`composed: the estates could not be read after the apply (${e.message}); the values unknown at plan stay unknown`);
|
|
337
|
+
return undefined;
|
|
338
|
+
}
|
|
339
|
+
}
|
|
340
|
+
/**
|
|
341
|
+
* Take the composed root away if a call left it, with the binary's working
|
|
342
|
+
* files under `.chant-compose/`, and the plan files. There is no lock to
|
|
343
|
+
* let go of. Safe to call more than once.
|
|
344
|
+
*/
|
|
345
|
+
async release() {
|
|
346
|
+
this.restoreRoot();
|
|
347
|
+
for (const f of [".terraform", ".terraform.lock.hcl"])
|
|
348
|
+
rmSync(join(this.composeDir, f), { recursive: true, force: true });
|
|
349
|
+
try {
|
|
350
|
+
if (existsSync(this.composeDir) && readdirSync(this.composeDir).length === 0)
|
|
351
|
+
rmdirSync(this.composeDir);
|
|
352
|
+
}
|
|
353
|
+
catch {
|
|
354
|
+
// Gone already.
|
|
355
|
+
}
|
|
356
|
+
if (this.madeWork)
|
|
357
|
+
rmSync(this.work, { recursive: true, force: true });
|
|
358
|
+
else
|
|
359
|
+
for (const f of ["composed.tfplan", "composed-after.tfplan"])
|
|
360
|
+
rmSync(join(this.work, f), { force: true });
|
|
361
|
+
this.planned = undefined;
|
|
362
|
+
}
|
|
363
|
+
}
|
|
@@ -0,0 +1,99 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* The HCL a composition reads from a root's files (chant#4438): its backend
|
|
3
|
+
* and the state that backend names, its `terraform_remote_state` and
|
|
4
|
+
* `terraform_estate_outputs` reads, its `live` estate, the providers its lock
|
|
5
|
+
* file pins, and the local modules it calls.
|
|
6
|
+
*
|
|
7
|
+
* Lifted from terragucci at c493e0e (`compose.ts` `blankComments`,
|
|
8
|
+
* `lockedProviders`, `localModules`, `importLiteral`, `jsonBlocks`;
|
|
9
|
+
* `detect.ts` `blockBody`, `hclAttr`, `stateOf`, `estateOf`,
|
|
10
|
+
* `estateOutputReads`, `liveRoots`; `linked.ts` `configFiles`), reading a
|
|
11
|
+
* root's `-backend-config` from `terraform.roots.<name>.backendConfig` where
|
|
12
|
+
* terragucci read `TF_CLI_ARGS_init`. Regex over text with comments blanked,
|
|
13
|
+
* as there: no HCL parse runs.
|
|
14
|
+
*/
|
|
15
|
+
import { type Attr, type StateKey } from "./state-address.js";
|
|
16
|
+
import { type ReadBackendInput } from "../state/backend.js";
|
|
17
|
+
export type { StateKey } from "./state-address.js";
|
|
18
|
+
/**
|
|
19
|
+
* HCL text with its comments blanked to spaces, newlines kept, so every
|
|
20
|
+
* position in it is the same position in the text as written. Strings and
|
|
21
|
+
* their escapes are read through, so a `#` or `//` in one stays.
|
|
22
|
+
*/
|
|
23
|
+
export declare function blankComments(text: string): string;
|
|
24
|
+
/** The text of the block that starts at `start`: up to the brace that closes its first `{`. */
|
|
25
|
+
export declare function blockBody(text: string, start: number): string;
|
|
26
|
+
/**
|
|
27
|
+
* An HCL block's attribute: its string, `null` when it is written as anything
|
|
28
|
+
* but a plain string, undefined when it is not written.
|
|
29
|
+
*/
|
|
30
|
+
export declare const hclAttr: (body: string) => Attr;
|
|
31
|
+
/**
|
|
32
|
+
* A root's own configuration files, not its modules', as paths: the set the
|
|
33
|
+
* root's `binary` reads (`.tf` and `.tf.json`, plus `.tofu` and `.tofu.json`
|
|
34
|
+
* for tofu or choudoufu), from the lexicon's one lister (chant#4457).
|
|
35
|
+
*/
|
|
36
|
+
export declare function configFiles(dir: string, binary?: string): string[];
|
|
37
|
+
/** One configuration file's text, comments blanked when it is HCL. */
|
|
38
|
+
export interface RootText {
|
|
39
|
+
file: string;
|
|
40
|
+
text: string;
|
|
41
|
+
json: boolean;
|
|
42
|
+
}
|
|
43
|
+
/** The text of a root's own configuration files, comments blanked so positions still match. */
|
|
44
|
+
export declare function rootTexts(dir: string, binary?: string): RootText[];
|
|
45
|
+
/** The blocks of a kind in a JSON-syntax file: `{"import": [...]}` or `{"import": {...}}`. */
|
|
46
|
+
export declare function jsonBlocks(doc: unknown, kind: string): Record<string, unknown>[];
|
|
47
|
+
/** A `terraform_remote_state` block: its label, the state it reads, and whether it repeats (count or for_each). */
|
|
48
|
+
export interface RemoteStateRead extends StateKey {
|
|
49
|
+
name: string;
|
|
50
|
+
repeated: boolean;
|
|
51
|
+
}
|
|
52
|
+
/** What a root's code says about state: the state its backend keeps and the states its `terraform_remote_state` blocks read. */
|
|
53
|
+
export interface RootState {
|
|
54
|
+
own?: StateKey;
|
|
55
|
+
reads: RemoteStateRead[];
|
|
56
|
+
}
|
|
57
|
+
/**
|
|
58
|
+
* The state the root at `dir` keeps, and the states its
|
|
59
|
+
* `terraform_remote_state` blocks read. `rel` is the root's directory
|
|
60
|
+
* relative to the project, which a `local` path resolves against.
|
|
61
|
+
*
|
|
62
|
+
* Which backend and which configuration name the root's own state is
|
|
63
|
+
* state/backend.ts's {@link readBackend} verdict (chant#4478): the code with
|
|
64
|
+
* the `-backend-config` flags of `TF_CLI_ARGS`, `TF_CLI_ARGS_init`,
|
|
65
|
+
* `backendConfigFiles` and `backendConfig` over it, and what `init` recorded
|
|
66
|
+
* once it has run. A key neither gives is read from the code's own block,
|
|
67
|
+
* which still names nested ones (a `cloud` or `remote` backend's
|
|
68
|
+
* `workspaces`). An address the code does not spell in plain strings is left
|
|
69
|
+
* out, so nothing lines up with it.
|
|
70
|
+
*/
|
|
71
|
+
export declare function rootState(dir: string, rel: string, input?: ReadBackendInput): RootState;
|
|
72
|
+
/** Two addresses name one state: the same key, and the same bucket where both name one. */
|
|
73
|
+
export declare const sameState: (a: StateKey, b: StateKey) => boolean;
|
|
74
|
+
/**
|
|
75
|
+
* A choudoufu root's estate, from its `estate.chdf.hcl` or the `live` block in
|
|
76
|
+
* its `terraform` block; undefined when it declares none. A `live` block takes
|
|
77
|
+
* effect only under choudoufu, so the files read are the ones choudoufu reads
|
|
78
|
+
* unless `binary` names another.
|
|
79
|
+
*/
|
|
80
|
+
export declare function liveEstate(dir: string, binary?: string): {
|
|
81
|
+
live: boolean;
|
|
82
|
+
estate?: string;
|
|
83
|
+
};
|
|
84
|
+
/** Each `data "terraform_estate_outputs"` block of a root: its label and the estate whose outputs it reads. */
|
|
85
|
+
export declare function estateOutputReads(dir: string, binary?: string): {
|
|
86
|
+
name: string;
|
|
87
|
+
estate: string;
|
|
88
|
+
}[];
|
|
89
|
+
/** The provider versions a root's lock file pins, by provider address. */
|
|
90
|
+
export declare function lockedProviders(dir: string): Map<string, string>;
|
|
91
|
+
/** Local module directories the root at `dir` calls (`source = "./..."` or `"../..."`), followed through, absolute. */
|
|
92
|
+
export declare function localModules(dir: string, binary?: string): string[];
|
|
93
|
+
/** `abs` relative to `from`, with `/` between parts, `.` for `from` itself. */
|
|
94
|
+
export declare const relPath: (from: string, abs: string) => string;
|
|
95
|
+
/** An `import` block the composed root can take as it is: a literal string id, no for_each, no provider of the root's own. */
|
|
96
|
+
export declare function importLiteral(body: string): boolean;
|
|
97
|
+
/** Whether a JSON-syntax `import` block takes no literal string id (or has for_each or a provider). */
|
|
98
|
+
export declare function jsonImportRefused(text: string): boolean;
|
|
99
|
+
//# sourceMappingURL=hcl.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"hcl.d.ts","sourceRoot":"","sources":["../../src/compose/hcl.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;GAaG;AAKH,OAAO,EAAyB,KAAK,IAAI,EAAE,KAAK,QAAQ,EAAE,MAAM,iBAAiB,CAAC;AAClF,OAAO,EAAe,KAAK,gBAAgB,EAAE,MAAM,kBAAkB,CAAC;AAEtE,YAAY,EAAE,QAAQ,EAAE,MAAM,iBAAiB,CAAC;AAEhD;;;;GAIG;AACH,wBAAgB,aAAa,CAAC,IAAI,EAAE,MAAM,GAAG,MAAM,CAqBlD;AAED,+FAA+F;AAC/F,wBAAgB,SAAS,CAAC,IAAI,EAAE,MAAM,EAAE,KAAK,EAAE,MAAM,GAAG,MAAM,CAO7D;AAED;;;GAGG;AACH,eAAO,MAAM,OAAO,SACX,MAAM,KAAG,IAgBf,CAAC;AAEJ;;;;GAIG;AACH,wBAAgB,WAAW,CAAC,GAAG,EAAE,MAAM,EAAE,MAAM,CAAC,EAAE,MAAM,GAAG,MAAM,EAAE,CAElE;AAED,sEAAsE;AACtE,MAAM,WAAW,QAAQ;IACvB,IAAI,EAAE,MAAM,CAAC;IACb,IAAI,EAAE,MAAM,CAAC;IACb,IAAI,EAAE,OAAO,CAAC;CACf;AAED,+FAA+F;AAC/F,wBAAgB,SAAS,CAAC,GAAG,EAAE,MAAM,EAAE,MAAM,CAAC,EAAE,MAAM,GAAG,QAAQ,EAAE,CAMlE;AAaD,8FAA8F;AAC9F,wBAAgB,UAAU,CAAC,GAAG,EAAE,OAAO,EAAE,IAAI,EAAE,MAAM,GAAG,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,EAAE,CAIhF;AAED,mHAAmH;AACnH,MAAM,WAAW,eAAgB,SAAQ,QAAQ;IAC/C,IAAI,EAAE,MAAM,CAAC;IACb,QAAQ,EAAE,OAAO,CAAC;CACnB;AAED,gIAAgI;AAChI,MAAM,WAAW,SAAS;IACxB,GAAG,CAAC,EAAE,QAAQ,CAAC;IACf,KAAK,EAAE,eAAe,EAAE,CAAC;CAC1B;AAWD;;;;;;;;;;;;;GAaG;AACH,wBAAgB,SAAS,CAAC,GAAG,EAAE,MAAM,EAAE,GAAG,EAAE,MAAM,EAAE,KAAK,GAAE,gBAAqB,GAAG,SAAS,CAsD3F;AAED,2FAA2F;AAC3F,eAAO,MAAM,SAAS,MAAO,QAAQ,KAAK,QAAQ,KAAG,OAA+E,CAAC;AAIrI;;;;;GAKG;AACH,wBAAgB,UAAU,CAAC,GAAG,EAAE,MAAM,EAAE,MAAM,SAAc,GAAG;IAAE,IAAI,EAAE,OAAO,CAAC;IAAC,MAAM,CAAC,EAAE,MAAM,CAAA;CAAE,CAiBhG;AAED,+GAA+G;AAC/G,wBAAgB,iBAAiB,CAAC,GAAG,EAAE,MAAM,EAAE,MAAM,CAAC,EAAE,MAAM,GAAG;IAAE,IAAI,EAAE,MAAM,CAAC;IAAC,MAAM,EAAE,MAAM,CAAA;CAAE,EAAE,CAUlG;AAED,0EAA0E;AAC1E,wBAAgB,eAAe,CAAC,GAAG,EAAE,MAAM,GAAG,GAAG,CAAC,MAAM,EAAE,MAAM,CAAC,CAahE;AAED,uHAAuH;AACvH,wBAAgB,YAAY,CAAC,GAAG,EAAE,MAAM,EAAE,MAAM,CAAC,EAAE,MAAM,GAAG,MAAM,EAAE,CAkBnE;AAED,+EAA+E;AAC/E,eAAO,MAAM,OAAO,SAAU,MAAM,OAAO,MAAM,KAAG,MAA0D,CAAC;AAE/G,8HAA8H;AAC9H,wBAAgB,aAAa,CAAC,IAAI,EAAE,MAAM,GAAG,OAAO,CAGnD;AAED,uGAAuG;AACvG,wBAAgB,iBAAiB,CAAC,IAAI,EAAE,MAAM,GAAG,OAAO,CAEvD"}
|