Commit Graph

24 Commits

Author SHA1 Message Date
lucaronin
094e806b13 feat: title = filename — wikilink resolution + slug collision detection
- Wikilink resolution order: filename stem (primary) → alias → title (fallback)
- Slug collision detection: auto-suffix (-2, -3, etc.) on note creation
- Add slugCollides utility for frontend collision checking
- resolveNewNote accepts entries param for collision-aware creation
- Title editing via H1 heading already triggers file rename (existing flow)
- Update docs/ARCHITECTURE.md with migrate_to_flat_vault command

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
2026-03-15 19:50:22 +01:00
lucaronin
37a2bd501f docs: fix Mermaid syntax error in Vault Cache diagram
VaultEntry[] inside ([...]) causes parse error — brackets not allowed
in stadium-shape node labels. Changed to 'VaultEntry list ready'.
2026-03-14 09:31:11 +01:00
lucaronin
2b33536a68 docs: convert remaining ASCII diagrams to Mermaid + add Mermaid rule to CLAUDE.md
ARCHITECTURE.md:
- System Overview → flowchart (React Frontend / Rust Backend / External Services)
- MCP Server Architecture → flowchart (index.js, vault.js, ws-bridge, transports)
- WebSocket Bridge → flowchart LR (Frontend ↔ ws-bridge ↔ vault)
- Vault Cache Three Strategies → flowchart (full scan / incremental / cache hit)
- Auto-Save Flow → flowchart LR
- Git Sync Flow → flowchart TD (auto-sync + manual commit paths)

CLAUDE.md:
- Added 'Documentation Diagrams' section: Mermaid preferred for all new diagrams,
  convert ASCII on sight, exception for spatial wireframe layouts
2026-03-13 19:22:36 +01:00
lucaronin
1b0f7d71d4 docs: add Mermaid diagrams to ARCHITECTURE and ABSTRACTIONS
- Three Representations flowchart (Filesystem → Cache → React state)
- Startup Sequence diagram (Tauri → App → VaultLoader → Editor)
- AI Agent Event Flow sequence diagram (NDJSON stream + MCP tool calls)
- Search & Indexing flowchart (full vs incremental, three search modes)
- Markdown-to-BlockNote pipeline flowchart (load path)
- BlockNote-to-Markdown pipeline flowchart (save path)
- VaultEntry class diagram (with TypeDocument + Frontmatter relationships)
2026-03-13 19:12:20 +01:00
lucaronin
0e265dc848 feat: add Playwright smoke tests, data-tab-path attr, store full VaultEntry in closed tab history
- Refactor useClosedTabHistory to store full VaultEntry (not stub) for reliable reopening
- Add data-tab-path attribute to TabItem for precise Playwright selectors
- Add 2 Playwright smoke tests: single close/reopen and empty-history no-op
- Update ARCHITECTURE.md and ABSTRACTIONS.md with closed tab history docs

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-03-12 00:54:48 +01:00
lucaronin
f53829f3fb docs: add trash management design file and update ARCHITECTURE.md
Add batch_delete_notes and empty_trash to Tauri IPC commands table
(62 → 64 total). Create placeholder design file for the feature.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-03-12 00:33:44 +01:00
lucaronin
ba5ba58c6b fix: reload vault invalidates cache and rescans from filesystem
Reload Vault (Cmd+K) now calls the new `reload_vault` Tauri command which
deletes the cache file before scanning, guaranteeing a full filesystem
rescan. Previously it called `list_vault` which used incremental git-based
cache updates that could miss recent changes (e.g. trashing a note then
reloading showed stale data).

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-03-09 11:14:34 +01:00
lucaronin
010d2c3949 fix: disk-first writes in useEntryActions, document three-layer model
Move updateEntry() calls after handleUpdateFrontmatter/handleDeleteProperty
in handleCustomizeType, handleRenameSection, and handleToggleTypeVisibility
so React state only updates after the disk write succeeds. This prevents
state-disk divergence when writes fail.

Expand ARCHITECTURE.md "Three representations, one authority" section with
ownership rules, invariants table, and recovery mechanisms. Add
reload_vault_entry to the commands table (62 total).

Add Playwright smoke test for Reload Vault in Cmd+K palette.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-03-09 00:52:56 +01:00
lucaronin
9cc9ff80d8 refactor: remove hardcoded RELATIONSHIP_KEYS — detect wikilink fields dynamically
Any frontmatter field whose value contains [[wikilinks]] now renders as a
relationship chip automatically. Fields with plain-text values always render
as editable properties, even if they were formerly hardcoded relationship keys.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-03-09 00:33:57 +01:00
lucaronin
02611f6d41 feat: move vault cache to ~/.laputa/cache/ and make writes atomic
Cache files are now stored outside the vault directory at
~/.laputa/cache/<vault-hash>.json, preventing them from polluting
the user's git repo. Writes use atomic tmp+rename to avoid corruption.
Legacy .laputa-cache.json files are auto-migrated and cleaned up on
first run.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-03-08 23:04:14 +01:00
lucaronin
4787673841 docs: add design principles and semantic field conventions
- ARCHITECTURE.md: new Design Principles section covering filesystem as
  source of truth, convention over configuration, no hardcoded exceptions,
  AI-first knowledge graph, and three-representation model
- ABSTRACTIONS.md: design philosophy intro + semantic field names table
  documenting all conventional frontmatter fields and their UI behavior

Convention over configuration principle explicitly noted as serving
AI-readability: shared conventions make vaults navigable by AI agents
without bespoke per-vault instructions.
2026-03-08 19:58:28 +01:00
lucaronin
87090cebc3 feat: show type instances in inspector Properties panel
When viewing a Type note (e.g. "Project"), the Properties panel now shows
an Instances section listing all notes of that type, sorted by modified_at
descending. Trashed instances are excluded, archived instances are dimmed.
Display capped at 50 with count badge for large collections.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-03-08 18:14:14 +01:00
lucaronin
bb42ebbdc1 docs: update 'Is A' → 'type:' throughout — type: is now canonical
The frontmatter field for entity type is now 'type:' (not 'Is A:').
The Rust parser accepts both via serde alias, but all documentation,
examples, and new code should use 'type:'.

Updated: ABSTRACTIONS.md, ARCHITECTURE.md, PROJECT-SPEC.md, GETTING-STARTED.md
2026-03-08 18:03:02 +01:00
lucaronin
f136fd57d6 docs: add config/ vault type to architecture and abstractions
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-03-07 12:42:56 +01:00
lucaronin
d3a2951bc7 docs: update ARCHITECTURE, ABSTRACTIONS, GETTING-STARTED to reflect current codebase
Updated all three docs to reflect significant features added since they were last written:
- AI agent panel (Claude CLI subprocess with tool execution + NDJSON streaming)
- Vault cache system (git-based incremental caching in cache.rs)
- Theme system (vault-based themes, useThemeManager, ThemePropertyEditor)
- Search & indexing (qmd integration, keyword/semantic/hybrid modes)
- Pulse view (git activity feed with pagination)
- GitHub OAuth (device flow, vault clone/create)
- Vault management (multi-vault, vault config, onboarding, WelcomeScreen)
- Raw editor mode (CodeMirror 6 alternative)
- Command palette (Cmd+K registry)
- Auto-sync & conflict resolution

