Skip to content

Commit

Permalink
setup playwright
Browse files Browse the repository at this point in the history
  • Loading branch information
sgalsaleh committed Apr 21, 2024
1 parent e2d71bc commit 5316fdb
Show file tree
Hide file tree
Showing 16 changed files with 277 additions and 42 deletions.
2 changes: 1 addition & 1 deletion .github/actions/kots-e2e/action.yml
Original file line number Diff line number Diff line change
Expand Up @@ -28,7 +28,7 @@ inputs:
required: false
testim-access-token:
description: 'Testim access token'
required: true
required: false
testim-branch:
description: 'Testim branch'
default: 'master'
Expand Down
3 changes: 2 additions & 1 deletion e2e/hack/Dockerfile → e2e/Dockerfile
Original file line number Diff line number Diff line change
Expand Up @@ -11,7 +11,8 @@ ENV INSTALL_DIR=/usr/local/bin
ENV KREW_ROOT=$INSTALL_DIR/krew
ENV PATH=$INSTALL_DIR/node_modules/.bin:$KREW_ROOT/bin:$PATH

COPY deps.sh /usr/local/bin/deps.sh
COPY ./playwright /playwright
COPY ./scripts/deps.sh /usr/local/bin/deps.sh

RUN /usr/local/bin/deps.sh

Expand Down
2 changes: 1 addition & 1 deletion e2e/Makefile
Original file line number Diff line number Diff line change
Expand Up @@ -10,7 +10,7 @@ all: build deps test

.PHONY: deps
deps:
docker build -t e2e-deps -f ./hack/Dockerfile ./hack
docker build -t e2e-deps .

.PHONY: build
build:
Expand Down
23 changes: 16 additions & 7 deletions e2e/e2e_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -16,19 +16,21 @@ import (
"github.com/onsi/gomega/gexec"
"github.com/replicatedhq/kots/e2e/cluster"
"github.com/replicatedhq/kots/e2e/helm"
"github.com/replicatedhq/kots/e2e/inventory"
"github.com/replicatedhq/kots/e2e/kots"
"github.com/replicatedhq/kots/e2e/kubectl"
"github.com/replicatedhq/kots/e2e/minio"
"github.com/replicatedhq/kots/e2e/playwright"
"github.com/replicatedhq/kots/e2e/prometheus"
"github.com/replicatedhq/kots/e2e/registry"
"github.com/replicatedhq/kots/e2e/testim"
"github.com/replicatedhq/kots/e2e/testim/inventory"
"github.com/replicatedhq/kots/e2e/util"
"github.com/replicatedhq/kots/e2e/velero"
"github.com/replicatedhq/kots/e2e/workspace"
)

var testimClient *testim.Client
var playwrightClient *playwright.Client
var helmCLI *helm.CLI
var veleroCLI *velero.CLI
var kotsInstaller *kots.Installer
Expand Down Expand Up @@ -73,9 +75,6 @@ func TestE2E(t *testing.T) {
}

