1
0
mirror of https://github.com/hashicorp/terraform.git synced 2026-02-05 06:46:14 +01:00

Backport of Add component registry source resolution support to Terraform Stacks into v1.14 (#37983)

* Add component registry source resolution support to Terraform Stacks

This change implements the missing component source resolution case in the stack configuration loader, enabling Terraform Stacks to properly handle component registry sources from HCP Terraform and other component registries.

The implementation mirrors the existing module registry resolution workflow, where component sources are first resolved to their versioned form using the source bundle's component metadata, then converted to final source addresses that can be used to locate the actual component code. This completes the integration between the terraform-registry-address component parsing capabilities and the go-slug sourcebundle component resolution APIs.

* chore: bump go-slug to v0.18.1

* fix: add case for component final source type

* chore: rm space

* chore: sync module deps

* chore: update testdata with separate bundle

* fix: manifest file json obj with trailing comma

* Add changelog entry to 1.14

* fix deps

---------

Co-authored-by: James Pogran <james.pogran@hashicorp.com>
Co-authored-by: Michael Yocca <michael.yocca@hashicorp.com>
Co-authored-by: Samsondeen Dare <samsondeen.dare@hashicorp.com>
This commit is contained in:
github-actions[bot]
2025-12-11 10:17:05 +01:00
committed by GitHub
parent 2d747e90b6
commit eb62e3eec1
30 changed files with 241 additions and 34 deletions

View File

@@ -0,0 +1,5 @@
kind: ENHANCEMENTS
body: Add component registry source resolution support to Terraform Stacks
time: 2025-12-04T12:58:48.622196-05:00
custom:
Issue: "37888"

2
go.mod
View File

@@ -28,7 +28,7 @@ require (
github.com/hashicorp/go-hclog v1.6.3
github.com/hashicorp/go-plugin v1.7.0
github.com/hashicorp/go-retryablehttp v0.7.8
github.com/hashicorp/go-slug v0.16.8
github.com/hashicorp/go-slug v0.18.1
github.com/hashicorp/go-tfe v1.94.0
github.com/hashicorp/go-uuid v1.0.3
github.com/hashicorp/go-version v1.7.0

4
go.sum
View File

@@ -482,8 +482,8 @@ github.com/hashicorp/go-retryablehttp v0.7.8/go.mod h1:rjiScheydd+CxvumBsIrFKlx3
github.com/hashicorp/go-rootcerts v1.0.1/go.mod h1:pqUvnprVnM5bf7AOirdbb01K4ccR319Vf4pU3K5EGc8=
github.com/hashicorp/go-rootcerts v1.0.2 h1:jzhAVGtqPKbwpyCPELlgNWhE1znq+qwJtW5Oi2viEzc=
github.com/hashicorp/go-rootcerts v1.0.2/go.mod h1:pqUvnprVnM5bf7AOirdbb01K4ccR319Vf4pU3K5EGc8=
github.com/hashicorp/go-slug v0.16.8 h1:f4/sDZqRsxx006HrE6e9BE5xO9lWXydKhVoH6Kb0v1M=
github.com/hashicorp/go-slug v0.16.8/go.mod h1:hB4mUcVHl4RPu0205s0fwmB9i31MxQgeafGkko3FD+Y=
github.com/hashicorp/go-slug v0.18.1 h1:UnWIy4mq9GaDr1LhAzCPgA6RSQUn952RLFqQe3HPyCs=
github.com/hashicorp/go-slug v0.18.1/go.mod h1:Zxkkl8/LfXmhxZO3fLXQUCy3MVXAJK9pybY8WoDPgvs=
github.com/hashicorp/go-sockaddr v1.0.0/go.mod h1:7Xibr9yA9JjQq1JpNB2Vw7kxv8xerXegt+ozgdvDeDU=
github.com/hashicorp/go-sockaddr v1.0.2/go.mod h1:rB4wwRAUzs07qva3c5SdrY/NEtAUjGlgmH/UkBUC97A=
github.com/hashicorp/go-sockaddr v1.0.5 h1:dvk7TIXCZpmfOlM+9mlcrWmWjw/wlKT+VDq2wMvfPJU=

View File

@@ -34,7 +34,7 @@ require (
github.com/hashicorp/go-cty v1.4.1 // indirect
github.com/hashicorp/go-hclog v1.6.3 // indirect
github.com/hashicorp/go-retryablehttp v0.7.8 // indirect
github.com/hashicorp/go-slug v0.16.8 // indirect
github.com/hashicorp/go-slug v0.18.1 // indirect
github.com/hashicorp/go-version v1.7.0 // indirect
github.com/hashicorp/hcl/v2 v2.24.0 // indirect
github.com/hashicorp/logutils v1.0.0 // indirect

View File

@@ -241,8 +241,8 @@ github.com/hashicorp/go-hclog v1.6.3 h1:Qr2kF+eVWjTiYmU7Y31tYlP1h0q/X3Nl3tPGdaB1
github.com/hashicorp/go-hclog v1.6.3/go.mod h1:W4Qnvbt70Wk/zYJryRzDRU/4r0kIg0PVHBcfoyhpF5M=
github.com/hashicorp/go-retryablehttp v0.7.8 h1:ylXZWnqa7Lhqpk0L1P1LzDtGcCR0rPVUrx/c8Unxc48=
github.com/hashicorp/go-retryablehttp v0.7.8/go.mod h1:rjiScheydd+CxvumBsIrFKlx3iS0jrZ7LvzFGFmuKbw=
github.com/hashicorp/go-slug v0.16.8 h1:f4/sDZqRsxx006HrE6e9BE5xO9lWXydKhVoH6Kb0v1M=
github.com/hashicorp/go-slug v0.16.8/go.mod h1:hB4mUcVHl4RPu0205s0fwmB9i31MxQgeafGkko3FD+Y=
github.com/hashicorp/go-slug v0.18.1 h1:UnWIy4mq9GaDr1LhAzCPgA6RSQUn952RLFqQe3HPyCs=
github.com/hashicorp/go-slug v0.18.1/go.mod h1:Zxkkl8/LfXmhxZO3fLXQUCy3MVXAJK9pybY8WoDPgvs=
github.com/hashicorp/go-uuid v1.0.3 h1:2gKiV6YVmrJ1i2CKKa9obLvRieoRGviZFL26PcT/Co8=
github.com/hashicorp/go-uuid v1.0.3/go.mod h1:6SBZvOh/SIDV7/2o3Jml5SYk/TvGqwFJ/bN7x4byOro=
github.com/hashicorp/go-version v1.7.0 h1:5tqGy27NaOTB8yJKUZELlFAS/LTKJkrmONwQKeRZfjY=

View File

@@ -27,7 +27,7 @@ require (
github.com/hashicorp/go-metrics v0.5.4 // indirect
github.com/hashicorp/go-multierror v1.1.1 // indirect
github.com/hashicorp/go-rootcerts v1.0.2 // indirect
github.com/hashicorp/go-slug v0.16.8 // indirect
github.com/hashicorp/go-slug v0.18.1 // indirect
github.com/hashicorp/go-uuid v1.0.3 // indirect
github.com/hashicorp/go-version v1.7.0 // indirect
github.com/hashicorp/golang-lru v1.0.2 // indirect

View File

@@ -252,8 +252,8 @@ github.com/hashicorp/go-retryablehttp v0.7.8 h1:ylXZWnqa7Lhqpk0L1P1LzDtGcCR0rPVU
github.com/hashicorp/go-retryablehttp v0.7.8/go.mod h1:rjiScheydd+CxvumBsIrFKlx3iS0jrZ7LvzFGFmuKbw=
github.com/hashicorp/go-rootcerts v1.0.2 h1:jzhAVGtqPKbwpyCPELlgNWhE1znq+qwJtW5Oi2viEzc=
github.com/hashicorp/go-rootcerts v1.0.2/go.mod h1:pqUvnprVnM5bf7AOirdbb01K4ccR319Vf4pU3K5EGc8=
github.com/hashicorp/go-slug v0.16.8 h1:f4/sDZqRsxx006HrE6e9BE5xO9lWXydKhVoH6Kb0v1M=
github.com/hashicorp/go-slug v0.16.8/go.mod h1:hB4mUcVHl4RPu0205s0fwmB9i31MxQgeafGkko3FD+Y=
github.com/hashicorp/go-slug v0.18.1 h1:UnWIy4mq9GaDr1LhAzCPgA6RSQUn952RLFqQe3HPyCs=
github.com/hashicorp/go-slug v0.18.1/go.mod h1:Zxkkl8/LfXmhxZO3fLXQUCy3MVXAJK9pybY8WoDPgvs=
github.com/hashicorp/go-sockaddr v1.0.5 h1:dvk7TIXCZpmfOlM+9mlcrWmWjw/wlKT+VDq2wMvfPJU=
github.com/hashicorp/go-sockaddr v1.0.5/go.mod h1:uoUUmtwU7n9Dv3O4SNLeFvg0SxQ3lyjsj6+CCykpaxI=
github.com/hashicorp/go-uuid v1.0.0/go.mod h1:6SBZvOh/SIDV7/2o3Jml5SYk/TvGqwFJ/bN7x4byOro=

View File

@@ -23,7 +23,7 @@ require (
github.com/google/go-cmp v0.7.0 // indirect
github.com/google/go-querystring v1.1.0 // indirect
github.com/google/uuid v1.6.0 // indirect
github.com/hashicorp/go-slug v0.16.8 // indirect
github.com/hashicorp/go-slug v0.18.1 // indirect
github.com/hashicorp/go-uuid v1.0.3 // indirect
github.com/hashicorp/go-version v1.7.0 // indirect
github.com/hashicorp/hcl/v2 v2.24.0 // indirect

View File

@@ -210,8 +210,8 @@ github.com/hashicorp/go-hclog v1.6.3 h1:Qr2kF+eVWjTiYmU7Y31tYlP1h0q/X3Nl3tPGdaB1
github.com/hashicorp/go-hclog v1.6.3/go.mod h1:W4Qnvbt70Wk/zYJryRzDRU/4r0kIg0PVHBcfoyhpF5M=
github.com/hashicorp/go-retryablehttp v0.7.8 h1:ylXZWnqa7Lhqpk0L1P1LzDtGcCR0rPVUrx/c8Unxc48=
github.com/hashicorp/go-retryablehttp v0.7.8/go.mod h1:rjiScheydd+CxvumBsIrFKlx3iS0jrZ7LvzFGFmuKbw=
github.com/hashicorp/go-slug v0.16.8 h1:f4/sDZqRsxx006HrE6e9BE5xO9lWXydKhVoH6Kb0v1M=
github.com/hashicorp/go-slug v0.16.8/go.mod h1:hB4mUcVHl4RPu0205s0fwmB9i31MxQgeafGkko3FD+Y=
github.com/hashicorp/go-slug v0.18.1 h1:UnWIy4mq9GaDr1LhAzCPgA6RSQUn952RLFqQe3HPyCs=
github.com/hashicorp/go-slug v0.18.1/go.mod h1:Zxkkl8/LfXmhxZO3fLXQUCy3MVXAJK9pybY8WoDPgvs=
github.com/hashicorp/go-uuid v1.0.3 h1:2gKiV6YVmrJ1i2CKKa9obLvRieoRGviZFL26PcT/Co8=
github.com/hashicorp/go-uuid v1.0.3/go.mod h1:6SBZvOh/SIDV7/2o3Jml5SYk/TvGqwFJ/bN7x4byOro=
github.com/hashicorp/go-version v1.7.0 h1:5tqGy27NaOTB8yJKUZELlFAS/LTKJkrmONwQKeRZfjY=

View File

@@ -34,7 +34,7 @@ require (
github.com/googleapis/enterprise-certificate-proxy v0.3.2 // indirect
github.com/googleapis/gax-go/v2 v2.12.0 // indirect
github.com/hashicorp/go-cleanhttp v0.5.2 // indirect
github.com/hashicorp/go-slug v0.16.8 // indirect
github.com/hashicorp/go-slug v0.18.1 // indirect
github.com/hashicorp/go-uuid v1.0.3 // indirect
github.com/hashicorp/go-version v1.7.0 // indirect
github.com/hashicorp/hcl/v2 v2.24.0 // indirect

View File

@@ -215,8 +215,8 @@ github.com/hashicorp/go-hclog v1.6.3 h1:Qr2kF+eVWjTiYmU7Y31tYlP1h0q/X3Nl3tPGdaB1
github.com/hashicorp/go-hclog v1.6.3/go.mod h1:W4Qnvbt70Wk/zYJryRzDRU/4r0kIg0PVHBcfoyhpF5M=
github.com/hashicorp/go-retryablehttp v0.7.8 h1:ylXZWnqa7Lhqpk0L1P1LzDtGcCR0rPVUrx/c8Unxc48=
github.com/hashicorp/go-retryablehttp v0.7.8/go.mod h1:rjiScheydd+CxvumBsIrFKlx3iS0jrZ7LvzFGFmuKbw=
github.com/hashicorp/go-slug v0.16.8 h1:f4/sDZqRsxx006HrE6e9BE5xO9lWXydKhVoH6Kb0v1M=
github.com/hashicorp/go-slug v0.16.8/go.mod h1:hB4mUcVHl4RPu0205s0fwmB9i31MxQgeafGkko3FD+Y=
github.com/hashicorp/go-slug v0.18.1 h1:UnWIy4mq9GaDr1LhAzCPgA6RSQUn952RLFqQe3HPyCs=
github.com/hashicorp/go-slug v0.18.1/go.mod h1:Zxkkl8/LfXmhxZO3fLXQUCy3MVXAJK9pybY8WoDPgvs=
github.com/hashicorp/go-uuid v1.0.3 h1:2gKiV6YVmrJ1i2CKKa9obLvRieoRGviZFL26PcT/Co8=
github.com/hashicorp/go-uuid v1.0.3/go.mod h1:6SBZvOh/SIDV7/2o3Jml5SYk/TvGqwFJ/bN7x4byOro=
github.com/hashicorp/go-version v1.7.0 h1:5tqGy27NaOTB8yJKUZELlFAS/LTKJkrmONwQKeRZfjY=

View File

@@ -29,7 +29,7 @@ require (
github.com/google/gnostic-models v0.6.9 // indirect
github.com/google/go-cmp v0.7.0 // indirect
github.com/google/uuid v1.6.0 // indirect
github.com/hashicorp/go-slug v0.16.8 // indirect
github.com/hashicorp/go-slug v0.18.1 // indirect
github.com/hashicorp/go-uuid v1.0.3 // indirect
github.com/hashicorp/go-version v1.7.0 // indirect
github.com/hashicorp/hcl/v2 v2.24.0 // indirect

View File

@@ -227,8 +227,8 @@ github.com/hashicorp/go-hclog v1.6.3 h1:Qr2kF+eVWjTiYmU7Y31tYlP1h0q/X3Nl3tPGdaB1
github.com/hashicorp/go-hclog v1.6.3/go.mod h1:W4Qnvbt70Wk/zYJryRzDRU/4r0kIg0PVHBcfoyhpF5M=
github.com/hashicorp/go-retryablehttp v0.7.8 h1:ylXZWnqa7Lhqpk0L1P1LzDtGcCR0rPVUrx/c8Unxc48=
github.com/hashicorp/go-retryablehttp v0.7.8/go.mod h1:rjiScheydd+CxvumBsIrFKlx3iS0jrZ7LvzFGFmuKbw=
github.com/hashicorp/go-slug v0.16.8 h1:f4/sDZqRsxx006HrE6e9BE5xO9lWXydKhVoH6Kb0v1M=
github.com/hashicorp/go-slug v0.16.8/go.mod h1:hB4mUcVHl4RPu0205s0fwmB9i31MxQgeafGkko3FD+Y=
github.com/hashicorp/go-slug v0.18.1 h1:UnWIy4mq9GaDr1LhAzCPgA6RSQUn952RLFqQe3HPyCs=
github.com/hashicorp/go-slug v0.18.1/go.mod h1:Zxkkl8/LfXmhxZO3fLXQUCy3MVXAJK9pybY8WoDPgvs=
github.com/hashicorp/go-uuid v1.0.3 h1:2gKiV6YVmrJ1i2CKKa9obLvRieoRGviZFL26PcT/Co8=
github.com/hashicorp/go-uuid v1.0.3/go.mod h1:6SBZvOh/SIDV7/2o3Jml5SYk/TvGqwFJ/bN7x4byOro=
github.com/hashicorp/go-version v1.7.0 h1:5tqGy27NaOTB8yJKUZELlFAS/LTKJkrmONwQKeRZfjY=

View File

@@ -21,7 +21,7 @@ require (
github.com/fatih/color v1.18.0 // indirect
github.com/gofrs/flock v0.10.0 // indirect
github.com/google/uuid v1.6.0 // indirect
github.com/hashicorp/go-slug v0.16.8 // indirect
github.com/hashicorp/go-slug v0.18.1 // indirect
github.com/hashicorp/go-version v1.7.0 // indirect
github.com/hashicorp/hcl/v2 v2.24.0 // indirect
github.com/hashicorp/terraform-registry-address v0.4.0 // indirect

View File

@@ -208,8 +208,8 @@ github.com/hashicorp/go-hclog v1.6.3 h1:Qr2kF+eVWjTiYmU7Y31tYlP1h0q/X3Nl3tPGdaB1
github.com/hashicorp/go-hclog v1.6.3/go.mod h1:W4Qnvbt70Wk/zYJryRzDRU/4r0kIg0PVHBcfoyhpF5M=
github.com/hashicorp/go-retryablehttp v0.7.8 h1:ylXZWnqa7Lhqpk0L1P1LzDtGcCR0rPVUrx/c8Unxc48=
github.com/hashicorp/go-retryablehttp v0.7.8/go.mod h1:rjiScheydd+CxvumBsIrFKlx3iS0jrZ7LvzFGFmuKbw=
github.com/hashicorp/go-slug v0.16.8 h1:f4/sDZqRsxx006HrE6e9BE5xO9lWXydKhVoH6Kb0v1M=
github.com/hashicorp/go-slug v0.16.8/go.mod h1:hB4mUcVHl4RPu0205s0fwmB9i31MxQgeafGkko3FD+Y=
github.com/hashicorp/go-slug v0.18.1 h1:UnWIy4mq9GaDr1LhAzCPgA6RSQUn952RLFqQe3HPyCs=
github.com/hashicorp/go-slug v0.18.1/go.mod h1:Zxkkl8/LfXmhxZO3fLXQUCy3MVXAJK9pybY8WoDPgvs=
github.com/hashicorp/go-uuid v1.0.3 h1:2gKiV6YVmrJ1i2CKKa9obLvRieoRGviZFL26PcT/Co8=
github.com/hashicorp/go-uuid v1.0.3/go.mod h1:6SBZvOh/SIDV7/2o3Jml5SYk/TvGqwFJ/bN7x4byOro=
github.com/hashicorp/go-version v1.7.0 h1:5tqGy27NaOTB8yJKUZELlFAS/LTKJkrmONwQKeRZfjY=

View File

@@ -26,7 +26,7 @@ require (
github.com/golang/protobuf v1.5.4 // indirect
github.com/google/go-cmp v0.7.0 // indirect
github.com/google/uuid v1.6.0 // indirect
github.com/hashicorp/go-slug v0.16.8 // indirect
github.com/hashicorp/go-slug v0.18.1 // indirect
github.com/hashicorp/go-version v1.7.0 // indirect
github.com/hashicorp/hcl/v2 v2.24.0 // indirect
github.com/hashicorp/terraform-registry-address v0.4.0 // indirect

View File

@@ -215,8 +215,8 @@ github.com/hashicorp/go-hclog v1.6.3 h1:Qr2kF+eVWjTiYmU7Y31tYlP1h0q/X3Nl3tPGdaB1
github.com/hashicorp/go-hclog v1.6.3/go.mod h1:W4Qnvbt70Wk/zYJryRzDRU/4r0kIg0PVHBcfoyhpF5M=
github.com/hashicorp/go-retryablehttp v0.7.8 h1:ylXZWnqa7Lhqpk0L1P1LzDtGcCR0rPVUrx/c8Unxc48=
github.com/hashicorp/go-retryablehttp v0.7.8/go.mod h1:rjiScheydd+CxvumBsIrFKlx3iS0jrZ7LvzFGFmuKbw=
github.com/hashicorp/go-slug v0.16.8 h1:f4/sDZqRsxx006HrE6e9BE5xO9lWXydKhVoH6Kb0v1M=
github.com/hashicorp/go-slug v0.16.8/go.mod h1:hB4mUcVHl4RPu0205s0fwmB9i31MxQgeafGkko3FD+Y=
github.com/hashicorp/go-slug v0.18.1 h1:UnWIy4mq9GaDr1LhAzCPgA6RSQUn952RLFqQe3HPyCs=
github.com/hashicorp/go-slug v0.18.1/go.mod h1:Zxkkl8/LfXmhxZO3fLXQUCy3MVXAJK9pybY8WoDPgvs=
github.com/hashicorp/go-uuid v1.0.3 h1:2gKiV6YVmrJ1i2CKKa9obLvRieoRGviZFL26PcT/Co8=
github.com/hashicorp/go-uuid v1.0.3/go.mod h1:6SBZvOh/SIDV7/2o3Jml5SYk/TvGqwFJ/bN7x4byOro=
github.com/hashicorp/go-version v1.7.0 h1:5tqGy27NaOTB8yJKUZELlFAS/LTKJkrmONwQKeRZfjY=

View File

@@ -19,7 +19,7 @@ require (
github.com/davecgh/go-spew v1.1.2-0.20180830191138-d8f796af33cc // indirect
github.com/google/go-cmp v0.7.0 // indirect
github.com/google/uuid v1.6.0 // indirect
github.com/hashicorp/go-slug v0.16.8 // indirect
github.com/hashicorp/go-slug v0.18.1 // indirect
github.com/hashicorp/go-version v1.7.0 // indirect
github.com/hashicorp/terraform-registry-address v0.4.0 // indirect
github.com/hashicorp/terraform-svchost v0.1.1 // indirect

View File

@@ -203,8 +203,8 @@ github.com/hashicorp/go-hclog v1.6.3 h1:Qr2kF+eVWjTiYmU7Y31tYlP1h0q/X3Nl3tPGdaB1
github.com/hashicorp/go-hclog v1.6.3/go.mod h1:W4Qnvbt70Wk/zYJryRzDRU/4r0kIg0PVHBcfoyhpF5M=
github.com/hashicorp/go-retryablehttp v0.7.8 h1:ylXZWnqa7Lhqpk0L1P1LzDtGcCR0rPVUrx/c8Unxc48=
github.com/hashicorp/go-retryablehttp v0.7.8/go.mod h1:rjiScheydd+CxvumBsIrFKlx3iS0jrZ7LvzFGFmuKbw=
github.com/hashicorp/go-slug v0.16.8 h1:f4/sDZqRsxx006HrE6e9BE5xO9lWXydKhVoH6Kb0v1M=
github.com/hashicorp/go-slug v0.16.8/go.mod h1:hB4mUcVHl4RPu0205s0fwmB9i31MxQgeafGkko3FD+Y=
github.com/hashicorp/go-slug v0.18.1 h1:UnWIy4mq9GaDr1LhAzCPgA6RSQUn952RLFqQe3HPyCs=
github.com/hashicorp/go-slug v0.18.1/go.mod h1:Zxkkl8/LfXmhxZO3fLXQUCy3MVXAJK9pybY8WoDPgvs=
github.com/hashicorp/go-uuid v1.0.3 h1:2gKiV6YVmrJ1i2CKKa9obLvRieoRGviZFL26PcT/Co8=
github.com/hashicorp/go-uuid v1.0.3/go.mod h1:6SBZvOh/SIDV7/2o3Jml5SYk/TvGqwFJ/bN7x4byOro=
github.com/hashicorp/go-version v1.7.0 h1:5tqGy27NaOTB8yJKUZELlFAS/LTKJkrmONwQKeRZfjY=

View File

@@ -49,7 +49,7 @@ require (
github.com/google/uuid v1.6.0 // indirect
github.com/hashicorp/errwrap v1.1.0 // indirect
github.com/hashicorp/go-multierror v1.1.1 // indirect
github.com/hashicorp/go-slug v0.16.8 // indirect
github.com/hashicorp/go-slug v0.18.1 // indirect
github.com/hashicorp/go-version v1.7.0 // indirect
github.com/hashicorp/terraform-plugin-log v0.9.0 // indirect
github.com/hashicorp/terraform-registry-address v0.4.0 // indirect

View File

@@ -225,8 +225,8 @@ github.com/hashicorp/go-multierror v1.1.1 h1:H5DkEtf6CXdFp0N0Em5UCwQpXMWke8IA0+l
github.com/hashicorp/go-multierror v1.1.1/go.mod h1:iw975J/qwKPdAO1clOe2L8331t/9/fmwbPZ6JB6eMoM=
github.com/hashicorp/go-retryablehttp v0.7.8 h1:ylXZWnqa7Lhqpk0L1P1LzDtGcCR0rPVUrx/c8Unxc48=
github.com/hashicorp/go-retryablehttp v0.7.8/go.mod h1:rjiScheydd+CxvumBsIrFKlx3iS0jrZ7LvzFGFmuKbw=
github.com/hashicorp/go-slug v0.16.8 h1:f4/sDZqRsxx006HrE6e9BE5xO9lWXydKhVoH6Kb0v1M=
github.com/hashicorp/go-slug v0.16.8/go.mod h1:hB4mUcVHl4RPu0205s0fwmB9i31MxQgeafGkko3FD+Y=
github.com/hashicorp/go-slug v0.18.1 h1:UnWIy4mq9GaDr1LhAzCPgA6RSQUn952RLFqQe3HPyCs=
github.com/hashicorp/go-slug v0.18.1/go.mod h1:Zxkkl8/LfXmhxZO3fLXQUCy3MVXAJK9pybY8WoDPgvs=
github.com/hashicorp/go-uuid v1.0.3 h1:2gKiV6YVmrJ1i2CKKa9obLvRieoRGviZFL26PcT/Co8=
github.com/hashicorp/go-uuid v1.0.3/go.mod h1:6SBZvOh/SIDV7/2o3Jml5SYk/TvGqwFJ/bN7x4byOro=
github.com/hashicorp/go-version v1.7.0 h1:5tqGy27NaOTB8yJKUZELlFAS/LTKJkrmONwQKeRZfjY=

View File

@@ -21,7 +21,7 @@ require (
github.com/apparentlymart/go-versions v1.0.2 // indirect
github.com/bmatcuk/doublestar v1.1.5 // indirect
github.com/google/uuid v1.6.0 // indirect
github.com/hashicorp/go-slug v0.16.8 // indirect
github.com/hashicorp/go-slug v0.18.1 // indirect
github.com/hashicorp/go-uuid v1.0.3 // indirect
github.com/hashicorp/go-version v1.7.0 // indirect
github.com/hashicorp/hcl/v2 v2.24.0 // indirect

View File

@@ -133,8 +133,8 @@ github.com/googleapis/gax-go/v2 v2.0.5/go.mod h1:DWXyrwAJ9X0FpwwEdw+IPEYBICEFu5m
github.com/googleapis/google-cloud-go-testing v0.0.0-20200911160855-bcd43fbb19e8/go.mod h1:dvDLG8qkwmyD9a/MJJN3XJcT3xFxOKAvTZGvuZmac9g=
github.com/hashicorp/go-hclog v1.6.3 h1:Qr2kF+eVWjTiYmU7Y31tYlP1h0q/X3Nl3tPGdaB11/k=
github.com/hashicorp/go-hclog v1.6.3/go.mod h1:W4Qnvbt70Wk/zYJryRzDRU/4r0kIg0PVHBcfoyhpF5M=
github.com/hashicorp/go-slug v0.16.8 h1:f4/sDZqRsxx006HrE6e9BE5xO9lWXydKhVoH6Kb0v1M=
github.com/hashicorp/go-slug v0.16.8/go.mod h1:hB4mUcVHl4RPu0205s0fwmB9i31MxQgeafGkko3FD+Y=
github.com/hashicorp/go-slug v0.18.1 h1:UnWIy4mq9GaDr1LhAzCPgA6RSQUn952RLFqQe3HPyCs=
github.com/hashicorp/go-slug v0.18.1/go.mod h1:Zxkkl8/LfXmhxZO3fLXQUCy3MVXAJK9pybY8WoDPgvs=
github.com/hashicorp/go-uuid v1.0.3 h1:2gKiV6YVmrJ1i2CKKa9obLvRieoRGviZFL26PcT/Co8=
github.com/hashicorp/go-uuid v1.0.3/go.mod h1:6SBZvOh/SIDV7/2o3Jml5SYk/TvGqwFJ/bN7x4byOro=
github.com/hashicorp/go-version v1.7.0 h1:5tqGy27NaOTB8yJKUZELlFAS/LTKJkrmONwQKeRZfjY=

View File

@@ -369,7 +369,23 @@ func resolveFinalSourceAddr(base sourceaddrs.FinalSource, rel sourceaddrs.Source
}
underlyingSource = base.FinalSourceAddr(underlyingSource)
return sourceaddrs.ResolveRelativeFinalSource(underlyingSource, rel)
case sourceaddrs.ComponentSourceFinal:
ret, err := sourceaddrs.ResolveRelativeFinalSource(base, rel)
if err == nil {
return ret, nil
}
// If we can't resolve relative to the registry source then
// we need to resolve relative to its underlying remote source
// instead.
underlyingSource, ok := sources.ComponentPackageSourceAddr(base.Package(), base.SelectedVersion())
if !ok {
// If we also can't find the underlying source for some reason
// then we're stuck.
return nil, fmt.Errorf("can't find underlying source address for %s", base.Package())
}
underlyingSource = base.FinalSourceAddr(underlyingSource)
return sourceaddrs.ResolveRelativeFinalSource(underlyingSource, rel)
default:
// Easy case: this source type is already a final type
return sourceaddrs.ResolveRelativeFinalSource(base, rel)
@@ -391,6 +407,17 @@ func resolveFinalSourceAddr(base sourceaddrs.FinalSource, rel sourceaddrs.Source
}
finalRel := rel.Versioned(selectedVersion)
return sourceaddrs.ResolveRelativeFinalSource(base, finalRel)
case sourceaddrs.ComponentSource:
// Component registry sources work similar to module registry sources
allowedVersions := versions.MeetingConstraints(versionConstraints)
availableVersions := sources.ComponentPackageVersions(rel.Package())
selectedVersion := availableVersions.NewestInSet(allowedVersions)
if selectedVersion == versions.Unspecified {
return nil, fmt.Errorf("no cached versions of %s match the given version constraints", rel.Package())
}
finalRel := rel.Versioned(selectedVersion)
return sourceaddrs.ResolveRelativeFinalSource(base, finalRel)
default:
// Should not get here because the above cases should be exhaustive
// for all implementations of sourceaddrs.Source.

View File

@@ -284,3 +284,86 @@ func TestOmittingBuiltInProviders(t *testing.T) {
})
})
}
func TestComponentSourceResolution(t *testing.T) {
stackResourceName := "pet-nulls"
bundle, err := sourcebundle.OpenDir("testdata/embedded-stack-bundle")
if err != nil {
t.Fatal(err)
}
rootAddr := sourceaddrs.MustParseSource("git::https://example.com/root.git").(sourceaddrs.RemoteSource)
config, diags := LoadConfigDir(rootAddr, bundle)
if len(diags) != 0 {
t.Fatalf("unexpected diagnostics:\n%s", diags.NonFatalErr().Error())
}
t.Run("component source resolution", func(t *testing.T) {
// Verify that the component was loaded
if got, want := len(config.Root.Stack.EmbeddedStacks), 1; got != want {
t.Errorf("wrong number of components %d; want %d", got, want)
}
t.Run("pet-nulls component", func(t *testing.T) {
cmpn, ok := config.Root.Stack.EmbeddedStacks[stackResourceName]
if !ok {
t.Fatalf("Root stack config has no component named %q.", stackResourceName)
}
// Verify component name
if got, want := cmpn.Name, stackResourceName; got != want {
t.Errorf("wrong component name\ngot: %s\nwant: %s", got, want)
}
// Verify that the source address was parsed correctly
componentSource, ok := cmpn.SourceAddr.(sourceaddrs.ComponentSource)
if !ok {
t.Fatalf("expected ComponentSource, got %T", cmpn.SourceAddr)
}
expectedSourceStr := "example.com/awesomecorp/tfstack-pet-nulls"
if got := componentSource.String(); got != expectedSourceStr {
t.Errorf("wrong source address\ngot: %s\nwant: %s", got, expectedSourceStr)
}
// Verify that version constraints were parsed
if cmpn.VersionConstraints == nil {
t.Fatal("component has no version constraints")
}
// Verify that the final source address was resolved
if cmpn.FinalSourceAddr == nil {
t.Fatal("component FinalSourceAddr was not resolved")
}
// The final source should be a ComponentSourceFinal
componentSourceFinal, ok := cmpn.FinalSourceAddr.(sourceaddrs.ComponentSourceFinal)
if !ok {
t.Fatalf("expected ComponentSourceFinal for FinalSourceAddr, got %T", cmpn.FinalSourceAddr)
}
// Verify it resolved to the correct version (0.0.2)
expectedVersion := "0.0.2"
if got := componentSourceFinal.SelectedVersion().String(); got != expectedVersion {
t.Errorf("wrong selected version\ngot: %s\nwant: %s", got, expectedVersion)
}
// Verify the unversioned component source matches
if got := componentSourceFinal.Unversioned().String(); got != expectedSourceStr {
t.Errorf("wrong unversioned source in final address\ngot: %s\nwant: %s", got, expectedSourceStr)
}
// Verify we can get the local path from the bundle
localPath, err := bundle.LocalPathForSource(cmpn.FinalSourceAddr)
if err != nil {
t.Fatalf("failed to get local path for component source: %s", err)
}
// The local path should point to the pet-nulls directory
if localPath == "" {
t.Error("local path is empty")
}
t.Logf("Component resolved to local path: %s", localPath)
})
})
}

View File

@@ -45,4 +45,4 @@
}
}
]
}
}

View File

@@ -0,0 +1,17 @@
variable "name" {
type = string
}
resource "null_resource" "example" {
triggers = {
name = var.name
}
}
output "greeting" {
value = "Hello, ${var.name}!"
}
output "resource_id" {
value = null_resource.example.id
}

View File

@@ -0,0 +1,22 @@
required_providers {
null = {
source = "hashicorp/null"
version = "3.2.1"
}
}
variable "name" {
type = string
}
component "a" {
source = "./a"
inputs = {
name = var.name
}
providers = {
null = var.provider
}
}

View File

@@ -0,0 +1,24 @@
required_providers {
null = {
source = "hashicorp/null"
version = "3.2.1"
}
}
stack "pet-nulls" {
source = "example.com/awesomecorp/tfstack-pet-nulls"
version = "0.0.2"
inputs = {
name = var.name
provider = provider.null.a
}
}
provider "null" "a" {
}
locals {
sound = "bleep bloop"
}

View File

@@ -0,0 +1,29 @@
{
"terraform_source_bundle": 1,
"packages": [
{
"source": "git::https://example.com/root.git",
"local": "root",
"meta": {}
},
{
"source": "git::https://example.com/pet-nulls.git?ref=0.0.2",
"local": "component",
"meta": {}
}
],
"registry": [],
"components": [
{
"source": "example.com/awesomecorp/tfstack-pet-nulls",
"versions": {
"0.0.1": {
"source": "git::https://example.com/pet-nulls.git?ref=0.0.1"
},
"0.0.2": {
"source": "git::https://example.com/pet-nulls.git?ref=0.0.2"
}
}
}
]
}