callumalpass_tasknotes/docs/development/refactor-smoke-checks.md
2026-05-19 13:10:40 +10:00

42 KiB

Refactor Smoke Checks

Use this checklist for the architecture refactor phases that touch TaskNotes plugin lifecycle, Bases views, calendar mutation, task creation, or cache freshness.

Baseline Commands

Run these from /home/calluma/projects/tasknotes after the relevant Jest checks:

npm run lint
npm run typecheck
npm test -- --runInBand
npm run build:test
obsidian vault=test plugin:reload id=tasknotes
obsidian vault=test dev:errors

Phase A Focused Checks

These commands exercise the first refactor seams in the running test vault after build and reload:

obsidian vault=test eval code="const p = app.plugins.plugins.tasknotes; if (!p?.taskService || !p?.cacheManager || !p?.fieldMapper) throw new Error('TaskNotes core services unavailable'); 'tasknotes-ready'"
obsidian vault=test eval code="(async () => { await app.commands.executeCommandById('tasknotes:refresh-views'); return 'refresh-views-ok'; })()"
obsidian vault=test eval code="(async () => { const p = app.plugins.plugins.tasknotes; const r = await p.taskService.createTask({ title: 'Phase A smoke task', scheduled: '2026-05-18', due: '2026-05-19', creationContext: 'api' }, { applyDefaults: false }); const cached = await p.cacheManager.getTaskInfo(r.taskInfo.path); if (!cached) throw new Error('Created task was not cached'); await p.taskService.updateProperty(cached, 'scheduled', '2026-05-20'); const refreshed = await p.cacheManager.getTaskInfo(r.taskInfo.path); if (!refreshed || refreshed.scheduled !== '2026-05-20') throw new Error('Updated task was not visible in cache'); return r.file.path; })()"

Plugin Shell Focused Checks

Run these after plugin startup, settings persistence, or settings migration refactors:

npm test -- --runInBand tests/unit/settings/settingsPersistence.test.ts tests/unit/issues/issue-1591-settings-lost-on-update.test.ts tests/unit/issues/issue-1669-data-json-frequent-writes.test.ts tests/unit/issues/issue-1419-settings-save-coalescing.test.ts
npm test -- --runInBand tests/unit/bootstrap/defaultBasesFiles.test.ts tests/unit/issues/issue-1495-default-bases-regenerate.test.ts
obsidian vault=test eval code="(() => { const p = app.plugins.plugins.tasknotes; if (!p?.settings || !p?.settingsLifecycleService || !p?.commandRegistry || !p?.cacheManager) throw new Error('TaskNotes plugin shell unavailable'); return { language: p.settings.uiLanguage, commands: Object.keys(p.settings.commandFileMapping ?? {}).length, basesRegistered: p.basesRegistered }; })()"
obsidian vault=test dev:errors

Filtering Focused Checks

Run these after FilterService query, agenda, grouping, sorting, or filter-option refactors:

npm test -- --runInBand tests/unit/services/filterPredicateEvaluation.test.ts tests/unit/services/filterTaskGrouping.test.ts tests/unit/services/filterTaskSorting.test.ts tests/unit/services/filterOptions.test.ts tests/unit/services/filterQueryState.test.ts tests/unit/services/filterService.agendaTaskSelection.test.ts tests/unit/services/filterService.userListNormalization.test.ts tests/unit/services/filterService.groupByUserField.test.ts tests/unit/services/filterService.groupByUserField.more.test.ts tests/unit/services/filterService.sortByUserField.test.ts tests/unit/services/FilterService-fix-verification.test.ts tests/unit/services/FilterService-issue-153-fixed.test.ts tests/unit/issues/issue-353-has-subtasks-filter.test.ts tests/unit/issues/issue-1027-overdue-tasknotes-base.test.ts tests/unit/issues/issue-1059-recurring-task-overdue-agenda.test.ts tests/unit/issues/issue-810-overdue-tasks-disappear.test.ts tests/unit/issues/issue-1651-query-api-scheduled-date-time-filter.test.ts
obsidian vault=test dev:errors

Phase C Focused Checks

Run these after task-creation assembly or default-handling refactors:

npm test -- --runInBand tests/unit/services/taskCreationDefaults.test.ts tests/unit/services/taskTitleSanitizer.test.ts tests/unit/services/taskPropertyUpdate.test.ts tests/unit/services/taskUpdatePlanning.test.ts tests/unit/services/taskPropertyChangeSideEffects.test.ts tests/unit/services/taskArchivePlanning.test.ts tests/unit/services/taskTimeTrackingPlanning.test.ts tests/unit/services/taskRecurringPlanning.test.ts tests/unit/services/taskBlockingRelationships.test.ts tests/unit/bases/basesFilterDefaults.test.ts tests/unit/bases/basesTaskCreation.test.ts tests/unit/api/SystemController.nlp-task-data.test.ts
obsidian vault=test eval code="(async () => { const p = app.plugins.plugins.tasknotes; const r = await p.taskService.createTask({ title: 'Phase C smoke task', contexts: ['phase-c'], creationContext: 'api' }); const task = await p.cacheManager.getTaskInfo(r.taskInfo.path); if (!task || task.title !== 'Phase C smoke task') throw new Error('Task creation smoke failed'); return r.file.path; })()"
obsidian vault=test dev:errors

TaskManager Focused Checks

Run these after task read, task identification, or cache-freshness refactors:

npm test -- --runInBand tests/unit/utils/TaskManager.isTaskFile.test.ts tests/unit/utils/taskInfoAssembly.test.ts tests/unit/issues/issue-1684-plain-markdown-task-discovery.test.ts tests/unit/issues/issue-1302-task-manager-file-fallback.test.ts tests/unit/issues/issue-1820-api-created-task-cache-fallback.test.ts tests/unit/issues/issue-1374-native-property-labels.test.ts tests/unit/services/filterService.userListNormalization.test.ts tests/unit/services/filterService.groupByUserField.test.ts tests/unit/services/filterService.groupByUserField.more.test.ts tests/unit/services/filterService.sortByUserField.test.ts
obsidian vault=test eval code="(async () => { const p = app.plugins.plugins.tasknotes; const cache = p.cacheManager; const prev = { taskIdentificationMethod: p.settings.taskIdentificationMethod, taskPropertyName: p.settings.taskPropertyName, taskPropertyValue: p.settings.taskPropertyValue, taskTag: p.settings.taskTag }; try { p.settings.taskIdentificationMethod = 'property'; p.settings.taskPropertyName = 'type'; p.settings.taskPropertyValue = 'task'; cache.updateConfig(p.settings); if (!cache.isTaskFile({ type: ['note', 'task'] })) throw new Error('property task identification failed'); } finally { Object.assign(p.settings, prev); cache.updateConfig(p.settings); } const timeEntriesField = p.settings.fieldMapping.timeEntries || 'timeEntries'; const path = `TaskNotes/TaskManager smoke ${Date.now()}.md`; await app.vault.create(path, ['---', 'title: TaskManager smoke', 'status: open', 'tags:', '  - task', `${timeEntriesField}:`, '  - startTime: 2026-05-19T00:00:00.000Z', '    endTime: 2026-05-19T00:45:00.000Z', '---', ''].join('\n')); const task = await cache.getTaskInfo(path); if (!task || task.totalTrackedTime !== 45) throw new Error('TaskManager assembly smoke failed'); return { path, totalTrackedTime: task.totalTrackedTime }; })()"
obsidian vault=test dev:errors

Phase E Focused Checks

Run these after Kanban or shared Bases drag/drop refactors:

npm test -- --runInBand tests/unit/bases/basesViewAdapters.test.ts tests/unit/bases/basesSelectionUi.test.ts tests/unit/bases/basesExport.test.ts tests/unit/bases/basesUpdateEvents.test.ts tests/unit/bases/basesTaskUpdateListeners.test.ts tests/unit/bases/basesRefreshLifecycle.test.ts tests/unit/bases/basesEntryProperties.test.ts tests/unit/bases/basesValueConversion.test.ts tests/unit/bases/basesTaskCopyActions.test.ts tests/unit/bases/basesCreateFileForView.test.ts tests/unit/bases/basesToolbar.test.ts tests/unit/bases/basesVisibleProperties.test.ts tests/unit/bases/basesSearchUi.test.ts tests/unit/bases/kanbanGrouping.test.ts tests/unit/bases/kanbanDragUtils.test.ts tests/unit/bases/kanbanCreationDefaults.test.ts tests/unit/issues/issue-1783-kanban-drag-image.test.ts tests/unit/issues/issue-1784-kanban-pinned-columns.test.ts tests/unit/issues/issue-1797-kanban-touch-drop-target.test.ts tests/unit/issues/issue-1808-kanban-swimlane-order.test.ts tests/unit/issues/issue-1176-kanban-wip-limits.test.ts tests/unit/bases/taskListDragGeometry.test.ts tests/unit/bases/taskListGrouping.test.ts tests/unit/bases/taskListDropPlanning.test.ts tests/unit/ui/TaskListView.dragControls.test.ts
obsidian vault=test eval code="(async () => { const p = app.plugins.plugins.tasknotes; await p.openBasesFileForCommand('open-kanban-view'); app.workspace.trigger('tasknotes:refresh-views'); return p.settings.commandFileMapping['open-kanban-view']; })()"
obsidian vault=test eval code="(async () => { const p = app.plugins.plugins.tasknotes; await p.openBasesFileForCommand('open-tasks-view'); app.workspace.trigger('tasknotes:refresh-views'); await new Promise((resolve) => setTimeout(resolve, 1500)); const cards = Array.from(document.querySelectorAll('.tn-bases-items-container .task-card[data-task-path]')); return { mapping: p.settings.commandFileMapping['open-tasks-view'], cards: cards.length, reorderable: cards.filter((card) => card.classList.contains('task-card--reorderable') || card.querySelector('[data-tn-drag-handle=true]')).length }; })()"
obsidian vault=test dev:errors

Phase F Focused Checks

Run these after TaskCard or modal interaction refactors:

