vorteil/direktiv

View on GitHub
ui/e2e/gateway/routes/list/index.spec.ts

Summary

Maintainability
C
7 hrs
Test Coverage
import { createNamespace, deleteNamespace } from "e2e/utils/namespace";
import {
  createRouteFile,
  findRouteWithApiRequest,
  routeWithAWarning,
  routeWithAnError,
} from "../utils";
import { expect, test } from "@playwright/test";

import { createFile } from "e2e/utils/files";

let namespace = "";

test.beforeEach(async () => {
  namespace = await createNamespace();
});

test.afterEach(async () => {
  await deleteNamespace(namespace);
  namespace = "";
});

test("Route list is empty by default", async ({ page }) => {
  await page.goto(`/n/${namespace}/gateway/routes`, {
    waitUntil: "networkidle",
  });

  await expect(
    page.getByTestId("breadcrumb-routes"),
    "it renders the 'Routes' breadcrumb"
  ).toBeVisible();

  await expect(
    page.getByText("No routes exist yet"),
    "it renders an empty list of routes"
  ).toBeVisible();
});

test("Route list shows all available routes", async ({ page }) => {
  const path = "newPath";
  await createFile({
    name: "my-route.yaml",
    namespace,
    type: "endpoint",
    yaml: createRouteFile({
      path,
      targetType: "instant-response",
      targetConfigurationStatus: "202",
    }),
  });

  await expect
    .poll(
      async () =>
        await findRouteWithApiRequest({
          namespace,
          match: (route) => route.file_path === "/my-route.yaml",
        }),
      "the route was created and is available"
    )
    .toBeTruthy();

  await page.goto(`/n/${namespace}/gateway/routes`, {
    waitUntil: "networkidle",
  });

  await expect(
    page.getByTestId("route-table").locator("tr"),
    "it renders one row of routes"
  ).toHaveCount(1);

  await expect(
    page
      .getByTestId("route-table")
      .getByRole("link", { name: "/my-route.yaml" }),
    "it renders the text for the file path"
  ).toBeVisible();

  await expect(
    page.getByTestId("route-table").getByRole("textbox"),
    "it renders the text for the path"
  ).toHaveValue(
    `${process.env.PLAYWRIGHT_UI_BASE_URL}/ns/${namespace}/${path}`
  );

  await expect(
    page.getByTestId("route-table").getByText("GET", { exact: true }),
    "it renders the text for the method"
  ).toBeVisible();

  await page.getByTestId("route-table").getByText("+7").hover();

  await expect(
    page
      .getByTestId("route-table")
      .getByText("OPTIONSPUTPOSTHEADCONNECTPATCHTRACE"),
    'it shows more methods when hovering over the "+7"'
  ).toBeVisible();

  // hover over somethiing else to make the overlay disappear
  await page.getByTestId("route-table").getByText("yes").hover();

  await expect(
    page.getByTestId("route-table").getByRole("cell", { name: "1 plugin" }),
    "it renders the correct number for plugins"
  ).toBeVisible();

  await page
    .getByTestId("route-table")
    .getByRole("cell", { name: "1 plugin" })
    .hover();

  await expect(
    page.getByTestId("route-table").getByText("1 target plugin"),
    "it shows the plugin details on hover"
  ).toBeVisible();

  await expect(
    page.getByTestId("route-table").getByText("yes"),
    "it renders the correct label for 'allow anonymous'"
  ).toBeVisible();
});

test("Route list shows an error on no target plugin", async ({ page }) => {
  await createFile({
    name: "my-route.yaml",
    namespace,
    type: "endpoint",
    yaml: routeWithAWarning,
  });

  await expect
    .poll(
      async () =>
        await findRouteWithApiRequest({
          namespace,
          match: (route) => route.file_path === "/my-route.yaml",
        }),
      "the route was created and is available"
    )
    .toBeTruthy();

  await page.goto(`/n/${namespace}/gateway/routes`, {
    waitUntil: "networkidle",
  });

  await expect(
    page.getByTestId("route-table").locator("tr"),
    "it renders one row of routes"
  ).toBeVisible();

  await expect(
    page.locator("a").filter({ hasText: "1 error" }),
    "there is a link with 1 error"
  ).toHaveText("1 error");

  await page.locator("a").filter({ hasText: "1 error" }).hover();

  await expect(
    page.getByTestId("route-table").getByText("no target plugin found"),
    "it shows the warning details on hover"
  ).toBeVisible();
});

test("Route list shows an error", async ({ page }) => {
  await createFile({
    name: "my-route.yaml",
    namespace,
    type: "endpoint",
    yaml: routeWithAnError,
  });

  await expect
    .poll(
      async () =>
        await findRouteWithApiRequest({
          namespace,
          match: (route) => route.file_path === "/my-route.yaml",
        }),
      "the route was created and is available"
    )
    .toBeTruthy();

  await page.goto(`/n/${namespace}/gateway/routes`, {
    waitUntil: "networkidle",
  });

  await expect(
    page.getByTestId("route-table").locator("tr"),
    "it renders one row of routes"
  ).toHaveCount(1);

  await expect(
    page.getByTestId("route-table").locator("a").filter({ hasText: "1 error" }),
    "there is a link with 1 error"
  ).toBeVisible();

  await page
    .getByTestId("route-table")
    .locator("a")
    .filter({ hasText: "1 error" })
    .hover();

  await expect(
    page
      .getByTestId("route-table")
      .getByText("plugin 'this-plugin-does-not-exist' err: doesn't exist"),
    "it shows the error detail on hover"
  ).toBeVisible();
});

test("Route list links the file name to the route file", async ({ page }) => {
  await createFile({
    name: "my-route.yaml",
    namespace,
    type: "endpoint",
    yaml: createRouteFile(),
  });

  await page.goto(`/n/${namespace}/gateway/routes`, {
    waitUntil: "networkidle",
  });

  await page
    .getByTestId("route-table")
    .getByRole("link", { name: "/my-route.yaml" })
    .click();

  await expect(
    page,
    "after clicking on the file name, the user gets redirected to the file explorer page of the service file"
  ).toHaveURL(`/n/${namespace}/explorer/endpoint/my-route.yaml`);
});