Wothmag07's picture
Doc-MCP Application
1e6a9db
"""SQLite database helpers for document indexing schema."""
from __future__ import annotations
from pathlib import Path
import sqlite3
from typing import Iterable
PROJECT_ROOT = Path(__file__).resolve().parents[3]
DATA_DIR = PROJECT_ROOT / "data"
DEFAULT_DB_PATH = DATA_DIR / "index.db"
DDL_STATEMENTS: tuple[str, ...] = (
"""
CREATE TABLE IF NOT EXISTS note_metadata (
user_id TEXT NOT NULL,
note_path TEXT NOT NULL,
version INTEGER NOT NULL DEFAULT 1,
title TEXT NOT NULL,
created TEXT NOT NULL,
updated TEXT NOT NULL,
size_bytes INTEGER NOT NULL DEFAULT 0,
normalized_title_slug TEXT,
normalized_path_slug TEXT,
PRIMARY KEY (user_id, note_path)
)
""",
"CREATE INDEX IF NOT EXISTS idx_metadata_user ON note_metadata(user_id)",
"CREATE INDEX IF NOT EXISTS idx_metadata_updated ON note_metadata(user_id, updated DESC)",
"CREATE INDEX IF NOT EXISTS idx_metadata_title_slug ON note_metadata(user_id, normalized_title_slug)",
"CREATE INDEX IF NOT EXISTS idx_metadata_path_slug ON note_metadata(user_id, normalized_path_slug)",
"""
CREATE VIRTUAL TABLE IF NOT EXISTS note_fts USING fts5(
user_id UNINDEXED,
note_path UNINDEXED,
title,
body,
tokenize='porter unicode61',
prefix='2 3'
)
""",
"""
CREATE TABLE IF NOT EXISTS note_tags (
user_id TEXT NOT NULL,
note_path TEXT NOT NULL,
tag TEXT NOT NULL,
PRIMARY KEY (user_id, note_path, tag)
)
""",
"CREATE INDEX IF NOT EXISTS idx_tags_user_tag ON note_tags(user_id, tag)",
"CREATE INDEX IF NOT EXISTS idx_tags_user_path ON note_tags(user_id, note_path)",
"""
CREATE TABLE IF NOT EXISTS note_links (
user_id TEXT NOT NULL,
source_path TEXT NOT NULL,
target_path TEXT,
link_text TEXT NOT NULL,
is_resolved INTEGER NOT NULL DEFAULT 0,
PRIMARY KEY (user_id, source_path, link_text)
)
""",
"CREATE INDEX IF NOT EXISTS idx_links_user_source ON note_links(user_id, source_path)",
"CREATE INDEX IF NOT EXISTS idx_links_user_target ON note_links(user_id, target_path)",
"CREATE INDEX IF NOT EXISTS idx_links_unresolved ON note_links(user_id, is_resolved)",
"""
CREATE TABLE IF NOT EXISTS index_health (
user_id TEXT PRIMARY KEY,
note_count INTEGER NOT NULL DEFAULT 0,
last_full_rebuild TEXT,
last_incremental_update TEXT
)
""",
)
class DatabaseService:
"""Manage SQLite connections and schema initialization."""
def __init__(self, db_path: str | Path | None = None):
self.db_path = Path(db_path) if db_path else DEFAULT_DB_PATH
def _ensure_directory(self) -> None:
self.db_path.parent.mkdir(parents=True, exist_ok=True)
def connect(self) -> sqlite3.Connection:
"""Return a sqlite3 connection with the proper data directory created."""
self._ensure_directory()
conn = sqlite3.connect(self.db_path)
conn.row_factory = sqlite3.Row
return conn
def initialize(self, statements: Iterable[str] | None = None) -> Path:
"""Create all schema artifacts required for indexing."""
conn = self.connect()
try:
with conn: # Transactional apply of DDL
for statement in statements or DDL_STATEMENTS:
conn.execute(statement)
finally:
conn.close()
return self.db_path
def init_database(db_path: str | Path | None = None) -> Path:
"""Convenience wrapper matching the quickstart instructions."""
return DatabaseService(db_path).initialize()
__all__ = ["DatabaseService", "init_database", "DEFAULT_DB_PATH"]