Also added mandatory docs-update rule to CLAUDE.md: docs/ files must be
updated in the same commit as significant feature changes.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-03-07 04:09:23 +01:00
lucaronin
2bd9cd91dd docs: update architecture with full MCP server tool surface and auto-registration
- Document all 14 MCP tools with params
- Add auto-registration flow (Claude Code + Cursor configs)
- Document dual WebSocket bridge (tool port 9710, UI port 9711)
- Add Rust MCP module details (spawn, register, upsert)
- Update startup sequence with MCP initialization steps
- Add register_mcp_tools to Tauri IPC commands table

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-02-28 20:18:21 +01:00
Luca Rossi
5941f16d06 refactor: decompose Editor.tsx, NoteList.tsx, Sidebar.tsx — CodeScene hotspots (#126)
* refactor: decompose Editor.tsx into focused subcomponents and hooks

Extract from the monolithic Editor component (cc=35, 213 LoC, score 7.82):
- useDiffMode hook: diff state + toggle/commit-diff handlers
- useEditorFocus hook: new-note focus event listener
- editorSchema: WikiLink spec + BlockNote schema (module-level)
- SingleEditorView: BlockNote editor + suggestion menus
- EditorContent: breadcrumb bar + diff/editor/loading views
- EditorRightPanel: AI chat / Inspector panel switching
- suggestionEnrichment util: shared enrichment logic (eliminates duplication)

Editor.tsx is now 10.0 code health (was 7.82). All 25 existing tests pass.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>

* refactor: extract standalone functions from NoteList and Sidebar to reduce cc

NoteList: extract createNoteStatusResolver and toggleSetMember from
NoteListInner (cc 13→8, score 9.04→9.38).
Sidebar: extract applyCustomization from Sidebar (cc 10→7, score 9.09→10.0).

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>

* test: add tests for useDiffMode, useEditorFocus, and suggestionEnrichment

Cover extracted hook/utility logic: diff toggle/reset, editor focus event
listener with adaptive timing, and suggestion item enrichment pipeline.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>

* docs: update architecture for editor decomposition and write .claude-done

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>

---------

Co-authored-by: Claude Opus 4.6 <noreply@anthropic.com>
Co-authored-by: github-actions[bot] <41898282+github-actions[bot]@users.noreply.github.com>
2026-02-27 15:27:25 +01:00
Luca Rossi
192b5ee080 Merge pull request #21 from refactoringhq/task/refactor-vault-rs
refactor: split vault.rs into focused submodules (CodeScene 7.29 → 10.0)
2026-02-24 00:03:22 +01:00
lucaronin
017120990f docs: update ARCHITECTURE.md with vault module structure
Add new "Vault Module Structure" section documenting the 6 submodules,
their responsibilities, and CodeScene health scores.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-02-23 22:37:31 +01:00
lucaronin
536e7b628f chore: update docs and .claude-done summary
- ARCHITECTURE.md: document modified note indicators in NoteList, TabBar, StatusBar
- .claude-done: task completion summary

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-02-23 22:35:10 +01:00
lucaronin
40061a5baa docs: update architecture and add completion summary
Update ARCHITECTURE.md to document react-virtuoso virtual rendering
in NoteList for large vault performance.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-02-23 21:56:25 +01:00
Luca Rossi
9aa00c9c8b feat: auto-build, GitHub Release, and in-app updater (#14)
* ci: auto-release workflow on merge to main

Rewrite .github/workflows/release.yml to trigger on every push to main
instead of manual tag pushes. The workflow now:

- Computes version as 0.YYYYMMDD.GITHUB_RUN_NUMBER
- Builds aarch64-apple-darwin and x86_64-apple-darwin in parallel
- Merges them into a universal binary using lipo
- Creates a universal .dmg and signed updater tarball
- Generates latest.json with per-arch and universal platform entries
- Publishes a GitHub Release with auto-generated release notes
- Updates a GitHub Pages release history site (gh-pages branch)

Product decisions:
- Universal binary approach: copy arm64 .app as base, lipo the main
  executable, keep everything else from arm64 (shared frameworks are
  architecture-independent). This is the standard Tauri pattern.
- Per-arch updater tarballs are also uploaded so the Tauri updater can
  download the correct arch-specific build (smaller download).
- Release notes are auto-generated from git log since last tag.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>

* ci: github pages with release history

Use peaceiris/actions-gh-pages@v4 to deploy a release history site.
The page fetches releases.json (also deployed) and renders each release
with date, notes, and download links for .dmg files.

This handles the gh-pages branch creation automatically on first run.
The page is available at https://refactoringhq.github.io/laputa-app/

Product decision: used fetch() to load releases.json at runtime instead
of inlining it, which is cleaner and avoids shell escaping issues with
release note content. The releases.json is deployed alongside index.html.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>

* feat: in-app update notification UI

Replace the old window.confirm updater with a proper React-based
update notification system:

- useUpdater hook now exposes state machine (idle → available →
  downloading → ready) and actions (startDownload, openReleaseNotes,
  dismiss)
- UpdateBanner component renders at the top of the app shell:
  - "Available" state: shows version, Release Notes link, Update Now
    button, dismiss X
  - "Downloading" state: animated spinner, progress bar with percentage
  - "Ready" state: Restart Now button to apply the update
- Silently checks on startup after 3s delay; fails silently on
  network errors or 404
- Release Notes link opens the GitHub Pages release history site

Product decisions:
- Banner at top of app (not a modal) — non-intrusive, visible but
  not blocking. User can dismiss and continue working.
- Progress bar shows during download so user knows it's working.
- Separate "Restart Now" state after download so user controls when
  the app restarts (they may have unsaved work).

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>

* test: updater component tests

Rewrite useUpdater hook tests and add UpdateBanner component tests:

Hook tests (10 cases):
- Starts in idle state
- Does nothing when not in Tauri
- Checks for updates after 3s delay
- Stays idle when no update available
- Transitions to available when update found
- Handles missing release body gracefully
- Stays idle on network error (fails silently)
- Dismiss returns to idle
- openReleaseNotes opens correct URL
- startDownload transitions through downloading to ready

Component tests (10 cases):
- Renders nothing when idle
- Renders nothing on error
- Shows version and buttons when available
- Update Now calls startDownload
- Release Notes calls openReleaseNotes
- Dismiss button works
- Shows progress bar during download
- Shows 0% at start of download
- Shows restart button when ready
- Restart button calls restartApp

All 457 tests pass.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>

* design: auto-build-release wireframes

Copy ui-design.pen as base. Frames to be added for:

1. Update notification banner (visible state) — horizontal bar at
   top of app shell with version text, Release Notes link, Update
   Now button, and dismiss X
2. Update download progress state — spinner icon, progress bar with
   percentage, downloading text
3. "Restart to apply" state — green accent, version text, Restart
   Now button

Note: Pencil editor was not available during this session. The base
design file is committed; frames will be added when the editor is
accessible. The implemented component (UpdateBanner.tsx) serves as
the source of truth for the design.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>

* docs: update ARCHITECTURE.md with release/update system

Add comprehensive documentation for:
- Release pipeline (4-phase workflow: version → build → release → pages)
- Versioning scheme (0.YYYYMMDD.RUN_NUMBER)
- Universal binary strategy (lipo merge)
- Updater endpoint and latest.json manifest
- In-app update UI state machine
- GitHub Pages release history site

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>

* fix: rustfmt formatting

* fix: rustfmt build.rs

---------

Co-authored-by: Claude Opus 4.6 <noreply@anthropic.com>
2026-02-23 10:50:36 +00:00
lucaronin
bca6b3c8e8 docs: AI chat architecture + fix pre-existing build errors
Update docs/ARCHITECTURE.md with:
- AI Chat system architecture (context picker, streaming, MCP)
- WebSocket bridge protocol
- New files listing and data flow diagrams
- Updated tech stack table

Update mock-tauri.ts with richer AI chat mock responses
(context-aware summarize, expand, grammar responses).

Fix pre-existing TypeScript build errors:
- Add missing snippet/relationships to test VaultEntry fixtures
- Fix string|null → string type mismatches in Sidebar, NoteList, Inspector
- Remove unused imports (cn in Editor, AIChatPanel in App)
- Fix tryParseMarkdownToBlocks Promise cast

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
2026-02-20 23:07:10 +01:00
lucaronin
e7c4563200 feat: add comprehensive documentation and CI/CD pipeline
- Add docs/ with ARCHITECTURE, ABSTRACTIONS, GETTING-STARTED, THEMING
- Add GitHub Actions workflow with automated quality checks:
  • Tests (frontend + Rust)
  • Coverage (70% threshold)
  • Code Health (CodeScene delta analysis)
  • Documentation check (warning only)
  • Lint & Format (ESLint + Clippy + rustfmt)
- Configure coverage in vite.config.ts (v8 provider, 70% threshold)
- Add test:coverage script to package.json
- Install @vitest/coverage-v8
- Update CLAUDE.md with docs-update requirement
- Add CI/CD setup guides in .github/
2026-02-17 13:10:43 +01:00