Skip to content

Find two-character Han words inside filenames - #85

Closed
MaxTheHaters wants to merge 2 commits into
ARahim3:mainfrom
MaxTheHaters:fix/han-filename-search
Closed

MaxTheHaters wants to merge 2 commits into
ARahim3:mainfrom
MaxTheHaters:fix/han-filename-search

Conversation

@MaxTheHaters

@MaxTheHaters MaxTheHaters commented Oct 15, 2026 •

Copy link
Copy Markdown

Summary

Scope discussion: #137. This PR remains a draft pending maintainer agreement on the direction.

FTS5 treats an unspaced Han filename as one token, so 輔導 can miss 學生情緒輔導紀錄.pdf. This adds literal basename lookup for queries containing at least two consecutive Han characters, using the existing name rows without reindexing.

query → existing FTS + meaning search
      → Han-run name prefilter → verify all query components in the basename
      → complete name/stem → partial name → existing content/meaning results

NFKC normalization, mixed case/numbers/extensions, file-kind filters and live rename/delete handling are covered. Literal filename hits point to the name rather than a semantic page. Latin-only queries and code identifier lookup keep their existing rules. This PR contains no interface-localization changes and is independent of #34.

I saw the request for maintainer agreement before implementation in CONTRIBUTING. This draft presents a reproducible fix and evaluation evidence for discussion; it is not a request to bypass that review.

Evidence

Before: name-only evaluation found the expected file first for 4 of 12 queries.
After: the same index finds it first for all 12; no embedding/model fallback is needed.

Same-index evaluation Queries Before R@1 / R@5 / R@10 After R@1 / R@5 / R@10
Han filenames 12 .33 / .33 / .33 1.00 / 1.00 / 1.00
Upstream synthetic 37 .92 / .97 / .97 .92 / .97 / .97
Upstream multilingual 48 .92 / .98 / .98 .92 / .98 / .98
Upstream code 41 1.00 / 1.00 / 1.00 1.00 / 1.00 / 1.00
  • All 126 upstream queries produced byte-identical before/after evaluation output on generated synthetic fixtures. Personal-file sampling was omitted.
  • swift test: 101 passed (95 DigUpKit, 6 LlamaRuntime, including actual model reference vectors). Nine added tests cover internal/two-character lookup, typing/settled results, exact/semantic ranking, duplicate prevention, all terms, kind filters, rename/delete, compatibility/case normalization, code isolation, and an exact name after 1,100 partial names.
  • Apple M2 Pro, 16 GB; 20,000 synthetic filename rows, 2,000 matches, 20 alternating measured CLI runs after two warmups: 輔導 median 15.18 → 59.02 ms (p95 19.48 → 63.12); 情緒輔導 14.70 → 57.25 ms; Latin annual 39.91 → 39.24 ms. Times include process startup and opening the same index; the extra work returns filename hits that were previously absent.
  • Reproduction commands, fixture generator and evaluation JSON are included in docs/han-filename-search.md, scripts/testbed/make_han_filenames.py and evals/han-filenames.json.

Independent regression update (2026-10-20)

  • Add a regression asserting exact Traditional Chinese filenames precede partial filenames and content-only hits, with one result per file, both while typing and after submission, without vectors.
  • The fixture uses the public segment insertion API and an existing standalone FTS keyword. It does not depend on the Han body tokenization or schema migration proposed by shimon-ai-dev in Fix Han full-text matching and preserve tokenizer-budgeted text tails #111; their implementation and body-search tests are not copied here.
  • This update changes tests and documentation only. Interface localization remains in Add English and Traditional Chinese interface localization #34, and production search code is unchanged.
  • Current focused validation: swift test --jobs 1 --filter HanFilenameTests with an isolated Xcode-build-system scratch directory: 10 tests passed. Earlier full-suite/evaluation/performance figures above are historical v0.6.1 evidence, not rerun measurements for this test-only update.

Merge Danger

Door: two-way

No schema, vector version, model, or file-content changes. Existing indexes remain readable by v0.6.1.

Blast Radius: search

Han queries with literal basename matches deliberately rank those above content-only matches. Extra filename verification costs about 44 ms in the measured 20,000-name case. Chinese full-text tokenization, Traditional/Simplified conversion and one-character substring queries are outside this change.

AmirHossein-84 added a commit to AmirHossein-84/DigUp that referenced this pull request Oct 18, 2026
… localization