npm test -- --runInBand tests/unit/ui/taskCardPropertyAccess.test.ts tests/unit/ui/taskCardRelationships.test.ts tests/unit/ui/taskCardRelationshipExpansion.test.ts tests/unit/ui/taskCardMetadata.test.ts tests/unit/ui/taskCardState.test.ts tests/unit/ui/taskCardCompletionState.test.ts tests/unit/ui/taskCardPrimaryIndicators.test.ts tests/unit/ui/taskCardSecondaryBadges.test.ts tests/unit/ui/taskCardTitle.test.ts tests/unit/ui/taskCardContextMenu.test.ts tests/unit/ui/taskCardActions.test.ts tests/unit/ui/taskCardIndicators.test.ts tests/unit/modals/taskModalDependencies.test.ts tests/unit/modals/taskModalTaskSelector.test.ts tests/unit/modals/taskModalSubtasks.test.ts tests/unit/modals/taskModalProjects.test.ts tests/unit/modals/taskModalActionValues.test.ts tests/unit/modals/taskModalActionMenus.test.ts tests/unit/modals/taskModalActionIconStates.test.ts tests/unit/modals/taskModalActionState.test.ts tests/unit/modals/taskModalActionBar.test.ts tests/unit/modals/taskModalActionButtons.test.ts tests/unit/modals/taskModalTitleInput.test.ts tests/unit/modals/taskModalLayout.test.ts tests/unit/modals/taskModalFocusGuards.test.ts tests/unit/modals/taskModalOrganizationFields.test.ts tests/unit/modals/taskModalMetadataFields.test.ts tests/unit/modals/taskModalFieldRenderer.test.ts tests/unit/modals/taskModalDetailsEditor.test.ts tests/unit/modals/taskModalUserFieldControls.test.ts tests/unit/modals/TaskModal.user-fields.test.ts tests/unit/modals/taskCreationFormState.test.ts tests/unit/modals/taskCreationSubtasks.test.ts tests/unit/modals/taskEditFormState.test.ts tests/unit/modals/taskEditChangeState.test.ts tests/unit/modals/taskEditSubtasks.test.ts tests/unit/modals/TaskCreationModal.test.ts tests/unit/modals/TaskEditModal.unsaved-changes.test.ts tests/unit/issues/issue-1633-task-card-i18n-field-mapping.test.ts tests/unit/issues/issue-1720-bases-date-value-icon-rendering.test.ts tests/unit/issues/issue-1610-subtasks-inherit-view-order.test.ts tests/unit/issues/issue-1235-blocked-tasks-toggle-arrow.test.ts tests/unit/issues/issue-922-dependency-display.test.ts tests/unit/issues/issue-1854-modal-completed-date.test.ts tests/unit/issues/issue-1846-nlp-boolean-user-fields.test.ts tests/unit/issues/issue-1870-user-field-wikilink-nlp.test.ts tests/unit/issues/issue-1756-custom-fields-http-api.test.ts
obsidian vault=test eval code="(() => { const cards = Array.from(document.querySelectorAll('.task-card')); if (cards.length === 0) throw new Error('No task cards rendered after Bases view smoke'); return { cards: cards.length, contextButtons: document.querySelectorAll('.task-card__context-menu').length, metadataProperties: document.querySelectorAll('.task-card__metadata-property').length, relationshipToggles: document.querySelectorAll('.task-card__blocking-toggle, .task-card__blocked-toggle, .task-card__chevron').length }; })()"
obsidian vault=test eval code="(async () => { const waitFor = (fn, label) => new Promise((resolve, reject) => { const started = Date.now(); const tick = () => { const value = fn(); if (value) return resolve(value); if (Date.now() - started > 2000) return reject(new Error(label)); requestAnimationFrame(tick); }; tick(); }); const closeModal = () => document.querySelector('.modal-close-button')?.dispatchEvent(new MouseEvent('click', { bubbles: true })); const p = app.plugins.plugins.tasknotes; p.openTaskCreationModal({ title: 'Phase F modal smoke' }); const creationInput = await waitFor(() => document.querySelector('.minimalist-modal-container .title-input, .minimalist-modal-container .title-input-detailed'), 'creation modal did not open'); const creationValue = creationInput.value; closeModal(); const r = await p.taskService.createTask({ title: 'Phase F edit modal smoke', creationContext: 'api' }, { applyDefaults: false }); await p.openTaskEditModal(r.taskInfo); const editInput = await waitFor(() => document.querySelector('.minimalist-modal-container .title-input, .minimalist-modal-container .title-input-detailed'), 'edit modal did not open'); const editValue = editInput.value; closeModal(); return { path: r.file.path, creationValue, editValue }; })()"
obsidian vault=test dev:errors

Phase G Focused Checks

Run these after diagnostics, logging, or error-policy refactors:

npm test -- --runInBand tests/unit/utils/tasknotesLogger.test.ts tests/unit/bases/basesApiDiagnostics.test.ts tests/unit/services/TaskLinkDetectionService.diagnostics.test.ts tests/unit/editor/MarkdownWidgetContext.test.ts
obsidian vault=test eval code="(async () => { const p = app.plugins.plugins.tasknotes; const previous = p.settings.enableDebugLogging; p.settings.enableDebugLogging = true; try { await app.commands.executeCommandById('tasknotes:refresh-views'); return { debugLogging: p.settings.enableDebugLogging, refreshTriggered: true }; } finally { p.settings.enableDebugLogging = previous; } })()"
obsidian vault=test dev:errors

Phase D Focused Checks

Run these after Calendar event-building or mutation refactors:

npm test -- --runInBand tests/unit/bases/calendarMutationPlanning.test.ts tests/unit/bases/calendarPropertyEvents.test.ts tests/unit/bases/calendarExternalEvents.test.ts tests/unit/bases/calendarTaskEvents.test.ts tests/unit/bases/calendarDataSignature.test.ts tests/unit/bases/calendarConfigSnapshot.test.ts tests/unit/bases/calendarInitialDate.test.ts tests/unit/bases/calendarEventMount.test.ts tests/unit/issues/calendar-list-task-card-width.test.ts tests/unit/issues/issue-1502-ics-related-note-indicators.test.ts tests/unit/issues/issue-1766-calendar-date-navigation-property.test.ts tests/unit/issues/issue-1687-calendar-recreate-date-preservation.test.ts tests/unit/issues/issue-287-calendar-linked-task-hover.test.ts
obsidian vault=test eval code="(async () => { const p = app.plugins.plugins.tasknotes; await p.openBasesFileForCommand('open-advanced-calendar-view'); app.workspace.trigger('tasknotes:refresh-views'); return p.settings.commandFileMapping['open-advanced-calendar-view']; })()"
obsidian vault=test dev:errors

Record known unrelated test-vault noise separately. Any TaskNotes stack frame, plugin reload failure, failed command registration, or missing core service is a blocker for the refactor phase.

Baseline Run

