This commit is contained in:
277
frontend/__tests__/input/helpers/validation.spec.ts
Normal file
277
frontend/__tests__/input/helpers/validation.spec.ts
Normal file
@@ -0,0 +1,277 @@
|
||||
import { describe, it, expect, vi, beforeEach, afterAll } from "vitest";
|
||||
import {
|
||||
isCharCorrect,
|
||||
shouldInsertSpaceCharacter,
|
||||
} from "../../../src/ts/input/helpers/validation";
|
||||
import { __testing } from "../../../src/ts/config/testing";
|
||||
import * as FunboxList from "../../../src/ts/test/funbox/list";
|
||||
import * as Strings from "../../../src/ts/utils/strings";
|
||||
|
||||
const { replaceConfig } = __testing;
|
||||
|
||||
// Mock dependencies
|
||||
vi.mock("../../../src/ts/test/funbox/list", () => ({
|
||||
findSingleActiveFunboxWithFunction: vi.fn(),
|
||||
}));
|
||||
|
||||
vi.mock("../../../src/ts/utils/strings", async () => {
|
||||
const actual = await vi.importActual<typeof Strings>(
|
||||
"../../../src/ts/utils/strings",
|
||||
);
|
||||
return {
|
||||
...actual,
|
||||
areCharactersVisuallyEqual: vi.fn(),
|
||||
};
|
||||
});
|
||||
|
||||
describe("isCharCorrect", () => {
|
||||
beforeEach(() => {
|
||||
vi.clearAllMocks();
|
||||
// Reset Config defaults
|
||||
replaceConfig({
|
||||
mode: "words",
|
||||
language: "english",
|
||||
stopOnError: "off",
|
||||
difficulty: "normal",
|
||||
strictSpace: false,
|
||||
});
|
||||
(FunboxList.findSingleActiveFunboxWithFunction as any).mockReturnValue(
|
||||
null,
|
||||
);
|
||||
(Strings.areCharactersVisuallyEqual as any).mockReturnValue(false);
|
||||
});
|
||||
|
||||
afterAll(() => {
|
||||
replaceConfig({});
|
||||
});
|
||||
|
||||
describe("Zen Mode", () => {
|
||||
it("always returns true", () => {
|
||||
replaceConfig({ mode: "zen" });
|
||||
expect(
|
||||
isCharCorrect({
|
||||
data: "a",
|
||||
inputValue: "test",
|
||||
targetWord: "word",
|
||||
correctShiftUsed: true,
|
||||
}),
|
||||
).toBe(true);
|
||||
});
|
||||
});
|
||||
|
||||
describe("Shift Key", () => {
|
||||
it("returns false if correct shift was not used", () => {
|
||||
expect(
|
||||
isCharCorrect({
|
||||
data: "A",
|
||||
inputValue: "test",
|
||||
targetWord: "testA",
|
||||
correctShiftUsed: false,
|
||||
}),
|
||||
).toBe(false);
|
||||
});
|
||||
});
|
||||
|
||||
describe("Space Handling", () => {
|
||||
it.each([
|
||||
["returns true at the end of a correct word", " ", "word", "word", true],
|
||||
[
|
||||
"returns false at the end of an incorrect word",
|
||||
" ",
|
||||
"worx",
|
||||
"word",
|
||||
false,
|
||||
],
|
||||
["returns false in the middle of a word", " ", "wor", "word", false],
|
||||
["returns false at the start of a word", " ", "", "word", false],
|
||||
[
|
||||
"returns false when longer than a word",
|
||||
" ",
|
||||
"wordwordword",
|
||||
"word",
|
||||
false,
|
||||
],
|
||||
])("%s", (_desc, char, input, word, expected) => {
|
||||
expect(
|
||||
isCharCorrect({
|
||||
data: char,
|
||||
inputValue: input,
|
||||
targetWord: word,
|
||||
correctShiftUsed: true,
|
||||
}),
|
||||
).toBe(expected);
|
||||
});
|
||||
});
|
||||
|
||||
describe("Standard Matching", () => {
|
||||
it.each([
|
||||
["a", "te", "tea", true],
|
||||
["b", "te", "tea", false],
|
||||
["x", "tea", "tea", false],
|
||||
])(
|
||||
"char '%s' for input '%s' (current word '%s') -> %s",
|
||||
(char, input, word, expected) => {
|
||||
expect(
|
||||
isCharCorrect({
|
||||
data: char,
|
||||
inputValue: input,
|
||||
targetWord: word,
|
||||
correctShiftUsed: true,
|
||||
}),
|
||||
).toBe(expected);
|
||||
},
|
||||
);
|
||||
});
|
||||
|
||||
it("throws error if data is undefined", () => {
|
||||
expect(() =>
|
||||
isCharCorrect({
|
||||
data: undefined as any,
|
||||
inputValue: "val",
|
||||
targetWord: "word",
|
||||
correctShiftUsed: true,
|
||||
}),
|
||||
).toThrow();
|
||||
});
|
||||
});
|
||||
|
||||
describe("shouldInsertSpaceCharacter", () => {
|
||||
beforeEach(() => {
|
||||
replaceConfig({
|
||||
mode: "time",
|
||||
stopOnError: "off",
|
||||
strictSpace: false,
|
||||
difficulty: "normal",
|
||||
});
|
||||
});
|
||||
|
||||
afterAll(() => {
|
||||
replaceConfig({});
|
||||
});
|
||||
|
||||
it("returns null if data is not a space", () => {
|
||||
expect(
|
||||
shouldInsertSpaceCharacter({
|
||||
data: "a",
|
||||
inputValue: "test",
|
||||
targetWord: "test",
|
||||
}),
|
||||
).toBe(null);
|
||||
});
|
||||
|
||||
it("returns false in zen mode", () => {
|
||||
replaceConfig({ mode: "zen" });
|
||||
expect(
|
||||
shouldInsertSpaceCharacter({
|
||||
data: " ",
|
||||
inputValue: "test",
|
||||
targetWord: "test",
|
||||
}),
|
||||
).toBe(false);
|
||||
});
|
||||
|
||||
describe("Logic Checks", () => {
|
||||
it.each([
|
||||
// Standard behavior (submit word)
|
||||
{
|
||||
desc: "submit correct word",
|
||||
inputValue: "hello",
|
||||
targetWord: "hello",
|
||||
config: {
|
||||
stopOnError: "off",
|
||||
strictSpace: false,
|
||||
difficulty: "normal",
|
||||
},
|
||||
expected: false,
|
||||
},
|
||||
{
|
||||
desc: "submit incorrect word (stopOnError off)",
|
||||
inputValue: "hel",
|
||||
targetWord: "hello",
|
||||
config: {
|
||||
stopOnError: "off",
|
||||
strictSpace: false,
|
||||
difficulty: "normal",
|
||||
},
|
||||
expected: false,
|
||||
},
|
||||
// Stop on error
|
||||
{
|
||||
desc: "insert space if incorrect (stopOnError letter)",
|
||||
inputValue: "hel",
|
||||
targetWord: "hello",
|
||||
config: {
|
||||
stopOnError: "letter",
|
||||
strictSpace: false,
|
||||
difficulty: "normal",
|
||||
},
|
||||
expected: true,
|
||||
},
|
||||
{
|
||||
desc: "insert space if incorrect (stopOnError word)",
|
||||
inputValue: "hel",
|
||||
targetWord: "hello",
|
||||
config: {
|
||||
stopOnError: "word",
|
||||
strictSpace: false,
|
||||
difficulty: "normal",
|
||||
},
|
||||
expected: true,
|
||||
},
|
||||
{
|
||||
desc: "submit if correct (stopOnError letter)",
|
||||
inputValue: "hello",
|
||||
targetWord: "hello",
|
||||
config: {
|
||||
stopOnError: "letter",
|
||||
strictSpace: false,
|
||||
difficulty: "normal",
|
||||
},
|
||||
expected: false,
|
||||
},
|
||||
// Strict space / Difficulty
|
||||
{
|
||||
desc: "insert space if empty input (strictSpace on)",
|
||||
inputValue: "",
|
||||
targetWord: "hello",
|
||||
config: {
|
||||
stopOnError: "off",
|
||||
strictSpace: true,
|
||||
difficulty: "normal",
|
||||
},
|
||||
expected: true,
|
||||
},
|
||||
{
|
||||
desc: "insert space if empty input (difficulty not normal - expert or master)",
|
||||
inputValue: "",
|
||||
targetWord: "hello",
|
||||
config: {
|
||||
stopOnError: "off",
|
||||
strictSpace: false,
|
||||
difficulty: "expert",
|
||||
},
|
||||
expected: true,
|
||||
},
|
||||
{
|
||||
desc: "submit if not empty input (strictSpace on)",
|
||||
inputValue: "h",
|
||||
targetWord: "hello",
|
||||
config: {
|
||||
stopOnError: "off",
|
||||
strictSpace: true,
|
||||
difficulty: "normal",
|
||||
},
|
||||
expected: false,
|
||||
},
|
||||
])("$desc", ({ inputValue, targetWord, config, expected }) => {
|
||||
replaceConfig(config as any);
|
||||
expect(
|
||||
shouldInsertSpaceCharacter({
|
||||
data: " ",
|
||||
inputValue,
|
||||
targetWord,
|
||||
}),
|
||||
).toBe(expected);
|
||||
});
|
||||
});
|
||||
});
|
||||
Reference in New Issue
Block a user