var _ = BeforeSuite(func() {
testimAccessToken := os.Getenv("TESTIM_ACCESS_TOKEN")
Expect(testimAccessToken).ShouldNot(BeEmpty(), "TESTIM_ACCESS_TOKEN required")

Expect(util.CommandExists("kubectl")).To(BeTrue(), "kubectl required")
Expect(util.CommandExists("helm")).To(BeTrue(), "helm required")
Expect(util.CommandExists("velero")).To(BeTrue(), "velero required")
Expand All @@ -86,12 +85,14 @@ var _ = BeforeSuite(func() {
DeferCleanup(w.Teardown)

testimClient = testim.NewClient(
testimAccessToken,
os.Getenv("TESTIM_ACCESS_TOKEN"),
util.EnvOrDefault("TESTIM_PROJECT_ID", "wpYAooUimFDgQxY73r17"),
"Testim-grid",
testimBranch,
)

playwrightClient = playwright.NewClient()

helmCLI = helm.NewCLI(w.GetDir())

veleroCLI = velero.NewCLI(w.GetDir(), isOpenShift)
Expand Down Expand Up @@ -190,12 +191,20 @@ var _ = Describe("E2E", func() {
adminConsolePort = kotsInstaller.Install(c.GetKubeconfig(), test, kotsadmForwardPort)
}

GinkgoWriter.Println("Running E2E tests")

if playwrightClient.HasTest(test) {
playwrightRun := playwrightClient.NewRun(c.GetKubeconfig(), test, playwright.RunOptions{
Port: adminConsolePort,
})
playwrightRun.ShouldSucceed()
return
}

var testimParams inventory.TestimParams
if test.Setup != nil {
testimParams = test.Setup(kubectlCLI)
}

GinkgoWriter.Println("Running E2E tests")
testimRun = testimClient.NewRun(c.GetKubeconfig(), test, testim.RunOptions{
TunnelPort: adminConsolePort,
BaseUrl: testimBaseUrl,
Expand Down
27 changes: 0 additions & 27 deletions e2e/testim/inventory/inventory.go → e2e/inventory/inventory.go
Original file line number Diff line number Diff line change
@@ -1,12 +1,8 @@
package inventory

import (
"bytes"
"context"
"encoding/base64"
"fmt"
"io/ioutil"
"strings"
"time"

"github.com/onsi/gomega/gexec"
Expand Down Expand Up @@ -81,7 +77,6 @@ func NewNoRequiredConfig() Test {
Suite: "no-required-config",
Namespace: "no-required-config",
UpstreamURI: "no-required-config/automated",
Setup: SetupNoRequiredConfig,
}
}

Expand Down Expand Up @@ -199,28 +194,6 @@ func SetupRegressionTest(kubectlCLI *kubectl.CLI) TestimParams {
return nil
}

func SetupNoRequiredConfig(kubectlCLI *kubectl.CLI) TestimParams {
cmd := kubectlCLI.Command(
context.Background(),
"--namespace=no-required-config",
"get",
"secret",
"kotsadm-authstring",
`--template='{{ index .data "kotsadm-authstring" }}'`,
)
buf := bytes.NewBuffer(nil)
session, err := gexec.Start(cmd, buf, GinkgoWriter)
Expect(err).WithOffset(1).Should(Succeed(), "Get kotsadm-authstring secret failed")
Eventually(session).WithOffset(1).WithTimeout(30*time.Minute).Should(gexec.Exit(0), "Get kotsadm-authstring secret failed with non-zero exit code")

kotsadmAPIToken, err := base64.StdEncoding.DecodeString(strings.Trim(buf.String(), `"' `))
Expect(err).WithOffset(1).Should(Succeed(), "Decode kotsadm-authstring secret failed")

err = ioutil.WriteFile(".env", []byte(fmt.Sprintf("KOTSADM_API_TOKEN=%s", string(kotsadmAPIToken))), 0600)
Expect(err).WithOffset(1).Should(Succeed(), "Create .env file failed")
return nil
}

func SetupHelmManagedMode(kubectlCLI *kubectl.CLI) TestimParams {
return TestimParams{
"kotsadmPassword": HelmPassword,
Expand Down
File renamed without changes.
10 changes: 6 additions & 4 deletions e2e/kots/kots.go
Original file line number Diff line number Diff line change
Expand Up @@ -12,7 +12,7 @@ import (
. "github.com/onsi/gomega"
"github.com/onsi/gomega/gexec"
"github.com/pkg/errors"
"github.com/replicatedhq/kots/e2e/testim/inventory"
"github.com/replicatedhq/kots/e2e/inventory"
"github.com/replicatedhq/kots/e2e/util"
)

Expand Down Expand Up @@ -45,9 +45,11 @@ func (i *Installer) Install(kubeconfig string, test inventory.Test, adminConsole
Expect(err).WithOffset(1).Should(Succeed(), "Kots install failed")
Eventually(session).WithOffset(1).WithTimeout(InstallWaitDuration).Should(gexec.Exit(0), "Kots install failed with non-zero exit code")

session, err = i.ensureSecret(kubeconfig, test)
Expect(err).WithOffset(1).Should(Succeed(), "Kots docker ensure-secret failed")
Eventually(session).WithOffset(1).WithTimeout(InstallWaitDuration).Should(gexec.Exit(0), "Kots docker ensure-secret failed with non-zero exit code")
if i.dockerhubUsername != "" && i.dockerhubPassword != "" {
session, err = i.ensureSecret(kubeconfig, test)
Expect(err).WithOffset(1).Should(Succeed(), "Kots docker ensure-secret failed")
Eventually(session).WithOffset(1).WithTimeout(InstallWaitDuration).Should(gexec.Exit(0), "Kots docker ensure-secret failed with non-zero exit code")
}

return i.AdminConsolePortForward(kubeconfig, test, adminConsolePort)
}
Expand Down
5 changes: 5 additions & 0 deletions e2e/playwright/.gitignore
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
node_modules/
/test-results/
/playwright-report/
/blob-report/
/playwright/.cache/
91 changes: 91 additions & 0 deletions e2e/playwright/package-lock.json

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

14 changes: 14 additions & 0 deletions e2e/playwright/package.json
Original file line number Diff line number Diff line change
@@ -0,0 +1,14 @@
{
"name": "playwright",
"version": "1.0.0",
"description": "",
"main": "index.js",
"scripts": {},
"keywords": [],
"author": "",
"license": "ISC",
"devDependencies": {
"@playwright/test": "^1.43.1",
"@types/node": "^20.12.7"
}
}
40 changes: 40 additions & 0 deletions e2e/playwright/playwright.config.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,40 @@
import { defineConfig, devices } from '@playwright/test';

/**
* Read environment variables from file.
* https://github.com/motdotla/dotenv
*/
// require('dotenv').config();

/**
* See https://playwright.dev/docs/test-configuration.
*/
export default defineConfig({
testDir: './tests',
/* Run tests in files in parallel */
fullyParallel: true,
/* Fail the build on CI if you accidentally left test.only in the source code. */
forbidOnly: !!process.env.CI,
/* Retry on CI only */
retries: process.env.CI ? 2 : 0,
/* Opt out of parallel tests on CI. */
workers: process.env.CI ? 1 : undefined,
/* Reporter to use. See https://playwright.dev/docs/test-reporters */
reporter: 'line',
/* Shared settings for all the projects below. See https://playwright.dev/docs/api/class-testoptions. */
use: {
/* Base URL to use in actions like `await page.goto('/')`. */
baseURL: `http://localhost:${process.env.PORT || 8800}`,

/* Collect trace when retrying the failed test. See https://playwright.dev/docs/trace-viewer */
trace: 'on-first-retry',
},

/* Configure projects for major browsers */
projects: [
{
name: 'chromium',
use: { ...devices['Desktop Chrome'] },
},
],
});
58 changes: 58 additions & 0 deletions e2e/playwright/playwright.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,58 @@
package playwright

import (
"fmt"
"os"
"os/exec"
"time"

//lint:ignore ST1001 since Ginkgo and Gomega are DSLs this makes the tests more natural to read
. "github.com/onsi/gomega"
"github.com/onsi/gomega/gexec"
"github.com/replicatedhq/kots/e2e/inventory"
"github.com/replicatedhq/kots/e2e/util"
)

type Client struct {
}

type Run struct {
session *gexec.Session
}

type RunOptions struct {
Port string
}

func NewClient() *Client {
return &Client{}
}

func (t *Client) HasTest(test inventory.Test) bool {
_, err := os.Stat(fmt.Sprintf("/playwright/tests/%s", test.Suite))
return err == nil
}

func (t *Client) NewRun(kubeconfig string, test inventory.Test, runOptions RunOptions) *Run {
args := []string{
"playwright",
"test",
test.Suite,
}

cmd := exec.Command("npx", args...)
cmd.Dir = "/playwright"
cmd.Env = os.Environ()
cmd.Env = append(cmd.Env, fmt.Sprintf("KUBECONFIG=%s", kubeconfig))
cmd.Env = append(cmd.Env, fmt.Sprintf("PORT=%s", runOptions.Port))
cmd.Env = append(cmd.Env, fmt.Sprintf("NAMESPACE=%s", test.Namespace))
cmd.Env = append(cmd.Env, "NODE_OPTIONS=--max-old-space-size=4096")
session, err := util.RunCommand(cmd)
Expect(err).WithOffset(1).Should(Succeed(), "Run playwright test failed")
return &Run{session}
}

func (r *Run) ShouldSucceed() {
Eventually(r.session).WithOffset(1).WithTimeout(30*time.Minute).Should(gexec.Exit(), "Run playwright test timed out")
Expect(r.session.ExitCode()).Should(Equal(0), "Run playwright test failed with non-zero exit code")
}
Loading

0 comments on commit 5316fdb

Please sign in to comment.