This commit is contained in:
Grol Grol 2025-03-15 12:10:57 +03:00
parent 1d4f782f53
commit 0c43e9f5e7
2 changed files with 40 additions and 5 deletions

View file

@ -11,18 +11,46 @@ describe("findCheckboxesLine", () => {
expect(findCheckboxesLine("1. [x] Numbered task")).not.toBeNull();
});
test("корректно обрабатывает разные состояния чекбокса", () => {
const states = [" ", "x", "-", "?", "!", "*", "#", "@", "[", "]", "y", "X", "Y"];
for (const state of states) {
const match = findCheckboxesLine(`- [${state}] Task`);
expect(match).not.toBeNull();
expect(match![3]).toBe(state);
}
});
test("корректно обрабатывает отступы", () => {
const noIndentMatch = findCheckboxesLine("- [ ] Task");
expect(noIndentMatch).not.toBeNull();
expect(noIndentMatch![1]).toBe("");
const singleSpaceMatch = findCheckboxesLine(" - [ ] Task");
expect(singleSpaceMatch).not.toBeNull();
expect(singleSpaceMatch![1]).toBe(" ");
const multiSpaceMatch = findCheckboxesLine(" - [ ] Task");
expect(multiSpaceMatch).not.toBeNull();
expect(multiSpaceMatch![1]).toBe(" ");
const tabMatch = findCheckboxesLine("\t- [ ] Task");
expect(tabMatch).not.toBeNull();
expect(tabMatch![1]).toBe("\t");
});
test("игнорирует некорректные строки", () => {
// Отсутствует пробел после маркера списка
expect(findCheckboxesLine("-[ ] Task")).toBeNull();
expect(findCheckboxesLine("*[x] Task")).toBeNull();
expect(findCheckboxesLine("1.[ ] Numbered task")).toBeNull();
// Неверное содержимое скобок или неверный регистр
// Пустые скобки недопустимы
expect(findCheckboxesLine("- [] Task")).toBeNull();
expect(findCheckboxesLine("- [X] Task")).toBeNull();
// Не соответствует шаблону чекбокса
expect(findCheckboxesLine(" - Task")).toBeNull();
expect(findCheckboxesLine("Just some text")).toBeNull();
expect(findCheckboxesLine("1. Some numbered task")).toBeNull();
expect(findCheckboxesLine("")).toBeNull();
});
});

View file

@ -2,9 +2,12 @@
* Функция для поиска строк с чекбоксами в формате Markdown.
*/
export function findCheckboxesLine(line: string): RegExpMatchArray | null {
return line.match(/^(\s*)([*+-]|\d+\.) \[([ x-])\] /);
return line.match(/^(\s*)([*+-]|\d+\.) \[(.)\] /);
}
export function isCheckedSymbol(text: string): boolean {
return text === "x";
}
/**
* Возвращает список изменений (позиции и новые значения), но не модифицирует текст напрямую.
*/
@ -17,7 +20,7 @@ export function syncCheckboxes(text: string): { line: number; ch: number; value:
if (!match) continue;
const indent = match[1].length;
const isChecked = match[3] === "x";
const isChecked = isCheckedSymbol(match[3]);
let allChildrenChecked = true;
let hasChildren = false;
let j = i + 1;
@ -26,7 +29,11 @@ export function syncCheckboxes(text: string): { line: number; ch: number; value:
const childMatch = findCheckboxesLine(lines[j]);
if (!childMatch || childMatch[1].length <= indent) break;
hasChildren = true;
if (childMatch[3] !== "x") allChildrenChecked = false;
const childrenIsChecked = isCheckedSymbol(childMatch[3]);
if (!childrenIsChecked) {
allChildrenChecked = false;
break;
}
j++;
}