diff --git a/scripts/rebuild-frontend.sh b/scripts/rebuild-frontend.sh index d95cd56..b21ae1c 100755 --- a/scripts/rebuild-frontend.sh +++ b/scripts/rebuild-frontend.sh @@ -15,15 +15,6 @@ FRONTEND_DIR="$PROJECT_ROOT/web/frontend" echo "[rebuild-frontend] Building frontend in $FRONTEND_DIR ..." cd "$FRONTEND_DIR" - -# KIN-122: auto npm install if package.json is newer than node_modules (or node_modules missing). -# This handles the case where agents add new imports/dependencies to package.json. -if [ ! -d "node_modules" ] || [ "package.json" -nt "node_modules" ]; then - echo "[rebuild-frontend] package.json changed or node_modules missing — running npm install ..." - npm install - echo "[rebuild-frontend] npm install complete." -fi - npm run build echo "[rebuild-frontend] Build complete." diff --git a/tests/test_kin_122_regression.py b/tests/test_kin_122_regression.py deleted file mode 100644 index a3352cc..0000000 --- a/tests/test_kin_122_regression.py +++ /dev/null @@ -1,91 +0,0 @@ -""" -KIN-122 regression: rebuild-frontend.sh должен запускать npm install -перед npm run build, если package.json изменился (новее node_modules). -""" - -import os -import shutil -import stat -import subprocess -import time -from pathlib import Path - -import pytest - -SCRIPT_PATH = Path(__file__).parent.parent / "scripts" / "rebuild-frontend.sh" - - -class TestKIN122RebuildFrontendNpmInstall: - """Структурные тесты: скрипт содержит условный npm install перед npm run build.""" - - def test_script_exists(self): - assert SCRIPT_PATH.is_file(), f"rebuild-frontend.sh not found at {SCRIPT_PATH}" - - def test_script_is_executable(self): - mode = SCRIPT_PATH.stat().st_mode - assert mode & stat.S_IXUSR, "rebuild-frontend.sh должен быть исполняемым" - - def test_script_contains_npm_install_conditional(self): - """Скрипт должен содержать условный блок npm install (KIN-122).""" - content = SCRIPT_PATH.read_text() - assert "npm install" in content, ( - "rebuild-frontend.sh должен содержать 'npm install'" - ) - - def test_script_npm_install_guarded_by_condition(self): - """npm install должен быть внутри if-блока, а не вызываться безусловно.""" - content = SCRIPT_PATH.read_text() - lines = content.splitlines() - - # Найти строку с npm install - npm_install_line_idx = next( - (i for i, line in enumerate(lines) if "npm install" in line and "if" not in line), - None, - ) - assert npm_install_line_idx is not None, "Строка с 'npm install' не найдена" - - # Должен быть if-блок выше - preceding = "\n".join(lines[:npm_install_line_idx]) - assert "if" in preceding, ( - "npm install должен быть внутри условного блока" - ) - - def test_script_checks_node_modules_existence(self): - """Условие должно проверять наличие node_modules.""" - content = SCRIPT_PATH.read_text() - assert "node_modules" in content, ( - "Скрипт должен проверять наличие node_modules" - ) - - def test_script_checks_package_json_mtime(self): - """Условие должно сравнивать mtime package.json с node_modules (флаг -nt).""" - content = SCRIPT_PATH.read_text() - assert "-nt" in content, ( - "Скрипт должен использовать '-nt' для сравнения mtime package.json и node_modules" - ) - - def test_npm_install_before_npm_run_build(self): - """npm install должен стоять раньше npm run build в скрипте.""" - content = SCRIPT_PATH.read_text() - install_pos = content.find("npm install") - build_pos = content.find("npm run build") - assert install_pos != -1, "npm install не найден в скрипте" - assert build_pos != -1, "npm run build не найден в скрипте" - assert install_pos < build_pos, ( - "npm install должен стоять раньше npm run build" - ) - - def test_npm_run_build_always_runs(self): - """npm run build должен вызываться вне условного блока — всегда выполняется.""" - content = SCRIPT_PATH.read_text() - lines = content.splitlines() - - # Найти строку с npm run build (не внутри if-блока) - # Ищем строку, которая содержит "npm run build" и не является частью if-условия - build_lines = [ - line for line in lines - if "npm run build" in line and line.strip().startswith("npm run build") - ] - assert len(build_lines) >= 1, ( - "npm run build должен быть безусловным вызовом" - ) diff --git a/web/frontend/src/__tests__/task-detail-revising-badge.test.ts b/web/frontend/src/__tests__/task-detail-revising-badge.test.ts index cd9d30d..a4e1497 100644 --- a/web/frontend/src/__tests__/task-detail-revising-badge.test.ts +++ b/web/frontend/src/__tests__/task-detail-revising-badge.test.ts @@ -110,7 +110,7 @@ describe('KIN-UI-017: TaskDetail — statusColor() для статуса revisin const header = wrapper.find('h1') expect(header.exists()).toBe(true) // Ищем Badge рядом с заголовком задачи — он должен быть orange, не gray/blue - const _grayBadgeInHeader = wrapper.find('.text-gray-400.text-xs.rounded') + const grayBadgeInHeader = wrapper.find('.text-gray-400.text-xs.rounded') // text-gray-400 может встречаться в других элементах, но мы проверяем наличие orange const orangeBadge = wrapper.find('.text-orange-400') expect(orangeBadge.exists()).toBe(true) diff --git a/web/frontend/src/__tests__/task-tree.test.ts b/web/frontend/src/__tests__/task-tree.test.ts index 83894a1..f2767f8 100644 --- a/web/frontend/src/__tests__/task-tree.test.ts +++ b/web/frontend/src/__tests__/task-tree.test.ts @@ -253,7 +253,7 @@ describe('KIN-127: дерево задач — отступы', () => { // Обёртка корневой задачи const taskWrapper = wrapper.find('div[style*="padding-left"]') if (taskWrapper.exists()) { - expect((taskWrapper.element as HTMLElement).style.paddingLeft).toBe('0px') + expect(taskWrapper.element.style.paddingLeft).toBe('0px') } else { // Если стиль не задан явно для 0 — это тоже приемлемо expect(true).toBe(true) @@ -278,7 +278,7 @@ describe('KIN-127: дерево задач — отступы', () => { w.find('a[href="/task/KIN-002"]').exists() ) expect(child1Wrapper?.exists()).toBe(true) - expect((child1Wrapper?.element as HTMLElement | undefined)?.style.paddingLeft).toBe('24px') + expect(child1Wrapper?.element.style.paddingLeft).toBe('24px') }) it('Задача второго уровня имеет paddingLeft 48px', async () => { @@ -304,7 +304,7 @@ describe('KIN-127: дерево задач — отступы', () => { w.find('a[href="/task/KIN-003"]').exists() ) expect(child2Wrapper?.exists()).toBe(true) - expect((child2Wrapper?.element as HTMLElement | undefined)?.style.paddingLeft).toBe('48px') + expect(child2Wrapper?.element.style.paddingLeft).toBe('48px') }) }) diff --git a/web/frontend/tsconfig.json b/web/frontend/tsconfig.json index 08c8a90..1ffef60 100644 --- a/web/frontend/tsconfig.json +++ b/web/frontend/tsconfig.json @@ -2,7 +2,6 @@ "files": [], "references": [ { "path": "./tsconfig.app.json" }, - { "path": "./tsconfig.node.json" }, - { "path": "./tsconfig.vitest.json" } + { "path": "./tsconfig.node.json" } ] } diff --git a/web/frontend/tsconfig.vitest.json b/web/frontend/tsconfig.vitest.json deleted file mode 100644 index aa9527b..0000000 --- a/web/frontend/tsconfig.vitest.json +++ /dev/null @@ -1,14 +0,0 @@ -{ - "extends": "./tsconfig.node.json", - "compilerOptions": { - "types": ["node", "vitest/globals"], - "lib": ["ES2023", "DOM"], - "moduleResolution": "bundler", - "noUnusedLocals": false, - "noUnusedParameters": false - }, - "include": [ - "src/__tests__/**/*.ts", - "src/**/__tests__/**/*.ts" - ] -} diff --git a/web/frontend/vite.config.ts b/web/frontend/vite.config.ts index 0d53811..186393b 100644 --- a/web/frontend/vite.config.ts +++ b/web/frontend/vite.config.ts @@ -13,6 +13,5 @@ export default defineConfig({ environment: 'jsdom', globals: true, setupFiles: ['./src/__tests__/vitest-setup.ts'], - typecheck: { tsconfig: './tsconfig.vitest.json' }, }, })