2026-05-18:

  • npm run lint, npm run typecheck, npm test -- --runInBand, and npm run build:test passed.
  • obsidian vault=test plugin:reload id=tasknotes passed and obsidian vault=test dev:errors reported no captured errors.
  • Phase A focused checks returned tasknotes-ready, refresh-views-ok, and TaskNotes/Phase A smoke task-9.md.
  • Phase C focused Jest checks covered task-creation defaults, Bases task-creation assembly, and HTTP NLP task-data assembly; the live creation smoke returned TaskNotes/Phase C smoke task-4.md.
  • Phase D focused Jest checks covered calendar mutation planning, task-event construction, property-event construction, and external provider event assembly. Calendar smoke opened TaskNotes/Views/calendar-default.base, triggered view refresh, and dev:errors reported no captured errors.
  • Phase E Kanban smoke opened TaskNotes/Views/kanban-default.base, triggered view refresh, rendered a Kanban board with 18 columns and 386 cards, and dev:errors reported no captured errors. Focused Kanban checks cover grouping, drag/drop planning, saved/default column ordering, pinned columns, WIP limit labels, swimlane ordering, and hidden-empty swimlane behavior. The final Kanban smoke emitted known VirtualScroller fallback sizing warnings before passing.
  • Shared Bases adapter checks cover formula computation, failed-formula isolation, frontmatter restoration, and path-property map assembly for formula-backed view properties.
  • 2026-05-19 shared Bases formula/property adapter slice verification passed focused adapter, Kanban grouping, Task List grouping, Calendar formula, and scheduled-group sort tests, npm run lint, npm run typecheck, npm test -- --runInBand (520 suites, 3306 tests), npm run build:test, obsidian vault=test plugin:reload id=tasknotes, live Kanban smoke opening TaskNotes/Views/kanban-default.base with a rendered board, 18 columns, 18 headers, and 386 cards, live Task List smoke opening TaskNotes/Views/tasks-default.base with 48 cards, 6 group headers, and 48 reorderable cards/handles, and obsidian vault=test dev:errors. The Kanban smoke emitted known malformed-fixture frontmatter warnings and a Google Calendar provider sync error for _codex/issue-1232/scheduled-today.md; the final error buffer was clean.
  • 2026-05-19 Kanban task-grouping slice verification passed focused Kanban grouping, drag, pinned-column, swimlane-order, WIP, and scheduled-group sort tests, npm run lint, npm run typecheck, npm test -- --runInBand (520 suites, 3311 tests), npm run build:test, obsidian vault=test plugin:reload id=tasknotes, live Kanban smoke opening TaskNotes/Views/kanban-default.base with a rendered board, 18 columns, 18 headers, 386 cards, and 10 unknown-status columns, and obsidian vault=test dev:errors. The Kanban smoke emitted known malformed-fixture frontmatter warnings, VirtualScroller fallback sizing warnings, and a Google Calendar provider sync error for _codex/issue-1232/scheduled-today.md; the final error buffer was clean.
  • 2026-05-19 Calendar data-signature slice verification passed focused Calendar signature, agenda sort, property-event, and formula-property tests, npm run lint, npm run typecheck, npm test -- --runInBand (521 suites, 3316 tests), npm run build:test, obsidian vault=test plugin:reload id=tasknotes, live Calendar smoke opening TaskNotes/Views/calendar-default.base with a rendered FullCalendar instance, 272 events, 15 day cells, and the refresh button, and obsidian vault=test dev:errors. The Calendar smoke emitted known malformed-fixture frontmatter warnings before the final error buffer passed cleanly.
  • 2026-05-19 Calendar property-event mutation-planning slice verification passed focused Calendar mutation and custom-field filter tests, npm run lint, npm run typecheck, npm test -- --runInBand (530 suites, 3380 tests), npm run build:test, obsidian vault=test plugin:reload id=tasknotes, live Calendar smoke opening TaskNotes/Views/calendar-default.base with a rendered FullCalendar instance, 280 events, and 15 day cells, obsidian vault=test dev:errors, git diff --check, and .ops mdbase validate ..
  • 2026-05-19 Kanban drop side-effect and settings-persistence tranche verification passed focused Kanban grouping/drag/drop tests and settings persistence/migration tests, npm run lint, npm run typecheck, npm test -- --runInBand (531 suites, 3392 tests), npm run build:test, obsidian vault=test plugin:reload id=tasknotes, live plugin-shell smoke confirming settings, lifecycle service, command registry, cache manager, and Bases registration, live Calendar smoke opening TaskNotes/Views/mini-calendar-default.base with 432 events and 7 day cells, live Kanban smoke opening TaskNotes/Views/kanban-default.base with 18 columns, 18 headers, and 381 cards, and obsidian vault=test dev:errors. The Kanban smoke emitted known VirtualScroller fallback sizing warnings before the final error buffer passed cleanly.
  • 2026-05-19 default-Bases, agenda-selection, and Bases reload-cleanup tranche verification passed focused default-Bases, agenda, Bases diagnostics, and existing agenda/overdue regression tests; npm run lint; npm run typecheck; full npm test -- --runInBand (533 suites, 3402 tests); npm run build:test; obsidian vault=test plugin:reload id=tasknotes; live plugin-shell smoke confirming settings, lifecycle service, command registry, cache manager, and Bases registration; live default-Bases smoke confirming 10 command mappings and 10 skipped existing files; live agenda smoke returning 1 day, 37 tasks for the day, and 4938 overdue candidates; live Advanced Calendar smoke opening TaskNotes/Views/calendar-default.base with 432 events, 7 day cells, and 1 FullCalendar instance; live Kanban smoke opening TaskNotes/Views/kanban-default.base with 18 columns, 18 headers, and 386 cards; and obsidian vault=test dev:errors. The live smokes emitted known malformed-fixture frontmatter warnings, dependency-cache warmup warnings, and VirtualScroller fallback sizing warnings before the final error buffer passed cleanly.
  • 2026-05-19 TaskUpdateService bulk-update planning slice verification passed focused taskUpdatePlanning, TaskService, store-title-in-filename, edit-modal subtask sort, completed-date, property-update, and property-side-effect tests; npm run lint; npm run typecheck; full npm test -- --runInBand (535 suites, 3412 tests); npm run build:test; obsidian vault=test plugin:reload id=tasknotes; live task-update smoke confirming status and priority updates, due removal, completed-date derivation, legacy time-entry duration cleanup, raw body update after CRLF details input, and cache freshness; and obsidian vault=test dev:errors. The live smoke emitted known malformed-fixture frontmatter warnings before the final error buffer passed cleanly.
  • 2026-05-19 task creation/update runtime-contract slice verification passed focused TaskService, store-title-in-filename, blockedBy creation, API/MCP filename-format, Bases task creation, NLP task-data, and update-planning tests; npm run lint; npm run typecheck; full npm test -- --runInBand (535 suites, 3415 tests); npm run build:test; obsidian vault=test plugin:reload id=tasknotes; live create/update smoke confirming created path/title, status/priority cache refresh, due removal, completed-date derivation, raw body update, and time-entry duration cleanup; and obsidian vault=test dev:errors.
  • 2026-05-19 FilterService runtime-contract slice focused verification passed user-field grouping/sorting/list normalization, agenda selection, hierarchical grouping, has-subtasks, overdue, weighted priority/date sorting, scheduled date-time filter, and recurring-overdue tests; npm run typecheck; and npm run lint.
  • 2026-05-19 FilterService runtime-contract slice full verification passed npm test -- --runInBand (535 suites, 3416 tests), npm run build:test, obsidian vault=test plugin:reload id=tasknotes, live FilterService agenda/filter-options smoke returning 1 day, 37 first-day tasks, 4940 overdue tasks, 7 user-field properties, locale en, and obsidian vault=test dev:errors.
  • 2026-05-19 current-note conversion planning slice focused verification passed current-note conversion, default-value, untouched-save, and sort-order helper tests, plus npm run typecheck and npm run lint.
  • 2026-05-19 current-note conversion planning slice full verification passed npm test -- --runInBand (536 suites, 3420 tests), npm run build:test, obsidian vault=test plugin:reload id=tasknotes, live convert-current-note smoke confirming the edit modal title/body from a temporary note, and obsidian vault=test dev:errors.
  • 2026-05-19 date-change detection extraction focused verification passed date-change timer tests, issue-1045 recurrence status tests, npm run typecheck, and npm run lint.
  • 2026-05-19 Task List drop-planning focused verification passed taskListDropPlanning and TaskListView.dragControls tests, plus npm run typecheck and npm run lint.
  • 2026-05-19 Task List drop-planning full verification passed npm test -- --runInBand (538 suites, 3432 tests), npm run build:test, obsidian vault=test plugin:reload id=tasknotes, live Task List smoke opening TaskNotes/Views/tasks-default.base with 329 cards, 36 group headers, and 329 reorderable cards, and obsidian vault=test dev:errors. The live smoke emitted the known Google Calendar provider sync error for _codex/issue-1232/scheduled-today.md; the final error buffer was clean.
  • 2026-05-19 Filter predicate extraction full verification passed focused predicate, has-subtasks, scheduled date-time, user-field grouping, and user-list normalization tests; npm run typecheck; npm run lint; full npm test -- --runInBand (539 suites, 3440 tests); npm run build:test; obsidian vault=test plugin:reload id=tasknotes; live FilterService smoke confirming nested query predicate evaluation with incomplete-condition skipping, status.isCompleted, 7 user-field properties, 1 agenda day, 37 first-day tasks, and 4940 overdue tasks; obsidian vault=test dev:errors; git diff --check; and .ops mdbase validate ..
  • 2026-05-19 Bases filter-default extraction full verification passed focused filter-default, Bases task creation, current-file subtask Base, native Bases result-menu, and custom New button tests; npm run typecheck; npm run lint; full npm test -- --runInBand (540 suites, 3443 tests); npm run build:test; obsidian vault=test plugin:reload id=tasknotes; live Bases creation smoke through the actual custom Task List Base view confirming filtered status: open, phase-live tag, and current project link from this.file.asLink(); obsidian vault=test dev:errors; git diff --check; and .ops mdbase validate .. The live smoke emitted a known malformed-fixture frontmatter warning while scanning the vault; the final error buffer was clean.
  • 2026-05-19 Kanban optimistic drag/drop extraction full verification passed focused Kanban drag utility, touch drop-target, drag-image, and swimlane-order tests; npm run typecheck; npm run lint; full npm test -- --runInBand (540 suites, 3449 tests); npm run build:test; obsidian vault=test plugin:reload id=tasknotes; live Kanban smoke opening TaskNotes/Views/kanban-default.base with 25 columns, 25 headers, 387 cards, and 0 stale drag classes; obsidian vault=test dev:errors; git diff --check; and .ops mdbase validate .. The live smoke emitted known VirtualScroller fallback sizing warnings before the final error buffer passed cleanly.
  • 2026-05-19 Calendar event-mount extraction full verification passed focused Calendar event-mount, related-note indicator, list-card width, and linked-hover tests; npm run typecheck; npm run lint; full npm test -- --runInBand (541 suites, 3455 tests); npm run build:test; obsidian vault=test plugin:reload id=tasknotes; live Calendar list smoke opening TaskNotes/Views/calendar-default.base in listWeek with 396 list rows, 396 mounted card rows, 396 full-width card cells, 396 task-card-backed cards, and 0 default rows; obsidian vault=test dev:errors; git diff --check; and .ops mdbase validate .. The live smoke emitted known malformed-fixture frontmatter warnings before the final error buffer passed cleanly.
  • 2026-05-19 Kanban creation-default extraction full verification passed focused Kanban creation default, column creation, Bases New default, custom-field drag coercion, and Bases task-creation tests; npm run typecheck; npm run lint; full npm test -- --runInBand (542 suites, 3461 tests); npm run build:test; obsidian vault=test plugin:reload id=tasknotes; live Kanban creation smoke opening TaskNotes/Views/kanban-default.base, creating TaskNotes/Kanban creation default live smoke 1779150870449.md from the done column through the creation modal, and confirming cached status done with 18 rendered columns and 972 cards; obsidian vault=test dev:errors; git diff --check; and .ops mdbase validate ..
  • 2026-05-19 Calendar initial-date/navigation extraction full verification passed focused Calendar initial-date, date-navigation, recreate-date-preservation, config-snapshot, and data-signature tests; npm run typecheck; npm run lint; full npm test -- --runInBand (543 suites, 3467 tests); npm run build:test; obsidian vault=test plugin:reload id=tasknotes; live Calendar initial-date smoke creating a temporary Base at TaskNotes/Views/calendar-initial-date-smoke-1779151501696.base, loading exactly two tagged scheduled tasks, and confirming the dayGridMonth Calendar opened on January 2031 from the earliest scheduled value; obsidian vault=test dev:errors; git diff --check; and .ops mdbase validate .. The live smoke emitted known malformed-fixture frontmatter warnings before the final error buffer passed cleanly.
  • 2026-05-19 Calendar config-snapshot slice verification passed focused Calendar config snapshot, data signature, agenda sort, and property-event tests, npm run lint, npm run typecheck, npm test -- --runInBand (522 suites, 3320 tests), npm run build:test, obsidian vault=test plugin:reload id=tasknotes, live Calendar smoke opening TaskNotes/Views/calendar-default.base with a rendered FullCalendar instance, 272 events, 15 day cells, and the refresh button, and obsidian vault=test dev:errors. The Calendar smoke emitted known malformed-fixture frontmatter warnings and a Google Calendar provider sync error for _codex/issue-1232/scheduled-today.md; the final error buffer was clean.
  • 2026-05-19 TaskService title-sanitizer slice verification passed focused TaskService, title sanitizer, store-title-in-filename, API filename-format, and creation-default tests, npm run lint, npm run typecheck, npm test -- --runInBand (523 suites, 3323 tests), npm run build:test, obsidian vault=test plugin:reload id=tasknotes, live task-creation smoke confirming unsafe filename characters were removed and normal stored titles stayed preserved in cache, and obsidian vault=test dev:errors.
  • 2026-05-19 TaskService property-change side-effects slice verification passed focused side-effect, TaskService, Bases status-event, null-property display, and Task List drag-control tests, npm run lint, npm run typecheck, npm test -- --runInBand (524 suites, 3327 tests), npm run build:test, obsidian vault=test plugin:reload id=tasknotes, live status-update smoke confirming refreshed cache status and completed date after TaskService.updateProperty, and obsidian vault=test dev:errors. The live smoke emitted known malformed-fixture frontmatter warnings before the final error buffer passed cleanly.
  • 2026-05-19 TaskService property-update planning slice verification passed focused property-update, TaskService, dependency serialization, store-title-in-filename, status-event, and null-property display tests, npm run lint, npm run typecheck, npm test -- --runInBand (525 suites, 3333 tests), npm run build:test, obsidian vault=test plugin:reload id=tasknotes, live property-update smoke confirming due removal, completion-date write, dependency wikilink serialization, and cache refresh through TaskService.updateProperty, and obsidian vault=test dev:errors. The live smoke emitted known malformed-fixture frontmatter warnings before the final error buffer passed cleanly.
  • 2026-05-19 TaskService archive-planning slice verification passed focused archive-planning, TaskService, Google Calendar archive reliability, and status-event tests, npm run lint, npm run typecheck, npm test -- --runInBand (526 suites, 3339 tests), npm run build:test, obsidian vault=test plugin:reload id=tasknotes, live archive/unarchive smoke confirming archive tag/cache state toggles with movement disabled, and obsidian vault=test dev:errors.
  • 2026-05-19 TaskService time-tracking planning slice verification passed focused time-tracking planning, TaskService, status-widget, Pomodoro task-switch, and calendar time-entry refresh tests, npm run lint, npm run typecheck, npm test -- --runInBand (527 suites, 3344 tests), npm run build:test, obsidian vault=test plugin:reload id=tasknotes, live start/stop time-tracking smoke confirming cache/frontmatter duration cleanup and active-session closure, and obsidian vault=test dev:errors.
  • 2026-05-19 TaskService recurring-planning slice verification passed focused recurring-planning, TaskService completion, context-menu completion-date, repeating-task overdue, recurring overdue, and new-note-per-instance tests, npm run lint, npm run typecheck, npm test -- --runInBand (528 suites, 3353 tests), npm run build:test, obsidian vault=test plugin:reload id=tasknotes, live recurring complete/uncomplete and skip/unskip smoke confirming cache/frontmatter instance arrays and active schedule advancement, and obsidian vault=test dev:errors.
  • 2026-05-19 TaskService blocking-relationship planning slice verification passed focused blocking-relationship, TaskService, context-menu dependency wikilink, create blockedBy, edit-change-state, and modal dependency tests, npm run lint, npm run typecheck, npm test -- --runInBand (529 suites, 3360 tests), npm run build:test, obsidian vault=test plugin:reload id=tasknotes, live blocking relationship smoke confirming reverse blockedBy frontmatter/cache add and removal, and obsidian vault=test dev:errors.
  • 2026-05-19 TaskService delete-time-entry planning slice verification passed focused time-tracking planning, TaskService, status-widget, calendar time-entry refresh, and TimeEntryEditor modal tests, npm run lint, npm run typecheck, npm test -- --runInBand (529 suites, 3363 tests), npm run build:test, obsidian vault=test plugin:reload id=tasknotes, live start/stop/delete time-entry smoke confirming cache/frontmatter entry removal, and obsidian vault=test dev:errors.
  • 2026-05-19 TaskManager task-read slice verification passed focused task identification, task-info assembly, plain markdown discovery, file fallback, cache fallback, native label, and grouped filter tests, npm run lint, npm run typecheck, npm test -- --runInBand (530 suites, 3369 tests), npm run build:test, obsidian vault=test plugin:reload id=tasknotes, live task-identification smoke for tag/property modes, live TaskManager assembly smoke confirming 45 minutes of computed tracked time through the configured time-entries field, and obsidian vault=test dev:errors.
  • The Task List drag/grouping smoke opened TaskNotes/Views/tasks-default.base, rendered 48 task cards with 6 group headers, confirmed 48 reorderable cards/handles, and dev:errors reported no captured errors. These smokes emitted unrelated Google Calendar provider sync noise and malformed-fixture frontmatter warnings before the final error check passed.
  • Phase F focused Jest checks covered TaskCard property access, relationship filtering/sorting, relationship expansion rendering, metadata assembly and metadata-line toggle wiring, render-state/class assembly, completion-state refresh, status/priority primary indicators, secondary badge/dependency controls, title/link rendering, context-menu integration, quick-action handlers, badge/interactive-control helpers, existing translated label mapping, Bases value rendering, subtask view-order inheritance, blocked-task toggles, and dependency display. TaskCard DOM smoke after opening the Bases Kanban view returned cards: 398, contextButtons: 398, metadataProperties: 2537, and relationshipToggles: 70; dev:errors reported no captured errors.
  • The completion-state smoke clicked a live task-card status dot for TaskNotes/this is testing.md and confirmed the card changed from in-progress to done, removed the old status class, added task-card--status-done, preserved project/priority classes, and synced completed title state.
  • The metadata-line adapter smoke clicked a live blocked-by metadata pill for TaskNotes/Archive/this is testing.md and confirmed the card expanded a .task-card__blocked-by container while setting aria-expanded to true.
  • The title-input smoke opened create and edit modals, confirmed title textareas normalized newline input to single-line text, kept one-row inputs, preserved aria labels, and prevented plain Enter.
  • The modal-layout smoke opened the NLP create modal, confirmed details/right-column surfaces started collapsed, expanded with completed animation classes, and collapsed both surfaces again from the same toggle.
  • The focus-guard smoke opened the create modal in mobile mode, confirmed tapped title focus restored the split-container scroll position, and confirmed focusing a text field set the mobile keyboard focus state.
  • The creation-form-state smoke created TaskNotes/Phase F form state live smoke 1779129221875.md through the create modal with temporary defaults and confirmed saved due/scheduled times, context, tag, project, time estimate, and custom user-field frontmatter.
  • The creation-subtask assignment smoke created TaskNotes/Phase F creation subtask parent 1779129710333.md through the create modal, selected TaskNotes/Phase F creation subtask child 1779129710333.md via the subtask selector, and confirmed the child task's projects contained [[Phase F creation subtask parent 1779129710333]].
  • The edit-change-state smoke opened the edit modal for TaskNotes/Phase F edit change-state clean smoke 1779130389542.md, confirmed the test custom field initialized from frontmatter, saved a changed title plus test: new, and confirmed the cache returned the updated title.
  • The edit-form-state smoke opened the edit modal for TaskNotes/Phase F edit form-state smoke 1779130783298.md, confirmed the test custom field initialized from frontmatter through the extracted form-state helper, saved a changed title plus test: new, and confirmed the cache returned the updated title.
  • The edit-subtask smoke opened the edit modal for TaskNotes/Phase F edit subtask parent 1779131231082.md, selected TaskNotes/Phase F edit subtask child 1779131231082.md through the task selector, saved, and confirmed the child task's projects contained [[Phase F edit subtask parent 1779131231082]].
  • The dependency-selector smoke opened the edit modal for TaskNotes/Phase F dependency selector parent 1779132064519.md, selected TaskNotes/Phase F dependency selector blocker 1779132064519.md through the blocked-by task selector, saved, and confirmed the parent task's blockedBy frontmatter contained the selected blocker.
  • Phase F modal-focused Jest checks covered TaskModal action-button bar construction, compact action-icon construction, action-icon state application, action-menu callback wiring, action-value derivation, project item parsing/deduplication/rendering, subtask candidate filtering, selected-state updates, and list rendering, dependency duplicate checks and blocked-by/blocking candidate filtering, shared task-selector opening, organization/dependency and metadata field construction, field rendering/visibility dispatch, user-field state, user-field control construction, details-editor adapter wiring, creation modal initialization, edit-modal unsaved-change behavior, completed-date writes, NLP boolean/wikilink user fields, and HTTP/API custom fields.
  • The create/edit modal smoke opened both modals, returned TaskNotes/Phase F user-field controls edit smoke.md, confirmed configured custom fields rendered in both modals, and verified edit-modal values for the visible test and Deferred user fields. It emitted known test-vault warnings from VirtualScroller fallback sizing and malformed fixture frontmatter before passing.
  • The action-button smoke opened both modals, returned TaskNotes/Phase F action buttons edit smoke.md, confirmed creation button order Save, Cancel, and confirmed edit button order Open note, Archive, Delete, Save, Cancel.
  • The action-icon smoke opened both modals, returned TaskNotes/Phase F action bar edit smoke.md, and confirmed the shared core icon order status, priority, due-date, scheduled-date, recurrence, reminders with focusable button roles in both modals.
  • The action-icon state smoke opened both modals, returned TaskNotes/Phase F action icon state edit smoke.md, and confirmed live active-state, labels, and configured colors for status, priority, due, scheduled, recurrence, and reminder icons.
  • The action-menu smoke opened the create modal, confirmed the due date picker title Set due date, and confirmed menu surfaces for status, priority, recurrence, and reminders.
  • The action-value smoke opened the edit modal for TaskNotes/Phase F action value edit smoke.md and confirmed the recurrence action label Recurrence: Monthly on the 1st.
  • The action-state adapter smoke opened the edit modal for TaskNotes/Phase F action state adapter smoke-3.md, confirmed active status, priority, due, scheduled, recurrence, and reminder icons from modal state, and confirmed the due date action still opened the Set due date picker.
  • The project-helper smoke opened the edit modal for TaskNotes/Phase F project helper edit smoke.md and confirmed a resolved non-unresolved project item for Projects/Phase F Project Helper.md.
  • The project-renderer smoke opened the edit modal for TaskNotes/Phase F project renderer child smoke 1779125431912.md and confirmed one resolved project link, one remove button, and no stray + prefix.
  • The subtask-helper smoke opened the edit modal for TaskNotes/Phase F subtask helper parent smoke.md and confirmed the linked child task rendered as a subtask card with one remove button.
  • The subtask-renderer smoke opened the edit modal for TaskNotes/Phase F subtask renderer parent smoke 1779125798508.md and confirmed the linked child rendered as one task-card-backed subtask row with one remove button.
  • The dependency-helper smoke opened the edit modal for TaskNotes/Phase F dependency helper blocked smoke 1779125072181.md and confirmed one blocked-by dependency rendered as a task-card-backed item with one remove button.
  • The create/update smoke check emitted known dependency-cache warmup and VirtualScroller fallback warnings before passing.
  • Phase G focused Jest checks covered the shared TaskNotes logger, user-safe category messages, debug gating, Bases API diagnostic logging, task-link detection diagnostics, and markdown-widget context diagnostics.