Local-first semantic code search for VS Code — optimized for Python structure and natural-language queries in English and Japanese.
Codex-ready MCP integration: register OwlSpotlight from the sidebar and call owlspotlight.search_code directly from Codex. Claude Code support is coming in the next few days.
Find functions, methods, classes, Python CodeBlocks, routes, tests, and call-heavy logic by describing intent — no need to remember names.
Describe what code does in English or Japanese — OwlSpotlight jumps straight to the highlighted definition.
▶ More clips (startup · search · Git Diff search): DEMO.md
OwlSpotlight lets you search your codebase by describing what the code does — no need to remember names or guess keywords. Type a natural-language query (in English or Japanese) into the VS Code sidebar, and OwlSpotlight finds the matching functions, methods, classes, top-level code blocks, FastAPI routes, and tests, then jumps straight to the definition and highlights it. You can also select a block of code in the editor and search for similar code, limit the search to files you've changed in git, and switch between hybrid, semantic, BM25, and literal keyword modes.
Everything runs locally on 127.0.0.1 — your code never leaves your machine — and the index refreshes automatically as you edit. AI agents can use the same search through the built-in Codex MCP bridge.
Under the hood, OwlSpotlight is more than generic chunk search. Its retrieval engine is NightOwl-CodeEmbedding, a ~150M-parameter code-embedding model I built myself: a bi-encoder on the ModernBERT architecture, fine-tuned for code retrieval from NightOwl, a base model I trained from scratch. OwlSpotlight builds a local semantic index from your code's structure, then combines the model's dense retrieval with lightweight BM25 lexical ranking and literal keyword matching.
| What you need | OwlSpotlight gives you |
|---|---|
| "Where is the FastAPI route that loads users?" | Route-aware Python metadata and hybrid search |
| "Find code like this selected block" | Editor selection search with direct jump |
| "Only search files I changed" | Git changed/untracked-file scope |
| "Search outside functions too" | Python CodeBlock extraction for top-level logic |
| "Use this from Codex" | Codex-ready MCP bridge with owlspotlight.search_code |
| "Keep code private" | Local index/search server on 127.0.0.1 |
- Search modes:
hybrid,semantic,bm25, or literalkeywordmode. - Python static analysis: params, return annotations, decorators, imports, calls, assigned names, docstrings, local call graph, and import dependencies.
- Python CodeBlocks: searches top-level logic outside functions and classes, grouped by the regions between function/class definitions.
- Framework-aware metadata: FastAPI route and pytest symbol hints.
- Search scopes: all files, auto-detected source folders, or a
Git Diffscope where you pick base/head commits from a built-in commit graph and search either the changed functions or the unified diff hunks. - Selection search: right-click selected code and run
OwlSpotlight: Find Similar to Selection. - Automatic incremental indexing: a file watcher refreshes the index whenever supported files change.
- Codex MCP support: register OwlSpotlight directly from the sidebar and use
owlspotlight.search_code,owlspotlight.grep_repo, and compact Agent Activity inside Codex. - Claude Code: support is coming in the next few days.
- Cross-platform setup:
uv+ Python 3.11 on macOS, Linux, and Windows, with CPU, GPU, and MPS support. - Japanese queries: optional Japanese-to-English query translation via the Gemini API.
| Language | Support |
|---|---|
| Python | Stable. Functions, methods, CodeBlocks, AST metadata, FastAPI/pytest hints |
| Java | Functions/methods/classes via Tree-sitter |
| TypeScript / TSX | Functions and class methods via Tree-sitter |
| JavaScript / JSX | Functions and class methods via Tree-sitter |
Prerequisite: install uv. uv can also manage Python 3.11 for you.
- Install from the VS Code Marketplace.
- Open the OwlSpotlight sidebar.
- Click Setup / Start.
- Search in natural language.
Manual command-palette flow:
OwlSpotlight: Setup Python Environment
OwlSpotlight: Start Server
Server logs appear under View -> Output -> OwlSpotlight. OwlSpotlight runs as a background process and never takes over your terminal.
The sidebar keeps the main search bar compact. Click Options to choose:
| Option | Values |
|---|---|
| Language | Python, Java, TypeScript, TSX, JavaScript, JSX |
| Scope | All, Source, Git Diff |
| Mode | Hybrid, Semantic, BM25, Keyword |
| Type | All, Functions, Methods, CodeBlocks |
Source auto-detects folders such as src, app, lib, packages, client, server, backend, and frontend.
Git Diff restricts the search to a git diff. Pick the base and head commits from the built-in commit graph (click a commit to set the base, Shift+Click to set the head; leave both blank to compare HEAD against the working tree), then choose a Diff view:
Functions— only the functions changed in the selected diff.Unified diff— the changed lines, shown as unified diff hunks.
Use Git Diff when you want to review a working-tree change, a branch comparison, or a PR-sized patch by intent, instead of reading a raw diff from top to bottom. OwlSpotlight builds the search corpus from the selected diff range only, so queries like "where was the new retry logic added?" or "why did the MaxSim aggregation change?" surface the changed code that matches your intent.
- Leave base/head blank to compare
HEADwith the working tree, or setmain,origin/main, a tag, or a commit SHA for branch/commit comparisons. Functionsmaps changed line ranges back to the function-level code units they belong to, then searches those units.Unified diffsearches the actual patch hunks — added, removed, and context lines — and results can open in VS Code's native side-by-side diff editor.- All the usual ranking modes apply: use
Hybrid/Semanticfor intent-based review,BM25for lexical terms, andKeywordfor exact identifiers.
Agents can use the same feature through owlspotlight.search_code: set search_target to changed_functions or diff_hunks, and pass diff_base_ref / diff_head_ref for a specific comparison.
Code Diff search keeps the query, the changed hunks, and VS Code's side-by-side diff view in a single workflow.
For Python, OwlSpotlight uses ast first and falls back to Tree-sitter when AST parsing fails — for example, while a file is temporarily broken mid-edit.
Extracted metadata includes:
paramsreturnsdecoratorsimportscallsassigned_namesdocstringframework_tagsrouteslocal_callsexternal_import_callscall_graphimport_dependency
CodeBlocks represent top-level code that lives outside functions and classes. They are grouped by the regions between function/class definitions rather than split aggressively at blank lines.
Start the VS Code OwlSpotlight server first, then run the MCP stdio bridge:
python model_server/mcp_server.pyExample .mcp.json for Cursor and other MCP clients:
{
"mcpServers": {
"owlspotlight": {
"type": "stdio",
"command": "python",
"args": ["/absolute/path/to/owlspotlight/model_server/mcp_server.py"],
"env": {
"OWLSPOTLIGHT_SERVER_URL": "http://127.0.0.1:8000",
"OWLSPOTLIGHT_WORKSPACE": "/absolute/path/to/your/workspace"
}
}
}
}The MCP tool is owlspotlight.search_code. If OWLSPOTLIGHT_WORKSPACE is set, you can call it with just a query. It also accepts the optional arguments directory, file_ext (defaults to auto, which respects .owlignore and git ignore/exclude rules), top_k (default 30), scope, search_mode (default semantic), search_target (functions, changed_functions, or diff_hunks), diff_base_ref, diff_head_ref, force_diff_refresh, and server_url.
Agent searches are mirrored in the OwlSpotlight sidebar as compact activity entries. Use owlspotlight.search_code for semantic discovery, owlspotlight.grep_repo for exact, repository-wide reference checks, owlspotlight.cancel_embedding to stop a running indexing/embedding job, and owlspotlight.mark_results_used to record which ranks or grep hits the agent actually used as evidence. Human feedback is optional: the companion tool owlspotlight.get_human_feedback only comes into play when you explicitly enter query-improvement suggestions in the sidebar.
If an agent can't see owlspotlight.search_code in its available tools, reload or restart the MCP client after updating .mcp.json. As long as the MCP tool is loaded, the agent never needs to inspect mcp_server.py or reverse-engineer the HTTP API.
To avoid hand-editing paths, run OwlSpotlight: Generate Agent Setup from the Command Palette, or click Agent Setup in the sidebar. It can register OwlSpotlight directly with the Codex CLI, create or update the workspace .mcp.json, and copy agent instructions with the current server URL.
- Codex CLI: register the MCP server with
codex mcp add, then restart Codex:
codex mcp add owlspotlight \
--env OWLSPOTLIGHT_SERVER_URL=http://127.0.0.1:8000 \
--env OWLSPOTLIGHT_WORKSPACE=/absolute/path/to/your/workspace \
-- /absolute/path/to/owlspotlight/model_server/.venv/bin/python /absolute/path/to/owlspotlight/model_server/mcp_server.pyTo remove the Codex registration later, use Agent Setup's remove option or run:
codex mcp remove owlspotlight- Cursor: use the project-level
.cursor/mcp.jsonor the global~/.cursor/mcp.json. - Claude Code: support is coming in the next few days.
- Cline: add the same
mcpServers.owlspotlightentry to your MCP settings, and include"disabled": falseif your config requires it.
git clone https://github.com/Shun0212/owlspotlight.git
cd owlspotlight
npm install
npm run compile
npx vsce packageThen install the generated .vsix with Extensions: Install from VSIX....
VS Code Sidebar/Webview
|
| localhost HTTP
v
FastAPI background server
|
|-- Tree-sitter extractors: Java, JS, JSX, TS, TSX
|-- Python AST extractor + Tree-sitter fallback
|-- NightOwl-CodeEmbedding embeddings
|-- FAISS vector index
|-- Lightweight BM25 ranking
|-- Literal keyword matching
|-- Disk + memory incremental cache
| Command | Description |
|---|---|
OwlSpotlight: Setup Python Environment |
Create or update the uv-managed Python environment |
OwlSpotlight: Start Server |
Start the background search server |
OwlSpotlight: Stop Server |
Stop the server |
OwlSpotlight: Code Search |
Open the sidebar search panel |
OwlSpotlight: Find Similar to Selection |
Search for code similar to the selected editor text |
OwlSpotlight: Clear Cache |
Clear the FAISS/index cache |
OwlSpotlight: Remove Virtual Environment |
Delete .venv and start fresh |
| Setting | Default | Description |
|---|---|---|
owlspotlight.modelName |
Shuu12121/NightOwl-CodeEmbedding |
Hugging Face embedding model |
owlspotlight.batchSize |
2 |
Embedding batch size |
owlspotlight.autoStartServer |
false |
Start the server when VS Code opens |
owlspotlight.autoIndexOnFileChange |
true |
Refresh the incremental index when supported files change |
owlspotlight.enableJapaneseTranslation |
false |
Enable Japanese-to-English query translation |
owlspotlight.geminiApiKey |
"" |
Gemini API key for translation |
owlspotlight.cacheSettings.autoClearCache |
false |
Clear the index cache on server start |
owlspotlight.environmentSettings.pythonVersion |
3.11 |
Python version used by uv |
| Problem | Fix |
|---|---|
| Server won't start | Run OwlSpotlight: Setup Python Environment, then check Output -> OwlSpotlight |
uv not found |
Install uv from the official docs, or via Homebrew, WinGet, or pipx |
| No results | Check the server status, language option, scope option, and whether files with that extension exist |
| Changed scope returns nothing | Make sure the workspace is a git repository and there are modified or untracked files |
| Memory issues | Lower owlspotlight.batchSize to 1 |
| Python file has syntax errors | OwlSpotlight falls back to Tree-sitter, so function/method search stays available |
For questions, bug reports, feedback, or collaboration, reach out at owlspotlight@gmail.com.
- Python framework extractors beyond FastAPI/pytest: Django views, SQLAlchemy models, Pydantic schemas.
- Call graph UI panel.
- Import dependency explorer.
- Search history and bookmarks.
- Benchmarks on real repositories.
VS Code 向けのローカル完結型セマンティックコード検索
OwlSpotlight は、関数やクラスの名前を覚えていなくても「そのコードが何をするものか」を説明するだけで目的のコードを見つけられる VS Code 拡張機能です。サイドバーから自然言語(日本語・英語)で入力すると、該当する関数・メソッド・クラス・トップレベルのコードブロック・FastAPI のルート・テストを見つけ出し、その場所へジャンプして定義をハイライト表示します。エディタで選択したコードに似たコードを探したり、検索範囲を Git の変更ファイルだけに絞り込んだり、Hybrid / Semantic / BM25 / 完全一致キーワードの各モードを切り替えたりすることもできます。
検索もインデックス作成もすべて 127.0.0.1 のローカルサーバー上で動くため、コードが外部に送信されることはありません。ファイルを編集すればインデックスも自動で更新されます。さらに、組み込みの Codex MCP ブリッジを介して、AI エージェントからも同じ検索機能を利用できます。
内部の仕組みも、単なるチャンク検索ではありません。検索エンジンには、私が独自に開発したコード埋め込みモデル NightOwl-CodeEmbedding(約 150M パラメータ、ModernBERT アーキテクチャの Bi-Encoder。ゼロから学習させた自作のベースモデル「NightOwl」をコード検索向けにファインチューニングしたもの)を採用しています。Python の構造・呼び出し・import・FastAPI のルート・pytest といった静的解析メタデータに、このモデルによる密ベクトル検索(dense retrieval)・BM25・完全一致キーワード検索を組み合わせて検索します。
Codex MCP 対応: サイドバーから OwlSpotlight を Codex に登録すれば、Codex 内で owlspotlight.search_code を直接呼び出せます。Claude Code への対応も数日中に追加予定です。
- 検索モード:
Hybrid/Semantic/BM25/Keywordを切り替え可能。 - Python の静的解析: params、return annotation、decorator、import、call、代入名、docstring、call graph、import dependency を抽出。
- Python の CodeBlock 検索: 関数やクラスの外にあるトップレベルの処理も検索対象に含めます。
- FastAPI / pytest のヒント: ルートや test / fixture をメタデータとして保持。
- 検索スコープ: 全体、source 系フォルダ、Git の変更済み・未追跡ファイル、またはブランチ比較から作った diff hunk から選択可能。
- 選択範囲からの類似検索: エディタでコードを選択すると、似たコードへジャンプできます。
- 自動の差分インデックス: 対応ファイルが変更されると、サーバー側の差分インデックスを更新します。
- Codex MCP 対応: サイドバーから Codex へ直接登録し、
owlspotlight.search_code/owlspotlight.grep_repoとコンパクトな Agent Activity を利用できます。 - Claude Code: 数日中に対応予定。
- ローカルファースト: 検索もインデックスも
127.0.0.1のローカルサーバーで実行します。 - 日本語クエリ対応: Gemini API を設定すると、日本語のクエリを英語へ翻訳して検索します。
前提: uv をインストールしておいてください。Python 3.11 のインストールも uv に任せられます。
- VS Code Marketplace からインストールします。
- OwlSpotlight のサイドバーを開きます。
- Setup / Start をクリックします。
- 自然言語で検索します。
手動で行う場合は、コマンドパレットから次を実行します:
OwlSpotlight: Setup Python Environment
OwlSpotlight: Start Server
ログは 表示 -> 出力 -> OwlSpotlight に表示されます。バックグラウンドで動作するため、VS Code のターミナルを占有することはありません。
検索バー右側の Options から変更できます。
| Option | 内容 |
|---|---|
| Language | Python, Java, TypeScript, TSX, JavaScript, JSX |
| Scope | All, Source, Git Diff |
| Mode | Hybrid, Semantic, BM25, Keyword |
| Type | All, Functions, Methods, CodeBlocks |
Source は src, app, lib, packages, client, server, backend, frontend などのフォルダを自動的に検出します。
Git Diff は検索対象を git の差分に限定します。内蔵のコミットグラフから base / head のコミットを選び(コミットをクリックで base、Shift+クリックで head を設定。両方空なら HEAD とワーキングツリーを比較)、Diff view を選択します。
Functions— 選択した差分で変更された関数のみ。Unified diff— 変更行を unified diff の hunk として表示。
Git Diff は、作業ツリーの変更、ブランチ比較、PR サイズのパッチを、生の diff を上から順に読む代わりに「どんな意図の変更か」でレビューしたいときに使います。選択した diff 範囲だけを検索対象にするため、リトライ処理を追加した箇所 や MaxSim の集計を変えた差分 のようなクエリで、意図に合う変更済みコードだけを順位付けできます。
- base/head を空にすると
HEADとワーキングツリーを比較します。main、origin/main、タグ、commit SHA を指定するとブランチ / コミット間の比較になります。 Functionsは変更行を含む関数レベルのコード単位へ写像し、そのコード単位を検索します。Unified diffは追加行・削除行・前後の context を含む実際の patch hunk を検索し、結果から VS Code の左右 diff エディタを開けます。- 通常の検索モードもそのまま使えます。意図ベースのレビューは
Hybrid/Semantic、用語一致はBM25、識別子の完全一致はKeywordが向いています。
エージェントからも同じ機能を使えます。owlspotlight.search_code で search_target に changed_functions または diff_hunks を指定し、特定の比較をしたい場合は diff_base_ref / diff_head_ref を渡します。
クエリ、差分 hunk の検索結果、VS Code の左右 diff 表示を同じ流れで確認できます。
先に VS Code 側の OwlSpotlight サーバーを起動してから、MCP の stdio ブリッジを起動します。
python model_server/mcp_server.pyCursor などの MCP クライアント向けの .mcp.json の例:
{
"mcpServers": {
"owlspotlight": {
"type": "stdio",
"command": "python",
"args": ["/absolute/path/to/owlspotlight/model_server/mcp_server.py"],
"env": {
"OWLSPOTLIGHT_SERVER_URL": "http://127.0.0.1:8000",
"OWLSPOTLIGHT_WORKSPACE": "/absolute/path/to/your/workspace"
}
}
}
}MCP ツールは owlspotlight.search_code です。OWLSPOTLIGHT_WORKSPACE を設定していれば、query だけで呼び出せます。このほか、任意の引数として directory、file_ext(デフォルトは auto で、.owlignore と Git の ignore / exclude ルールに従います)、top_k(デフォルト 30)、scope、search_mode(デフォルト semantic)、search_target(functions、changed_functions、diff_hunks)、diff_base_ref、diff_head_ref、force_diff_refresh、server_url も受け取ります。
エージェント経由の検索は、OwlSpotlight サイドバーにコンパクトなアクティビティとして表示されます。意味的な検索には owlspotlight.search_code、リポジトリ全体での厳密な参照確認には owlspotlight.grep_repo、実行中のインデックス作成・埋め込み処理の停止には owlspotlight.cancel_embedding、実際に根拠として使った順位や grep の該当箇所の記録には owlspotlight.mark_results_used を使います。人間によるフィードバックは任意です。サイドバーで改善案を明示的に入力した場合にのみ、追加の MCP ツール owlspotlight.get_human_feedback を通じてエージェントが取得できます。
エージェントの利用可能なツール一覧に owlspotlight.search_code が表示されない場合は、.mcp.json を更新したあとに MCP クライアントを再読み込みまたは再起動してください。MCP ツールさえ読み込まれていれば、エージェントが mcp_server.py を読んだり HTTP API を解析したりする必要はありません。
パスを手作業で書き換えたくない場合は、コマンドパレットの OwlSpotlight: Generate Agent Setup、またはサイドバーの Agent Setup を使ってください。Codex CLI への直接登録、現在のサーバー URL と絶対パスを埋め込んだワークスペースの .mcp.json の作成・更新、エージェント向け指示のコピーが行えます。
- Codex CLI:
codex mcp addで MCP サーバーを登録してから、Codex を再起動してください:
codex mcp add owlspotlight \
--env OWLSPOTLIGHT_SERVER_URL=http://127.0.0.1:8000 \
--env OWLSPOTLIGHT_WORKSPACE=/absolute/path/to/your/workspace \
-- /absolute/path/to/owlspotlight/model_server/.venv/bin/python /absolute/path/to/owlspotlight/model_server/mcp_server.pyあとで Codex への登録を解除する場合は、Agent Setup の削除オプションを使うか、次を実行します:
codex mcp remove owlspotlight質問・不具合報告・フィードバック・共同開発などは、owlspotlight@gmail.com までご連絡ください。
npm install
npm run compile
npm run lint
npm test
python3 -m unittest model_server.tests.test_extractorsMIT


