mirror of
https://github.com/TriliumNext/Notes.git
synced 2025-07-27 10:02:59 +08:00
Merge pull request #1006 from TriliumNext/chore_move-test-files
chore: clean up and move test files next to actual files
This commit is contained in:
commit
9025516806
@ -1,5 +0,0 @@
|
||||
import { describe, it } from "vitest";
|
||||
|
||||
describe.todo("Notes", () => {
|
||||
it("zzz", () => {});
|
||||
});
|
@ -1,5 +1,5 @@
|
||||
import { describe, it, expect } from "vitest";
|
||||
import attributeParser from "../src/public/app/services/attribute_parser.ts";
|
||||
import attributeParser from "./attribute_parser.js";
|
||||
|
||||
|
||||
describe("Lexing", () => {
|
||||
@ -41,7 +41,9 @@ describe("Lexing", () => {
|
||||
});
|
||||
|
||||
describe.todo("Parser", () => {
|
||||
/* #TODO
|
||||
it("simple label", () => {
|
||||
|
||||
const attrs = attributeParser.parse(["#token"].map((t: any) => ({ text: t })));
|
||||
|
||||
expect(attrs.length).toEqual(1);
|
||||
@ -85,6 +87,7 @@ describe.todo("Parser", () => {
|
||||
expect(attrs[0].name).toEqual("token");
|
||||
expect(attrs[0].value).toEqual("NFi2gL4xtPxM");
|
||||
});
|
||||
*/
|
||||
});
|
||||
|
||||
describe("error cases", () => {
|
@ -1,6 +1,6 @@
|
||||
import { describe, it, expect, beforeEach, vi } from "vitest";
|
||||
|
||||
import type { getTriliumDataDir as getTriliumDataDirType, getDataDirs as getDataDirsType, getPlatformAppDataDir as getPlatformAppDataDirType } from "../src/services/data_dir";
|
||||
import type { getTriliumDataDir as getTriliumDataDirType, getDataDirs as getDataDirsType, getPlatformAppDataDir as getPlatformAppDataDirType } from "./data_dir.js";
|
||||
|
||||
describe("data_dir.ts unit tests", async () => {
|
||||
let getTriliumDataDir: typeof getTriliumDataDirType;
|
||||
@ -42,9 +42,9 @@ describe("data_dir.ts unit tests", async () => {
|
||||
});
|
||||
|
||||
// import function to test now, after creating the mocks
|
||||
({ getTriliumDataDir } = await import("../src/services/data_dir.ts"));
|
||||
({ getPlatformAppDataDir } = await import("../src/services/data_dir.ts"));
|
||||
({ getDataDirs } = await import("../src/services/data_dir.ts"));
|
||||
({ getTriliumDataDir } = await import("./data_dir.js"));
|
||||
({ getPlatformAppDataDir } = await import("./data_dir.js"));
|
||||
({ getDataDirs } = await import("./data_dir.js"));
|
||||
|
||||
// helper to reset call counts
|
||||
const resetAllMocks = () => {
|
||||
@ -287,7 +287,7 @@ describe("data_dir.ts unit tests", async () => {
|
||||
const result = getDataDirs(`${mockValuePrefix}_TRILIUM_DATA_DIR`);
|
||||
|
||||
for (const key in result) {
|
||||
expect(result[key]).toEqual(`${mockValuePrefix}_${key}`);
|
||||
expect(result[key as keyof typeof result]).toEqual(`${mockValuePrefix}_${key}`);
|
||||
}
|
||||
});
|
||||
|
||||
@ -302,7 +302,7 @@ describe("data_dir.ts unit tests", async () => {
|
||||
const result = getDataDirs(mockDataDir);
|
||||
|
||||
for (const key in result) {
|
||||
expect(result[key].startsWith(mockDataDir)).toBeTruthy();
|
||||
expect(result[key as keyof typeof result].startsWith(mockDataDir)).toBeTruthy();
|
||||
}
|
||||
|
||||
mockFn.pathJoinMock.mockReset();
|
||||
@ -335,7 +335,7 @@ describe("data_dir.ts unit tests", async () => {
|
||||
if (typeof changeAttemptResult === "string") {
|
||||
// if it didn't throw above: assert that it did not change the value of it or any other keys of the object
|
||||
for (const key in result) {
|
||||
expect(result[key].startsWith(mockDataDirBase)).toBeTruthy();
|
||||
expect(result[key as keyof typeof result].startsWith(mockDataDirBase)).toBeTruthy();
|
||||
}
|
||||
} else {
|
||||
expect(changeAttemptResult).toBeInstanceOf(TypeError);
|
@ -1,5 +1,5 @@
|
||||
import { expect, describe, it } from "vitest";
|
||||
import sanitizeAttributeName from "../src/services/sanitize_attribute_name";
|
||||
import sanitizeAttributeName from "./sanitize_attribute_name.js";
|
||||
|
||||
// fn value, expected value
|
||||
const testCases: [fnValue: string, expectedValue: string][] = [
|
@ -1,6 +1,6 @@
|
||||
import { describe, it, expect } from "vitest";
|
||||
import handleParens from "../../src/services/search/services/handle_parens.js";
|
||||
import type { TokenStructure } from "../../src/services/search/services/types.js";
|
||||
import handleParens from "./handle_parens.js";
|
||||
import type { TokenStructure } from "./types.js";
|
||||
|
||||
describe("Parens handler", () => {
|
||||
it("handles parens", () => {
|
@ -1,5 +1,5 @@
|
||||
import { describe, it, expect } from "vitest";
|
||||
import lex from "../../src/services/search/services/lex.js";
|
||||
import lex from "./lex.js";
|
||||
|
||||
describe("Lexer fulltext", () => {
|
||||
it("simple lexing", () => {
|
@ -1,16 +1,16 @@
|
||||
import { describe, it, expect } from "vitest";
|
||||
import AndExp from "../../src/services/search/expressions/and.js";
|
||||
import AttributeExistsExp from "../../src/services/search/expressions/attribute_exists.js";
|
||||
import type Expression from "../../src/services/search/expressions/expression.js";
|
||||
import LabelComparisonExp from "../../src/services/search/expressions/label_comparison.js";
|
||||
import NotExp from "../../src/services/search/expressions/not.js";
|
||||
import NoteContentFulltextExp from "../../src/services/search/expressions/note_content_fulltext.js";
|
||||
import NoteFlatTextExp from "../../src/services/search/expressions/note_flat_text.js";
|
||||
import OrExp from "../../src/services/search/expressions/or.js";
|
||||
import OrderByAndLimitExp from "../../src/services/search/expressions/order_by_and_limit.js";
|
||||
import PropertyComparisonExp from "../../src/services/search/expressions/property_comparison.js";
|
||||
import SearchContext from "../../src/services/search/search_context.js";
|
||||
import { default as parseInternal, type ParseOpts } from "../../src/services/search/services/parse.js";
|
||||
import AndExp from "../../search/expressions/and.js";
|
||||
import AttributeExistsExp from "../../search/expressions/attribute_exists.js";
|
||||
import type Expression from "../../search/expressions/expression.js";
|
||||
import LabelComparisonExp from "../../search/expressions/label_comparison.js";
|
||||
import NotExp from "../../search/expressions/not.js";
|
||||
import NoteContentFulltextExp from "../../search/expressions/note_content_fulltext.js";
|
||||
import NoteFlatTextExp from "../../search/expressions/note_flat_text.js";
|
||||
import OrExp from "../../search/expressions/or.js";
|
||||
import OrderByAndLimitExp from "../../search/expressions/order_by_and_limit.js";
|
||||
import PropertyComparisonExp from "../../search/expressions/property_comparison.js";
|
||||
import SearchContext from "../../search/search_context.js";
|
||||
import { default as parseInternal, type ParseOpts } from "./parse.js";
|
||||
|
||||
describe("Parser", () => {
|
||||
it("fulltext parser without content", () => {
|
@ -1,11 +1,11 @@
|
||||
import { describe, it, expect, beforeEach, } from "vitest";
|
||||
import searchService from "../../src/services/search/services/search.js";
|
||||
import BNote from "../../src/becca/entities/bnote.js";
|
||||
import BBranch from "../../src/becca/entities/bbranch.js";
|
||||
import SearchContext from "../../src/services/search/search_context.js";
|
||||
import dateUtils from "../../src/services/date_utils.js";
|
||||
import becca from "../../src/becca/becca.js";
|
||||
import becca_mocking from "./becca_mocking.js";
|
||||
import searchService from "./search.js";
|
||||
import BNote from "../../../becca/entities/bnote.js";
|
||||
import BBranch from "../../../becca/entities/bbranch.js";
|
||||
import SearchContext from "../search_context.js";
|
||||
import dateUtils from "../../date_utils.js";
|
||||
import becca from "../../../becca/becca.js";
|
||||
import becca_mocking from "../../../../spec/support/becca_mocking.js";
|
||||
|
||||
describe("Search", () => {
|
||||
let rootNote: any;
|
@ -1,8 +1,8 @@
|
||||
import { describe, it, expect, beforeEach } from "vitest";
|
||||
import becca_mocking from "./becca_mocking.js";
|
||||
import ValueExtractor from "../../src/services/search/value_extractor.js";
|
||||
import becca from "../../src/becca/becca.js";
|
||||
import SearchContext from "../../src/services/search/search_context.js";
|
||||
import becca_mocking from "../../../spec/support/becca_mocking.js";
|
||||
import ValueExtractor from "./value_extractor.js";
|
||||
import becca from "../../becca/becca.js";
|
||||
import SearchContext from "./search_context.js";
|
||||
|
||||
const dsc = new SearchContext();
|
||||
|
@ -1,5 +1,5 @@
|
||||
import { expect, describe, it } from "vitest";
|
||||
import { formatDownloadTitle } from "../../src/services/utils.ts";
|
||||
import { formatDownloadTitle } from "./utils.js";
|
||||
|
||||
const testCases: [fnValue: Parameters<typeof formatDownloadTitle>, expectedValue: ReturnType<typeof formatDownloadTitle>][] = [
|
||||
// empty fileName tests
|
@ -1,416 +0,0 @@
|
||||
import { test, expect, type Page } from "@playwright/test";
|
||||
|
||||
test.beforeEach(async ({ page }) => {
|
||||
await page.goto("https://demo.playwright.dev/todomvc");
|
||||
});
|
||||
|
||||
const TODO_ITEMS = ["buy some cheese", "feed the cat", "book a doctors appointment"] as const;
|
||||
|
||||
test.describe("New Todo", () => {
|
||||
test("should allow me to add todo items", async ({ page }) => {
|
||||
// create a new todo locator
|
||||
const newTodo = page.getByPlaceholder("What needs to be done?");
|
||||
|
||||
// Create 1st todo.
|
||||
await newTodo.fill(TODO_ITEMS[0]);
|
||||
await newTodo.press("Enter");
|
||||
|
||||
// Make sure the list only has one todo item.
|
||||
await expect(page.getByTestId("todo-title")).toHaveText([TODO_ITEMS[0]]);
|
||||
|
||||
// Create 2nd todo.
|
||||
await newTodo.fill(TODO_ITEMS[1]);
|
||||
await newTodo.press("Enter");
|
||||
|
||||
// Make sure the list now has two todo items.
|
||||
await expect(page.getByTestId("todo-title")).toHaveText([TODO_ITEMS[0], TODO_ITEMS[1]]);
|
||||
|
||||
await checkNumberOfTodosInLocalStorage(page, 2);
|
||||
});
|
||||
|
||||
test("should clear text input field when an item is added", async ({ page }) => {
|
||||
// create a new todo locator
|
||||
const newTodo = page.getByPlaceholder("What needs to be done?");
|
||||
|
||||
// Create one todo item.
|
||||
await newTodo.fill(TODO_ITEMS[0]);
|
||||
await newTodo.press("Enter");
|
||||
|
||||
// Check that input is empty.
|
||||
await expect(newTodo).toBeEmpty();
|
||||
await checkNumberOfTodosInLocalStorage(page, 1);
|
||||
});
|
||||
|
||||
test("should append new items to the bottom of the list", async ({ page }) => {
|
||||
// Create 3 items.
|
||||
await createDefaultTodos(page);
|
||||
|
||||
// create a todo count locator
|
||||
const todoCount = page.getByTestId("todo-count");
|
||||
|
||||
// Check test using different methods.
|
||||
await expect(page.getByText("3 items left")).toBeVisible();
|
||||
await expect(todoCount).toHaveText("3 items left");
|
||||
await expect(todoCount).toContainText("3");
|
||||
await expect(todoCount).toHaveText(/3/);
|
||||
|
||||
// Check all items in one call.
|
||||
await expect(page.getByTestId("todo-title")).toHaveText(TODO_ITEMS);
|
||||
await checkNumberOfTodosInLocalStorage(page, 3);
|
||||
});
|
||||
});
|
||||
|
||||
test.describe("Mark all as completed", () => {
|
||||
test.beforeEach(async ({ page }) => {
|
||||
await createDefaultTodos(page);
|
||||
await checkNumberOfTodosInLocalStorage(page, 3);
|
||||
});
|
||||
|
||||
test.afterEach(async ({ page }) => {
|
||||
await checkNumberOfTodosInLocalStorage(page, 3);
|
||||
});
|
||||
|
||||
test("should allow me to mark all items as completed", async ({ page }) => {
|
||||
// Complete all todos.
|
||||
await page.getByLabel("Mark all as complete").check();
|
||||
|
||||
// Ensure all todos have 'completed' class.
|
||||
await expect(page.getByTestId("todo-item")).toHaveClass(["completed", "completed", "completed"]);
|
||||
await checkNumberOfCompletedTodosInLocalStorage(page, 3);
|
||||
});
|
||||
|
||||
test("should allow me to clear the complete state of all items", async ({ page }) => {
|
||||
const toggleAll = page.getByLabel("Mark all as complete");
|
||||
// Check and then immediately uncheck.
|
||||
await toggleAll.check();
|
||||
await toggleAll.uncheck();
|
||||
|
||||
// Should be no completed classes.
|
||||
await expect(page.getByTestId("todo-item")).toHaveClass(["", "", ""]);
|
||||
});
|
||||
|
||||
test("complete all checkbox should update state when items are completed / cleared", async ({ page }) => {
|
||||
const toggleAll = page.getByLabel("Mark all as complete");
|
||||
await toggleAll.check();
|
||||
await expect(toggleAll).toBeChecked();
|
||||
await checkNumberOfCompletedTodosInLocalStorage(page, 3);
|
||||
|
||||
// Uncheck first todo.
|
||||
const firstTodo = page.getByTestId("todo-item").nth(0);
|
||||
await firstTodo.getByRole("checkbox").uncheck();
|
||||
|
||||
// Reuse toggleAll locator and make sure its not checked.
|
||||
await expect(toggleAll).not.toBeChecked();
|
||||
|
||||
await firstTodo.getByRole("checkbox").check();
|
||||
await checkNumberOfCompletedTodosInLocalStorage(page, 3);
|
||||
|
||||
// Assert the toggle all is checked again.
|
||||
await expect(toggleAll).toBeChecked();
|
||||
});
|
||||
});
|
||||
|
||||
test.describe("Item", () => {
|
||||
test("should allow me to mark items as complete", async ({ page }) => {
|
||||
// create a new todo locator
|
||||
const newTodo = page.getByPlaceholder("What needs to be done?");
|
||||
|
||||
// Create two items.
|
||||
for (const item of TODO_ITEMS.slice(0, 2)) {
|
||||
await newTodo.fill(item);
|
||||
await newTodo.press("Enter");
|
||||
}
|
||||
|
||||
// Check first item.
|
||||
const firstTodo = page.getByTestId("todo-item").nth(0);
|
||||
await firstTodo.getByRole("checkbox").check();
|
||||
await expect(firstTodo).toHaveClass("completed");
|
||||
|
||||
// Check second item.
|
||||
const secondTodo = page.getByTestId("todo-item").nth(1);
|
||||
await expect(secondTodo).not.toHaveClass("completed");
|
||||
await secondTodo.getByRole("checkbox").check();
|
||||
|
||||
// Assert completed class.
|
||||
await expect(firstTodo).toHaveClass("completed");
|
||||
await expect(secondTodo).toHaveClass("completed");
|
||||
});
|
||||
|
||||
test("should allow me to un-mark items as complete", async ({ page }) => {
|
||||
// create a new todo locator
|
||||
const newTodo = page.getByPlaceholder("What needs to be done?");
|
||||
|
||||
// Create two items.
|
||||
for (const item of TODO_ITEMS.slice(0, 2)) {
|
||||
await newTodo.fill(item);
|
||||
await newTodo.press("Enter");
|
||||
}
|
||||
|
||||
const firstTodo = page.getByTestId("todo-item").nth(0);
|
||||
const secondTodo = page.getByTestId("todo-item").nth(1);
|
||||
const firstTodoCheckbox = firstTodo.getByRole("checkbox");
|
||||
|
||||
await firstTodoCheckbox.check();
|
||||
await expect(firstTodo).toHaveClass("completed");
|
||||
await expect(secondTodo).not.toHaveClass("completed");
|
||||
await checkNumberOfCompletedTodosInLocalStorage(page, 1);
|
||||
|
||||
await firstTodoCheckbox.uncheck();
|
||||
await expect(firstTodo).not.toHaveClass("completed");
|
||||
await expect(secondTodo).not.toHaveClass("completed");
|
||||
await checkNumberOfCompletedTodosInLocalStorage(page, 0);
|
||||
});
|
||||
|
||||
test("should allow me to edit an item", async ({ page }) => {
|
||||
await createDefaultTodos(page);
|
||||
|
||||
const todoItems = page.getByTestId("todo-item");
|
||||
const secondTodo = todoItems.nth(1);
|
||||
await secondTodo.dblclick();
|
||||
await expect(secondTodo.getByRole("textbox", { name: "Edit" })).toHaveValue(TODO_ITEMS[1]);
|
||||
await secondTodo.getByRole("textbox", { name: "Edit" }).fill("buy some sausages");
|
||||
await secondTodo.getByRole("textbox", { name: "Edit" }).press("Enter");
|
||||
|
||||
// Explicitly assert the new text value.
|
||||
await expect(todoItems).toHaveText([TODO_ITEMS[0], "buy some sausages", TODO_ITEMS[2]]);
|
||||
await checkTodosInLocalStorage(page, "buy some sausages");
|
||||
});
|
||||
});
|
||||
|
||||
test.describe("Editing", () => {
|
||||
test.beforeEach(async ({ page }) => {
|
||||
await createDefaultTodos(page);
|
||||
await checkNumberOfTodosInLocalStorage(page, 3);
|
||||
});
|
||||
|
||||
test("should hide other controls when editing", async ({ page }) => {
|
||||
const todoItem = page.getByTestId("todo-item").nth(1);
|
||||
await todoItem.dblclick();
|
||||
await expect(todoItem.getByRole("checkbox")).not.toBeVisible();
|
||||
await expect(
|
||||
todoItem.locator("label", {
|
||||
hasText: TODO_ITEMS[1]
|
||||
})
|
||||
).not.toBeVisible();
|
||||
await checkNumberOfTodosInLocalStorage(page, 3);
|
||||
});
|
||||
|
||||
test("should save edits on blur", async ({ page }) => {
|
||||
const todoItems = page.getByTestId("todo-item");
|
||||
await todoItems.nth(1).dblclick();
|
||||
await todoItems.nth(1).getByRole("textbox", { name: "Edit" }).fill("buy some sausages");
|
||||
await todoItems.nth(1).getByRole("textbox", { name: "Edit" }).dispatchEvent("blur");
|
||||
|
||||
await expect(todoItems).toHaveText([TODO_ITEMS[0], "buy some sausages", TODO_ITEMS[2]]);
|
||||
await checkTodosInLocalStorage(page, "buy some sausages");
|
||||
});
|
||||
|
||||
test("should trim entered text", async ({ page }) => {
|
||||
const todoItems = page.getByTestId("todo-item");
|
||||
await todoItems.nth(1).dblclick();
|
||||
await todoItems.nth(1).getByRole("textbox", { name: "Edit" }).fill(" buy some sausages ");
|
||||
await todoItems.nth(1).getByRole("textbox", { name: "Edit" }).press("Enter");
|
||||
|
||||
await expect(todoItems).toHaveText([TODO_ITEMS[0], "buy some sausages", TODO_ITEMS[2]]);
|
||||
await checkTodosInLocalStorage(page, "buy some sausages");
|
||||
});
|
||||
|
||||
test("should remove the item if an empty text string was entered", async ({ page }) => {
|
||||
const todoItems = page.getByTestId("todo-item");
|
||||
await todoItems.nth(1).dblclick();
|
||||
await todoItems.nth(1).getByRole("textbox", { name: "Edit" }).fill("");
|
||||
await todoItems.nth(1).getByRole("textbox", { name: "Edit" }).press("Enter");
|
||||
|
||||
await expect(todoItems).toHaveText([TODO_ITEMS[0], TODO_ITEMS[2]]);
|
||||
});
|
||||
|
||||
test("should cancel edits on escape", async ({ page }) => {
|
||||
const todoItems = page.getByTestId("todo-item");
|
||||
await todoItems.nth(1).dblclick();
|
||||
await todoItems.nth(1).getByRole("textbox", { name: "Edit" }).fill("buy some sausages");
|
||||
await todoItems.nth(1).getByRole("textbox", { name: "Edit" }).press("Escape");
|
||||
await expect(todoItems).toHaveText(TODO_ITEMS);
|
||||
});
|
||||
});
|
||||
|
||||
test.describe("Counter", () => {
|
||||
test("should display the current number of todo items", async ({ page }) => {
|
||||
// create a new todo locator
|
||||
const newTodo = page.getByPlaceholder("What needs to be done?");
|
||||
|
||||
// create a todo count locator
|
||||
const todoCount = page.getByTestId("todo-count");
|
||||
|
||||
await newTodo.fill(TODO_ITEMS[0]);
|
||||
await newTodo.press("Enter");
|
||||
|
||||
await expect(todoCount).toContainText("1");
|
||||
|
||||
await newTodo.fill(TODO_ITEMS[1]);
|
||||
await newTodo.press("Enter");
|
||||
await expect(todoCount).toContainText("2");
|
||||
|
||||
await checkNumberOfTodosInLocalStorage(page, 2);
|
||||
});
|
||||
});
|
||||
|
||||
test.describe("Clear completed button", () => {
|
||||
test.beforeEach(async ({ page }) => {
|
||||
await createDefaultTodos(page);
|
||||
});
|
||||
|
||||
test("should display the correct text", async ({ page }) => {
|
||||
await page.locator(".todo-list li .toggle").first().check();
|
||||
await expect(page.getByRole("button", { name: "Clear completed" })).toBeVisible();
|
||||
});
|
||||
|
||||
test("should remove completed items when clicked", async ({ page }) => {
|
||||
const todoItems = page.getByTestId("todo-item");
|
||||
await todoItems.nth(1).getByRole("checkbox").check();
|
||||
await page.getByRole("button", { name: "Clear completed" }).click();
|
||||
await expect(todoItems).toHaveCount(2);
|
||||
await expect(todoItems).toHaveText([TODO_ITEMS[0], TODO_ITEMS[2]]);
|
||||
});
|
||||
|
||||
test("should be hidden when there are no items that are completed", async ({ page }) => {
|
||||
await page.locator(".todo-list li .toggle").first().check();
|
||||
await page.getByRole("button", { name: "Clear completed" }).click();
|
||||
await expect(page.getByRole("button", { name: "Clear completed" })).toBeHidden();
|
||||
});
|
||||
});
|
||||
|
||||
test.describe("Persistence", () => {
|
||||
test("should persist its data", async ({ page }) => {
|
||||
// create a new todo locator
|
||||
const newTodo = page.getByPlaceholder("What needs to be done?");
|
||||
|
||||
for (const item of TODO_ITEMS.slice(0, 2)) {
|
||||
await newTodo.fill(item);
|
||||
await newTodo.press("Enter");
|
||||
}
|
||||
|
||||
const todoItems = page.getByTestId("todo-item");
|
||||
const firstTodoCheck = todoItems.nth(0).getByRole("checkbox");
|
||||
await firstTodoCheck.check();
|
||||
await expect(todoItems).toHaveText([TODO_ITEMS[0], TODO_ITEMS[1]]);
|
||||
await expect(firstTodoCheck).toBeChecked();
|
||||
await expect(todoItems).toHaveClass(["completed", ""]);
|
||||
|
||||
// Ensure there is 1 completed item.
|
||||
await checkNumberOfCompletedTodosInLocalStorage(page, 1);
|
||||
|
||||
// Now reload.
|
||||
await page.reload();
|
||||
await expect(todoItems).toHaveText([TODO_ITEMS[0], TODO_ITEMS[1]]);
|
||||
await expect(firstTodoCheck).toBeChecked();
|
||||
await expect(todoItems).toHaveClass(["completed", ""]);
|
||||
});
|
||||
});
|
||||
|
||||
test.describe("Routing", () => {
|
||||
test.beforeEach(async ({ page }) => {
|
||||
await createDefaultTodos(page);
|
||||
// make sure the app had a chance to save updated todos in storage
|
||||
// before navigating to a new view, otherwise the items can get lost :(
|
||||
// in some frameworks like Durandal
|
||||
await checkTodosInLocalStorage(page, TODO_ITEMS[0]);
|
||||
});
|
||||
|
||||
test("should allow me to display active items", async ({ page }) => {
|
||||
const todoItem = page.getByTestId("todo-item");
|
||||
await page.getByTestId("todo-item").nth(1).getByRole("checkbox").check();
|
||||
|
||||
await checkNumberOfCompletedTodosInLocalStorage(page, 1);
|
||||
await page.getByRole("link", { name: "Active" }).click();
|
||||
await expect(todoItem).toHaveCount(2);
|
||||
await expect(todoItem).toHaveText([TODO_ITEMS[0], TODO_ITEMS[2]]);
|
||||
});
|
||||
|
||||
test("should respect the back button", async ({ page }) => {
|
||||
const todoItem = page.getByTestId("todo-item");
|
||||
await page.getByTestId("todo-item").nth(1).getByRole("checkbox").check();
|
||||
|
||||
await checkNumberOfCompletedTodosInLocalStorage(page, 1);
|
||||
|
||||
await test.step("Showing all items", async () => {
|
||||
await page.getByRole("link", { name: "All" }).click();
|
||||
await expect(todoItem).toHaveCount(3);
|
||||
});
|
||||
|
||||
await test.step("Showing active items", async () => {
|
||||
await page.getByRole("link", { name: "Active" }).click();
|
||||
});
|
||||
|
||||
await test.step("Showing completed items", async () => {
|
||||
await page.getByRole("link", { name: "Completed" }).click();
|
||||
});
|
||||
|
||||
await expect(todoItem).toHaveCount(1);
|
||||
await page.goBack();
|
||||
await expect(todoItem).toHaveCount(2);
|
||||
await page.goBack();
|
||||
await expect(todoItem).toHaveCount(3);
|
||||
});
|
||||
|
||||
test("should allow me to display completed items", async ({ page }) => {
|
||||
await page.getByTestId("todo-item").nth(1).getByRole("checkbox").check();
|
||||
await checkNumberOfCompletedTodosInLocalStorage(page, 1);
|
||||
await page.getByRole("link", { name: "Completed" }).click();
|
||||
await expect(page.getByTestId("todo-item")).toHaveCount(1);
|
||||
});
|
||||
|
||||
test("should allow me to display all items", async ({ page }) => {
|
||||
await page.getByTestId("todo-item").nth(1).getByRole("checkbox").check();
|
||||
await checkNumberOfCompletedTodosInLocalStorage(page, 1);
|
||||
await page.getByRole("link", { name: "Active" }).click();
|
||||
await page.getByRole("link", { name: "Completed" }).click();
|
||||
await page.getByRole("link", { name: "All" }).click();
|
||||
await expect(page.getByTestId("todo-item")).toHaveCount(3);
|
||||
});
|
||||
|
||||
test("should highlight the currently applied filter", async ({ page }) => {
|
||||
await expect(page.getByRole("link", { name: "All" })).toHaveClass("selected");
|
||||
|
||||
//create locators for active and completed links
|
||||
const activeLink = page.getByRole("link", { name: "Active" });
|
||||
const completedLink = page.getByRole("link", { name: "Completed" });
|
||||
await activeLink.click();
|
||||
|
||||
// Page change - active items.
|
||||
await expect(activeLink).toHaveClass("selected");
|
||||
await completedLink.click();
|
||||
|
||||
// Page change - completed items.
|
||||
await expect(completedLink).toHaveClass("selected");
|
||||
});
|
||||
});
|
||||
|
||||
async function createDefaultTodos(page: Page) {
|
||||
// create a new todo locator
|
||||
const newTodo = page.getByPlaceholder("What needs to be done?");
|
||||
|
||||
for (const item of TODO_ITEMS) {
|
||||
await newTodo.fill(item);
|
||||
await newTodo.press("Enter");
|
||||
}
|
||||
}
|
||||
|
||||
async function checkNumberOfTodosInLocalStorage(page: Page, expected: number) {
|
||||
return await page.waitForFunction((e) => {
|
||||
return JSON.parse(localStorage["react-todos"]).length === e;
|
||||
}, expected);
|
||||
}
|
||||
|
||||
async function checkNumberOfCompletedTodosInLocalStorage(page: Page, expected: number) {
|
||||
return await page.waitForFunction((e) => {
|
||||
return JSON.parse(localStorage["react-todos"]).filter((todo: any) => todo.completed).length === e;
|
||||
}, expected);
|
||||
}
|
||||
|
||||
async function checkTodosInLocalStorage(page: Page, title: string) {
|
||||
return await page.waitForFunction((t) => {
|
||||
return JSON.parse(localStorage["react-todos"])
|
||||
.map((todo: any) => todo.title)
|
||||
.includes(t);
|
||||
}, title);
|
||||
}
|
Loading…
x
Reference in New Issue
Block a user