- SQLite & Search Layer (PRs ARahim3#16, ARahim3#38, ARahim3#82, ARahim3#85, ARahim3#94, ARahim3#111):
  * StatementCache with sqlite3_reset statement recycling and reentrant transactions
  * PRAGMA mmap_size = 1GB, synchronous = NORMAL, cache_size = -64000
  * Zero-copy row.copyBlob direct vector loading into searcher matrix halves
  * Unicode NFC normalization for cross-platform and CJK/accented file paths
  * Chunked IN queries with UNION ALL to eliminate N+1 roundtrips
  * CJK Han character detection, Han text budgeting, and Han-aware snippet generation
  * SIMD8<Float> acceleration in Math+Portable.swift without heap allocations
  * Float16Shim for Intel Mac x86_64 IEEE 754 binary16 compatibility

- Crawler, Rules, Path Normalization & Extractors (PRs ARahim3#33, ARahim3#42, ARahim3#56, ARahim3#60, ARahim3#79, ARahim3#80, ARahim3#86, ARahim3#88, ARahim3#91, ARahim3#101, ARahim3#107, ARahim3#109, Issues ARahim3#67, ARahim3#97, ARahim3#105, ARahim3#127):
  * Fix Windows path slash/drive normalization in DirectoryWalk preventing 0-file crawl
  * Fix case-insensitive folder matching on Windows in FolderSelection
  * Fix Crawler to never treat user-selected search roots (e.g. ~) as project roots
  * Exclude secrets/keys (.env*, .pem, .kdbx, SSH keys, passwd) in Rules
  * Honor standard CACHEDIR.TAG 43-byte signature when crawling
  * Skip build/intermediate directories (.venv, target, .build, .next, dist, bin, obj)
  * Drop FileProvider download status lookups for 10-50x faster cloud folder crawls
  * OfficeText extractor for .xlsx, .pptx, .ods, .odp XML documents
  * Headless LibreOffice .doc extractor on Linux and local Notion SQLite workspace extractor
  * Safe typed CGPDFDictionaryGetString for PDF metadata preventing crashes
  * Preserve OCR keywords on image-only PDFs
  * Outlook PST reader utility crate in pst/

- Indexing Pipeline & Runtime (PRs ARahim3#49, ARahim3#53, ARahim3#62, ARahim3#64, ARahim3#71, ARahim3#72, ARahim3#114, Issue ARahim3#3):
  * Batched document text embeddings (up to 16 docs per pass)
  * Cumulative IndexProgress tracking across multi-pass indexing
  * DocumentCache for extracted chunks to prevent redundant file disk reads
  * Linux URLSession SIGABRT fix in FileFetcher
  * ImageLoader parallel prefetching and batched image embeddings
  * Apple Neural Engine CoreML video frame encoding support
  * Scoped incremental subtree sync when changed paths are known
  * Autoreleasepool wrapping in background worker extraction to eliminate memory leaks

- Daemon, Lifecycle & Policies (PRs ARahim3#24, ARahim3#27, ARahim3#31, ARahim3#36, ARahim3#51, ARahim3#82, Issues ARahim3#22, ARahim3#68):
  * HelperRestartPolicy for clean stop/resume transitions
  * Backlog starvation recovery and --resume-pending in IndexService
  * Configurable indexing hours window policy
  * Opt-in Low Power Mode indexing to protect laptop thermals and battery
  * Win32 OpenProcess(SYNCHRONIZE) parent monitor to prevent zombie helpers on Windows
  * Correct 0-hit search behavior when all search roots are removed

- UI, Cross-Platform Shell, Localization & Build (PRs ARahim3#15, ARahim3#20, ARahim3#37, ARahim3#39, ARahim3#58, ARahim3#65, ARahim3#74, ARahim3#81, ARahim3#84, ARahim3#112):
  * DigUpLocalization framework with en, zh-Hans, zh-Hant string catalogs
  * AppSearch engine and launcher for macOS App and Tauri desktop shells
  * KeyCommands and QuickLookController shared handling
  * Preserved search field text during IME composition
  * Search panel fade transitions and @observable code editor selection
  * Hardened build scripts with pinned SHA-256 vendor checksum verification
@ARahim3

ARahim3 commented Oct 21, 2026

Copy link
Copy Markdown
Owner

Thanks @MaxTheHaters, the problem is real (I said as much in #4) and your eval shows it well. I'm going to fix it in the tokenizer rather than with a name scan: FTS5's trigram tokenizer, or an ICU one, so Chinese, Japanese and Thai match inside names and inside documents alike, measured with a Chinese eval. That's a one-time schema change, which is why I'd rather not add a second path first. Closing the PR; your fixture generator and queries will be useful when I get there.

@ARahim3 ARahim3 closed this Oct 21, 2026
@ARahim3 ARahim3 added the enhancement New feature or request label Oct 21, 2026
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

enhancement New feature or request

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants