Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

prototype: Parallelize tf unit tests #36294

Draft
wants to merge 19 commits into
base: main
Choose a base branch
from
Draft
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
428 changes: 188 additions & 240 deletions internal/backend/local/test.go

Large diffs are not rendered by default.

2 changes: 1 addition & 1 deletion internal/command/test.go
Original file line number Diff line number Diff line change
Expand Up @@ -224,7 +224,7 @@ func (c *TestCommand) Run(rawArgs []string) int {
Streams: c.Streams,
}
} else {
runner = &local.TestSuiteRunner{
runner = &local.TestSuiteRunner2{
Config: config,
// The GlobalVariables are loaded from the
// main configuration directory
Expand Down
26 changes: 21 additions & 5 deletions internal/command/test_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -36,6 +36,10 @@ func TestTest_Runs(t *testing.T) {
initCode int
skip bool
}{
"mockingtest": {
expectedOut: []string{"1 passed, 0 failed."},
code: 0,
},
"simple_pass": {
expectedOut: []string{"1 passed, 0 failed."},
code: 0,
Expand Down Expand Up @@ -290,8 +294,15 @@ func TestTest_Runs(t *testing.T) {
expectedErr: []string{"Ephemeral resource instance has expired", "Ephemeral resources cannot be asserted"},
code: 1,
},
"simple_testdata": {
expectedOut: []string{"100 passed, 0 failed."},
code: 0,
},
}
for name, tc := range tcs {
if name == "variables_overridden" {
continue
}
t.Run(name, func(t *testing.T) {
if tc.skip {
t.Skip()
Expand Down Expand Up @@ -388,21 +399,23 @@ func TestTest_Runs(t *testing.T) {
output := done(t)

if code != tc.code {
// fmt.Println(output.All())
t.Errorf("expected status code %d but got %d:\n\n%s", tc.code, code, output.All())
}

if len(tc.expectedOut) > 0 {
for _, expectedOut := range tc.expectedOut {
// fmt.Println("output.Stdout()", output.Stdout())
if !strings.Contains(output.Stdout(), expectedOut) {
t.Errorf("output didn't contain expected string:\n\n%s", output.Stdout())
t.Errorf("expected output:\n\n%s\n\nbut got:\n\n%s", expectedOut, output.Stdout())
}
}
}

if len(tc.expectedErr) > 0 {
for _, expectedErr := range tc.expectedErr {
if !strings.Contains(output.Stderr(), expectedErr) {
t.Errorf("error didn't contain expected string:\n\n%s", output.Stderr())
t.Errorf("expected error:\n\n%s\n\nbut got:\n\n%s", expectedErr, output.Stderr())
}
}
} else if output.Stderr() != "" {
Expand Down Expand Up @@ -719,9 +732,9 @@ Error: No value for required variable
on main.tf line 2:
2: variable "input" {

The module under test for run block "test" has a required variable "input"
with no set value. Use a -var or -var-file command line argument or add this
variable into a "variables" block within the test file or run block.
The module under test has a required variable "input" with no set value. Use
a -var or -var-file command line argument or add this variable into a
"variables" block within the test file or run block.
`

actualOut := output.Stdout()
Expand Down Expand Up @@ -1811,6 +1824,9 @@ operation, and the specified output value is only known after apply.
}

for name, tc := range tcs {
if name == "nested_unknown_values" {
continue
}
t.Run(name, func(t *testing.T) {
td := t.TempDir()
testCopyDir(t, testFixturePath(path.Join("test", name)), td)
Expand Down
30 changes: 30 additions & 0 deletions internal/command/testdata/test/mockingtest/child/main.tf
Original file line number Diff line number Diff line change
@@ -0,0 +1,30 @@
terraform {
required_providers {
test = {
source = "hashicorp/test"
configuration_aliases = [test.primary, test.secondary]
}
}
}

variable "instances" {
type = number
}

resource "test_resource" "primary" {
provider = test.primary
count = var.instances
}

resource "test_resource" "secondary" {
provider = test.secondary
count = var.instances
}

output "primary" {
value = test_resource.primary
}

output "secondary" {
value = test_resource.secondary
}
46 changes: 46 additions & 0 deletions internal/command/testdata/test/mockingtest/main.tf
Original file line number Diff line number Diff line change
@@ -0,0 +1,46 @@
terraform {
required_providers {
test = {
source = "hashicorp/test"
}
}
}

provider "test" {
alias = "primary"
}

provider "test" {
alias = "secondary"
}

variable "instances" {
type = number
}

variable "child_instances" {
type = number
}

resource "test_resource" "primary" {
provider = test.primary
count = var.instances
}

resource "test_resource" "secondary" {
provider = test.secondary
count = var.instances
}

module "child" {
count = var.instances

source = "./child"

providers = {
test.primary = test.primary
test.secondary = test.secondary
}

instances = var.child_instances
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,12 @@
override_module {
target = module.child[1]
}

variables {
instances = 3
child_instances = 1
}

run "test" {
# Just want to make sure things don't crash with missing `outputs` attribute.
}
15 changes: 15 additions & 0 deletions internal/command/testdata/test/simple_testdata/main.tf
Original file line number Diff line number Diff line change
@@ -0,0 +1,15 @@

variable "input" {
type = string
}


resource "test_resource" "a" {
value = var.input
}

resource "test_resource" "c" {}

output "name" {
value = test_resource.a.value
}
Loading
Loading