diff --git a/site/src/content/docs/contribute/testing.mdx b/site/src/content/docs/contribute/testing.mdx index ffaf3b8579..62252a12d7 100644 --- a/site/src/content/docs/contribute/testing.mdx +++ b/site/src/content/docs/contribute/testing.mdx @@ -6,15 +6,17 @@ Currently, we primarily test Zarf through a series of [end-to-end tests](https:/ In addition, Zarf implements unit tests for specific functions where edge cases prove difficult to cover through end-to-end testing alone. Unit tests follow standard Go convention and are `*_test.go` files. -## Dependencies +## Dependencies # TODO: update any more dependencies To run the end-to-end tests locally, you must meet the same prerequisites as those required for building and running Zarf, which include: 1. GoLang version >= the version specified in the [go.mod](https://github.com/zarf-dev/zarf/blob/main/go.mod) 2. Make -3. Any clean K8s cluster (local or remote) or Linux with `root` if you want to use the Zarf-installed K3s cluster +3. Docker +4. Docker Buildx +5. Any clean K8s cluster (local or remote) or Linux with `root` if you want to use the Zarf-installed K3s cluster -## Unit Tests +## Unit Tests # TODO: DONE these have been tested on mac and linux so this section is GTG There are several ways to run tests depending on your specific situation, such as: @@ -22,14 +24,19 @@ There are several ways to run tests depending on your specific situation, such a # The default way, from the root directory of the repo. Will run all of the unit tests that are currently defined. make test-unit +# To get a single-line readable summary of all the unit tests currently defined: +make test-unit 2>&1 | grep -E "^(ok|FAIL)\s" + # If you already have everything built, you can run this inside this folder. This lets you customize the test run. go test ./src/pkg/... -v -# Let's say you only want to run one test. You would run: +# To run a single test: go test ./src/pkg/... -v -run TestFooBarBaz ``` -### Adding New Unit Tests +All unit tests should pass locally before submitting a PR. + +### Adding New Unit Tests # TODO: make new unit test and test instructions To create a unit test, search for or create a file that ends with `_test.go` in the package of the file that requires testing, such as `auth.go` -> `auth_test.go`. Import the testing library and create test functions as necessary. Generic unit test helper functions can be found in [src/test/testutil](https://github.com/zarf-dev/zarf/tree/main/src/test/testutil). @@ -51,10 +58,13 @@ There are several ways to run tests depending on your specific situation, such a # The default way, from the root directory of the repo. Will run all of the tests against your chosen k8s distro. Will automatically build any binary dependencies that don't already exist. make test-e2e ARCH="[amd64|arm64]" -# To test against a Zarf-created cluster (on Linux with sudo) -APPLIANCE_MODE=true make test-e2e ARCH="[amd64|arm64]" +# To get a single-line readable summary of all the e2e tests currently defined: +cd src/test/e2e && go test ./main_test.go ./[01]* -failfast -v -timeout 35m 2>&1 | grep -E "^(--- FAIL|--- PASS|FAIL|ok)" + +# To test against a Zarf-created cluster (Linux only with sudo, not compatible with macOS) +APPLIANCE_MODE=true make test-e2e ARCH="amd64" -# If you already have everything build, you can run this inside this folder. This lets you customize the test run. +# If you already have everything built, you can run this inside this folder. This lets you customize the test run. go test ./src/test/... -v -failfast -count=1 # Let's say you only want to run one test. You would run: @@ -146,3 +156,23 @@ The end-to-end tests are run sequentially and the naming convention is set inten - 22 is reserved for tests required the git-server, which is removed at the end of the test. - 23-98 are for the remaining tests that only require a basic Zarf cluster without the git-server. - 99 is reserved for the `zarf destroy` and [YOLO Mode](/ref/examples/yolo/) test. + +### Troubleshooting ### + +Potential e2e testing errors and causes: +Docker/Buildx: + +`unknown flag: --load` → Buildx not installed or broken symlink + +Cluster: + +dial tcp [::1]:8080: connect: connection refused → No cluster configured or kubeconfig not set +error loading config file: duplicate name in list → Duplicate entries in ~/.kube/config + +Git/1Password: + +error: 1Password: Could not connect to socket → 1Password closed during rebase commit signing + +Architecture: + +no compatible component named k3s found → Either wrong ARCH value or trying to run Linux-only components on macOS diff --git a/src/test/e2e/main_test.go b/src/test/e2e/main_test.go index 50ec10291d..4d085b3ba2 100644 --- a/src/test/e2e/main_test.go +++ b/src/test/e2e/main_test.go @@ -5,13 +5,18 @@ package test import ( + "context" "log" "os" "path/filepath" + "runtime" "testing" "github.com/zarf-dev/zarf/src/config" + "github.com/zarf-dev/zarf/src/pkg/logger" + "github.com/zarf-dev/zarf/src/pkg/utils/exec" "github.com/zarf-dev/zarf/src/test" + // "github.com/zarf-dev/zarf/src/pkg/utils/exec" ) var ( @@ -45,5 +50,45 @@ func TestMain(m *testing.M) { if _, err := os.Stat(e2e.ZarfBinPath); err != nil { log.Fatalf("zarf binary %s not found: %v", e2e.ZarfBinPath, err) } + + // If APPLIANCE_MODE set to true, warn Mac user and run only non-cluster tests + if e2e.ApplianceMode && runtime.GOOS != "linux" { + cfg := logger.Config{ + Level: logger.Info, + Format: logger.FormatConsole, + Destination: logger.DestinationDefault, + Color: true, + } + l, err := logger.New(cfg) + if err != nil { + log.Fatal(err) + } + l.Warn("APPLIANCE_MODE=true is only fully supported on Linux. " + + "On macOS, only tests that do not require a cluster will run. " + + "To run with-cluster tests on macOS, create a local cluster first " + + "and run make test-e2e-with-cluster ARCH=arm64 instead.") + } + + // If not in appliance mode, check for cluster connectivity + // If no cluster is found, warn that only without-cluster tests will run + if !e2e.ApplianceMode { + _, _, err := exec.CmdWithContext(context.Background(), exec.Config{}, e2e.ZarfBinPath, "tools", "kubectl", "cluster-info") + if err != nil { + cfg := logger.Config{ + Level: logger.Warn, + Format: logger.FormatConsole, + Destination: logger.DestinationDefault, + Color: true, + } + l, logErr := logger.New(cfg) + if logErr != nil { + log.Fatal(logErr) + } + l.Warn("No cluster found - with-cluster tests will fail. " + + "To run only tests that do not require a cluster use: make test-e2e-without-cluster. " + + "To run with-cluster tests, ensure a valid cluster is running.") + } + } + os.Exit(m.Run()) }