@autorag/librarian 2.10.6 → 2.12.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (86) hide show
  1. package/NOTICE +14 -0
  2. package/README.md +52 -10
  3. package/dist/agent/agent.d.ts +70 -2
  4. package/dist/agent/answer-citations.d.ts +34 -2
  5. package/dist/agent/answer-guidelines.d.ts +24 -3
  6. package/dist/agent/ask-user.d.ts +8 -0
  7. package/dist/agent/automation-tool.d.ts +45 -0
  8. package/dist/agent/citation-links.d.ts +23 -0
  9. package/dist/agent/citation-numbers.d.ts +68 -0
  10. package/dist/agent/citation-relevance.d.ts +37 -0
  11. package/dist/agent/conversation-queries.d.ts +31 -0
  12. package/dist/agent/convert-tool.d.ts +28 -0
  13. package/dist/agent/evidence-persistence.d.ts +17 -11
  14. package/dist/agent/index.d.ts +1 -0
  15. package/dist/agent/intent-tracing.d.ts +33 -0
  16. package/dist/agent/mcp-client.d.ts +27 -0
  17. package/dist/agent/permission-gate.d.ts +78 -0
  18. package/dist/agent/permission-judgment.d.ts +72 -0
  19. package/dist/agent/permission-paths.d.ts +23 -0
  20. package/dist/agent/pi-session.d.ts +8 -0
  21. package/dist/agent/query-routing.d.ts +14 -17
  22. package/dist/agent/search-documents.d.ts +1 -1
  23. package/dist/agent/search-progress.d.ts +96 -0
  24. package/dist/agent/self-config.d.ts +2 -0
  25. package/dist/agent/user-requests.d.ts +52 -0
  26. package/dist/agent/welcome-header.d.ts +35 -0
  27. package/dist/automation/config.d.ts +48 -0
  28. package/dist/automation/daemon.d.ts +31 -0
  29. package/dist/automation/dispatch.d.ts +13 -0
  30. package/dist/automation/run-agent.d.ts +22 -0
  31. package/dist/automation/run.d.ts +32 -0
  32. package/dist/automation/service.d.ts +61 -0
  33. package/dist/cli/commands/automate.d.ts +2 -0
  34. package/dist/cli/commands/setup.d.ts +2 -0
  35. package/dist/cli/config.d.ts +21 -0
  36. package/dist/cli/index.d.ts +1 -1
  37. package/dist/cli/index.js +26740 -21094
  38. package/dist/cli/open-target.d.ts +9 -0
  39. package/dist/cli/setup.d.ts +21 -0
  40. package/dist/convert/cli.d.ts +77 -0
  41. package/dist/convert/index.d.ts +4 -0
  42. package/dist/convert/installer.d.ts +84 -0
  43. package/dist/convert/matrix.d.ts +27 -0
  44. package/dist/convert/relate.d.ts +30 -0
  45. package/dist/core.js +32095 -27288
  46. package/dist/datasource/connector-timeouts.d.ts +6 -2
  47. package/dist/datasource/crawler-types.d.ts +1 -1
  48. package/dist/datasource/errors.d.ts +1 -1
  49. package/dist/datasource/index.d.ts +2 -1
  50. package/dist/datasource/skills/factory.d.ts +3 -0
  51. package/dist/datasource/skills/hister/client.d.ts +83 -0
  52. package/dist/datasource/skills/hister/embedding.d.ts +64 -0
  53. package/dist/datasource/skills/hister/index.d.ts +2 -0
  54. package/dist/datasource/skills/hister/setup.d.ts +87 -0
  55. package/dist/datasource/skills/hister/skill.d.ts +63 -0
  56. package/dist/datasource/skills/lazykatok/types.d.ts +2 -2
  57. package/dist/datasource/skills/mailcrawl/types.d.ts +1 -1
  58. package/dist/datasource/skills/obsidian/index.d.ts +4 -6
  59. package/dist/datasource/skills/obsidian/methods.d.ts +13 -17
  60. package/dist/datasource/skills/obsidian/paths.d.ts +24 -24
  61. package/dist/datasource/skills/obsidian/skill.d.ts +10 -15
  62. package/dist/datasource/skills/obsidian/staging.d.ts +50 -0
  63. package/dist/datasource/skills/obsidian/vault-index.d.ts +44 -0
  64. package/dist/dupey/cli.d.ts +18 -0
  65. package/dist/index.d.ts +1 -0
  66. package/dist/index.js +32263 -27429
  67. package/dist/mcp/index.js +32149 -27342
  68. package/dist/minsync/installer.d.ts +1 -1
  69. package/dist/minsync/workspace-lock.d.ts +7 -0
  70. package/dist/process/terminate-tree.d.ts +4 -5
  71. package/dist/profiles/agent-factory.d.ts +60 -0
  72. package/dist/profiles/automation-profiles.d.ts +25 -0
  73. package/dist/profiles/loop-guard.d.ts +23 -0
  74. package/dist/profiles/retrieval-tools.d.ts +24 -0
  75. package/dist/profiles/session-model.d.ts +69 -0
  76. package/dist/profiles.d.ts +13 -0
  77. package/dist/profiles.js +34739 -0
  78. package/dist/retrieval/rerank.d.ts +6 -0
  79. package/licenses/hister-AGPL-3.0-notice.txt +47 -0
  80. package/package.json +9 -3
  81. package/skills/autorag/SKILL.md +79 -5
  82. package/skills/autorag-doctor/SKILL.md +5 -4
  83. package/skills/autorag-lite-setup/SKILL.md +23 -5
  84. package/skills/autorag-setup/SKILL.md +68 -7
  85. package/dist/datasource/skills/obsidian/client.d.ts +0 -15
  86. package/dist/datasource/skills/obsidian/types.d.ts +0 -92
package/NOTICE CHANGED
@@ -24,6 +24,9 @@ License: MIT
24
24
  @modelcontextprotocol/server@2.3.1
25
25
  License: Apache-2.0
26
26
 
27
+ @parcel/watcher@2.6.0
28
+ License: MIT
29
+
27
30
  chardet@2.2.0
28
31
  License: MIT
29
32
 
@@ -51,6 +54,9 @@ License: MIT
51
54
  pdfjs-dist@6.4.299
52
55
  License: Apache-2.0
53
56
 
57
+ pi-ask-user@0.17.0
58
+ License: MIT
59
+
54
60
  pi-discord-remote@0.2.4
55
61
  License: MIT
56
62
 
@@ -77,3 +83,11 @@ licenses/everything-MIT-and-PCRE-BSD.txt
77
83
  ES 1.1.0.38 command-line interface (voidtools)
78
84
  License: MIT
79
85
  licenses/es-MIT.txt
86
+
87
+ Separate programs AutoRAG talks to (not bundled, not distributed, not linked):
88
+ Hister (https://github.com/asciimoo/hister, asciimoo and Hister contributors)
89
+ License: AGPL-3.0-or-later
90
+ AutoRAG ships no Hister code. Users install the unmodified Hister release themselves and AutoRAG only sends
91
+ search requests to its public HTTP API (GET /search, GET /api/config), as a separate program over a network
92
+ socket. AutoRAG does not modify Hister and never hides that Hister is the backend of the `hister` datasource.
93
+ licenses/hister-AGPL-3.0-notice.txt
package/README.md CHANGED
@@ -18,7 +18,7 @@
18
18
 
19
19
  > [!IMPORTANT]
20
20
  > **Looking for the original AutoRAG (RAG AutoML / pipeline optimization tool)?**
21
- > This repository now hosts **AutoRAG 2.0**, a complete reimagining of AutoRAG as a self-evolving librarian agent. The original Python-based AutoRAG — the RAG AutoML tool for automatically finding an optimal RAG pipeline for your data — now lives in the [`legacy/`](legacy/) directory of this repository.
21
+ > This repository now hosts **AutoRAG 2.0**, a complete reimagining of AutoRAG as a personal librarian agent for your office work. The original Python-based AutoRAG — the RAG AutoML tool for automatically finding an optimal RAG pipeline for your data — now lives in the [`legacy/`](legacy/) directory of this repository.
22
22
  >
23
23
  > **The legacy AutoRAG is NOT abandoned.** It continues to be maintained (bug fixes, dependency updates, and PyPI releases via `pip install AutoRAG`) in maintenance mode. Existing users can keep using it exactly as before — see the [legacy README](legacy/README.md) for its documentation, and file issues in this repository as usual. New feature development is focused on AutoRAG Agent (2.0).
24
24
 
@@ -166,7 +166,7 @@ The app is one way in. The same librarian runs everywhere else:
166
166
 
167
167
  Search tools dump file paths and matching lines — forcing you to open files, read context, and synthesize answers yourself.
168
168
 
169
- **AutoRAG Agent is a self-evolving librarian agent.** Built on the [Pi](https://github.com/earendil-works/pi-mono) agent framework, a single configured model searches across multiple retrieval methods, opens source documents directly via `bash` to verify ground truth, and curates answers into clean, numbered knowledge units:
169
+ **AutoRAG Agent is a personal librarian agent that helps with your office work.** Built on the [Pi](https://github.com/earendil-works/pi-mono) agent framework, a single configured model searches your files, mail, chats, and notes in place, opens source documents directly via `bash` to verify ground truth, and curates answers into clean, numbered knowledge units. Because it works for you rather than only on your index, it can also act on your files when you ask, such as organizing, renaming, moving, or editing them with a record of every change:
170
170
 
171
171
  ```text
172
172
  You ask: "What changes were made to the cloud infrastructure contract in Q3?"
@@ -187,7 +187,7 @@ AutoRAG Agent:
187
187
 
188
188
  Three principles drive every design decision in AutoRAG Agent:
189
189
 
190
- 1. **Never migrate your data to search it.** Traditional RAG systems force you to upload, ETL, and duplicate your files into a centralized vector database. AutoRAG Agent federates your data **in place**, querying CLI-native stores (`lazykatok`, `discrawl`, `slacrawl`, `mailcrawl`, `rclone`, `qmd`) where your data already lives. Results retain opaque, source-native identities (`/kakao/...`, `/slack/...`) that preserve local access control and privacy. *(See our [Competitive Landscape Study](docs/competitive-landscape-2026-09.md) on why in-place federation is the durable differentiator).*
190
+ 1. **Never migrate your data to search it.** Traditional RAG systems force you to upload, ETL, and duplicate your files into a centralized vector database. AutoRAG Agent federates your data **in place**, querying CLI-native stores (`lazykatok`, `discrawl`, `slacrawl`, `mailcrawl`, `rclone`) where your data already lives. Results retain opaque, source-native identities (`/kakao/...`, `/slack/...`) that preserve local access control and privacy. *(See our [Competitive Landscape Study](docs/competitive-landscape-2026-09.md) on why in-place federation is the durable differentiator).*
191
191
 
192
192
  2. **Just works — no RAG degree required.** No pipeline tuning, no vector-DB maintenance, and no remote embedding keys required. AutoRAG Agent automatically manages [MinSync](docs/minsync-setup.md) for incremental Change Data Capture (CDC) chunking and provides a local [embedding backend](docs/minsync-setup.md#embedding-backends) out of the box with zero external telemetry. A [remote rerank model](docs/rerank.md) (the hosted Dazzi Models reranker when signed in, else OpenRouter `voyageai/rerank-3-lite`) is an opt-in extra.
193
193
 
@@ -218,8 +218,12 @@ AutoRAG uses `@earendil-works/pi-coding-agent` as the runtime host for model ses
218
218
 
219
219
  The CLI TUI (`autorag tui`) is Pi's interactive mode hosted on the AutoRAG librarian: there is no separate AutoRAG renderer. Pi owns the terminal UI and its native in-session commands — `/login`/`/logout`, `/model`, `/resume`, `/new`, `/tree`, `/compact`, and `/settings` — so provider sign-in and model selection work on first launch even when no AutoRAG model is configured. AutoRAG registers its retrieval tools and runs the two-phase search in the same Pi session, where the model's progress notes, first answer, and final answer are ordinary assistant messages, so resume and two-phase search keep working together.
220
220
 
221
+ A fresh session — at launch and after `/new` (or `/reload`) — opens on AutoRAG's own welcome screen: the AutoRAG logo, the version, and three rotating tips, centered and scaled down to a smaller logo or a plain wordmark on narrow terminals. Pi's own logo, key-hint list, and loaded skills/prompts/extensions listing are hidden by default (`quietStartup: "header"`). A `quietStartup` saved in Pi's global or project `settings.json` wins: `true` removes the banner, `false` brings Pi's resource listing back.
222
+
221
223
  Typing while a search runs works like steering one of Pi's own turns. **Enter** steers the running search: AutoRAG treats the text as a correction of a search that is going wrong, delivers it before the search's next model request (also between phases, where no turn is streaming), cuts in-flight retrieval short so the correction lands promptly, and always runs the verification phase so the answer reflects the correction. **Alt+Enter** queues a new question that runs after the current search answers. **Esc** stops the search instead of letting it continue into its next phase. Pi's registered `/` commands still run during a search; any other line starting with `/` (a path, for example) is a steer like any other text. A query typed after a search answers is a new search in the same session, as before.
222
224
 
225
+ From the moment a question is submitted, a live progress widget sits above the editor: a spinner, the elapsed time, and one line per step the search is running (routing, splitting the question, each retrieval source with its hit count and time, ranking, the first answer, verification). A slow source shows its own running timer, a failing source shows its error text verbatim, and the widget disappears when the answer is final or **Esc** stops the search. While the model streams, Pi's own `Working` loader takes over and the widget keeps only the header and steps. Every tool call also carries a short model-written intent (the `i` argument): Pi's `Working` loader shows the newest one, and `autorag search` and the desktop app receive it as progress, so the model does not write separate progress notes before tool calls.
226
+
223
227
  Update notices are AutoRAG's, not Pi's: `autorag tui` suppresses Pi's "run `pi update`" banner (Pi is a bundled host, not a separate install) and instead checks the published `@autorag/librarian` release, showing a one-line notice in the session when a newer version exists. Set `AUTORAG_NO_UPDATE_CHECK=1` to skip the lookup; `AUTORAG_UPDATE_CHECK_URL` overrides the registry endpoint.
224
228
 
225
229
  ---
@@ -259,6 +263,7 @@ bun add @autorag/librarian
259
263
  - **Rust Toolchain (Optional):** Automatically compiles Jikji (`jikji-cli`) if installed.
260
264
  - **MinSync:** Automatically downloaded and installed into `<workspace>/.autorag/bin` on first run.
261
265
  - **Everything (Windows only, bundled):** The package ships the portable Everything 1.4.1.1032 and its ES 1.1.0.38 CLI (x64 and ARM64, SHA-256 pinned). On Windows, AutoRAG extracts them into `<workspace>/.autorag/everything/` and runs a private, user-level instance that indexes only your configured search roots: no administrator rights, no Everything service, no whole-drive scan, no HTTP/ETP server, and no change to any Everything you already run. Set `"everything": false` in the config to turn it off. macOS and Linux are not affected.
266
+ - **filee-cli (file conversion, automatic):** `autorag setup` and the TUI download the pinned filee-cli release (~85 MB, SHA-256 verified) into `<AUTORAG_HOME>/tools/filee-cli/<version>/`, so the agent can convert between 255 formats offline with `convert_files`. A `filee`/`filee-cli` already on `PATH` is used instead. Set `"filee": { "autoInstall": false }` to forbid the download or `"filee": { "enabled": false }` to remove the tools. Filee fetches its own engines (FFmpeg, Pandoc, LibreOffice, calibre, Ghostscript; hundreds of MB, only when a conversion needs one) on first use.
262
267
  - **FSearch (macOS/Linux only, separate install):** Install [`fsearch-cli`](https://github.com/NomaDamas/fsearch-mac) yourself (e.g. `brew install NomaDamas/fsearch-mac/fsearch-mac` (installs the `fsearch-cli` binary); GPL-2.0, spawned as a separate process, never bundled or linked). On macOS and Linux, AutoRAG builds a per-workspace database at `<workspace>/.autorag/fsearch/` indexing only your configured search roots, and keeps a `fsearch-cli watch` daemon live (FSEvents/inotify) for sub-second name search. It never touches the FSearch app's own database. Without fsearch-cli, name search falls back to a slow bounded filesystem walk. Set `"fsearch": false` in the config to turn it off. Windows is not affected (Everything covers it).
263
268
 
264
269
  ---
@@ -471,7 +476,7 @@ mirrored are kept and not re-parsed on the next run. `onProgress` reports `parse
471
476
  | `autorag health` | Check model provider authentication, token validity, and API reachability |
472
477
  | `autorag models list` | List chat models the pi runtime can resolve (built-ins, `models.json`, custom/extension providers) with provider auth status; never prints credential values |
473
478
  | `autorag update-check` | Compare the running `autorag` against the published npm version (also runs on `autorag tui` launch) |
474
- | `autorag tui` | Open Pi's interactive librarian TUI (`/login`, `/model`, `/resume`, …); `--telegram` / `--whatsapp` / `--discord` add the Telegram / WhatsApp / Discord remote-control bridges |
479
+ | `autorag tui` | Open Pi's interactive librarian TUI (`/login`, `/model`, `/resume`, …); the agent can stop and ask you a multiple-choice or open question through the [`ask_user` tool](docs/ask-user.md); `--telegram` / `--whatsapp` / `--discord` add the Telegram / WhatsApp / Discord remote-control bridges; `--permission-mode ask\|auto\|full` (Shift+Tab, `/permissions`) sets the [approval gate for file changes](docs/permissions.md) |
475
480
  | `autorag duplicates [DIR]` | Read-only scan for exact and near-duplicate document families with `dupey` |
476
481
  | `autorag lite ...` | CLI bootstrap, indexing repair, terminal maintenance, and fallback interface; agents use MCP for normal Lite operation |
477
482
  | `autorag memory inspect` | Render a read-only, path-opaque snapshot of retrieval memory (judged evidence, curated results, evidence chunks, insights); model-free |
@@ -501,6 +506,36 @@ Core Lite tools include `autorag.status`, `autorag.search`,
501
506
  integrated datasources expose additional scoped search tools. Read-only MCP
502
507
  mode omits mutating tools such as refresh and report.
503
508
 
509
+ ## Using external MCP servers and agent skills
510
+
511
+ AutoRAG is also an MCP *client*. Servers listed in the pi agent directory's `mcp.json`
512
+ (`~/.pi/agent/mcp.json`, or `<piAgentDir>/mcp.json` when the agent is given one) are connected
513
+ when a TUI session or a one-shot `autorag search` starts, and their tools reach the model next to
514
+ AutoRAG's own tools. The file uses the format shared by other MCP clients:
515
+
516
+ ```json
517
+ {
518
+ "mcpServers": {
519
+ "filesystem": { "command": "npx", "args": ["-y", "@modelcontextprotocol/server-filesystem", "."] },
520
+ "docs": { "url": "https://example.com/mcp", "headers": { "Authorization": "Bearer ${DOCS_TOKEN}" } }
521
+ }
522
+ }
523
+ ```
524
+
525
+ - **Exposure.** By default a server's tools are reached through the `codemode` tool (the model
526
+ writes a short script that calls them); `"exposure": "direct"` declares them to the model
527
+ like built-in tools, `"deferred"` loads them on demand through `tool_search`, and `"hidden"`
528
+ turns a server off. `description` is shown to the model so it knows when to use the server.
529
+ - **Only the user-level file is read.** A project `.pi/mcp.json` is ignored on purpose: it would
530
+ let any folder AutoRAG starts in choose which processes run.
531
+ - **Failures are reported verbatim.** An invalid entry or a server that fails to start is
532
+ reported at session start with pi's own message; the other servers keep working.
533
+ - **Inside the TUI**, `/mcp` lists servers, reconnects them, signs in to OAuth servers, and
534
+ changes exposure. Pi's `/skill:<name>` commands and `<available_skills>` list also work for
535
+ any agent skill installed under the agent directory.
536
+ - MCP results are data from an external server. AutoRAG tells the model never to follow
537
+ instructions found in them.
538
+
504
539
  ---
505
540
 
506
541
  ## ⚡ AutoRAG Lite: Model-Free Retrieval Engine
@@ -584,7 +619,8 @@ Do not copy or retain the removed `autorag-lite-search` skill.
584
619
  autorag search "your question" --json
585
620
  ```
586
621
  4. **Safety Guidelines for Agents:**
587
- - **Never delete, move, or modify original user documents.**
622
+ - **Setup, diagnostics, indexing, and refresh never modify your documents.** An agent that installs, configures, or repairs AutoRAG (Claude Code, Codex, and similar) must not move, rename, edit, or delete user documents as part of that work. That rule is about those procedures; it is not a limit on the librarian itself, which may organize, create, or modify files in local sessions when the user asks (see `Local File Organization` in the system prompt).
623
+ - **Never permanently delete.** Deletion goes to the OS trash, and every change is listed as old path → new path so it can be undone.
588
624
  - AutoRAG writes index artifacts into `<workspace>/.autorag/` and Jikji's central store (`<OS data dir>/jikji/`, override with `JIKJI_DATA_DIR`). Jikji also drops a `.jikji_agent_map.md` guide into each indexed root.
589
625
  - Never print or leak API keys, tokens, or credential values into stdout or logs.
590
626
 
@@ -605,15 +641,16 @@ AutoRAG Agent connects to external tools and communication platforms using dedic
605
641
  | **Notion** | `notion` | [`notcrawl`](https://github.com/openclaw/notcrawl) CLI | Local page/database/block archive + FTS5 | Lexical FTS5 |
606
642
  | **Email Archives** | `mailcrawl` | [`mailcrawl`](https://github.com/NomaDamas/mailcrawl) CLI | Local Gmail, IMAP, and Maildir storage | BM25, Semantic, Hybrid |
607
643
  | **Local Mail Export**| `mail-export` | Built-in `.mbox` / `.eml` parser | Local filesystem mailboxes | Lexical |
608
- | **Obsidian Vaults** | `obsidian` | [`qmd`](https://github.com/tobi/qmd) CLI | Direct markdown vault indexing | BM25, Semantic |
644
+ | **Obsidian Vaults** | `obsidian` | Indexed with MinSync in its own workspace (no external CLI) | Markdown notes, folder-scopable | Lexical (BM25), Semantic, Scoped |
609
645
  | **GitHub** | `github` | GitHub REST API | In-memory fetched Issues and Pull Requests | Lexical, Scoped |
610
646
  | **GitHub Gists** | `github-gist` | GitHub REST API | Incremental local index of own-account public and permitted secret Gist content/metadata; token not stored | Lexical (BM25), Local Semantic, Scoped |
611
647
  | **Cloud Drives** | `cloud-drive` | [`rclone`](https://rclone.org) CLI | Google Drive (Tier-1), OneDrive, Dropbox, etc. | Incremental Mirror + BM25 |
612
648
  | **Photos & Shots** | `clawgallery` | `clawgallery` CLI | Local screenshot and photo store | Hybrid OCR/Visual Search |
613
649
  | **RSS / News** | `rss` | Native HTTP Poller | RSS 2.0 & Atom feeds (24h deduplication) | Lexical |
614
650
  | **macOS Spotlight** | `spotlight` | Native `mdfind` CLI | macOS system metadata and content index | System Native |
651
+ | **Browser History** | `hister` | [Hister](https://github.com/asciimoo/hister) server (AGPL-3.0-or-later, separate program, HTTP API) | Pages visited in Chrome/Chromium/Firefox, captured by Hister's own extension and indexed by Hister (web pages only; its local-file indexing is never used) | Lexical full-text; optional Semantic via Hister's own embedding endpoint |
615
652
 
616
- For configuration syntax and connector details, see [docs/datasource-skills.md](docs/datasource-skills.md). Non-interactive `sync`/`index` steps get a 30-minute per-connector budget (`connector.indexTimeoutMs`) because first-run imports routinely take minutes; interactive search keeps its 60-second default.
653
+ For configuration syntax and connector details, see [docs/datasource-skills.md](docs/datasource-skills.md). Non-interactive `sync`/`index` steps get a one-hour per-connector budget (`connector.indexTimeoutMs`) because first-run imports routinely take minutes; interactive search keeps its 60-second default.
617
654
 
618
655
  ---
619
656
 
@@ -692,7 +729,8 @@ Deep dive into AutoRAG Agent's architecture, security, and integration guides:
692
729
  - **[Discord Remote Control](docs/discord.md):** Ask the librarian from a Discord channel through a running `autorag tui --discord` session: bot setup, permissions, and limits.
693
730
  - **[Telegram Remote Control](docs/telegram.md):** Ask the librarian from a Telegram chat through a running `autorag tui --telegram` session: setup, commands, and keeping it alive.
694
731
  - **[Datasource Skills Reference](docs/datasource-skills.md):** Full configuration contracts, connection aliases, and connector options.
695
- - **[Jev Decisions](docs/jev-decisions.md):** Jev query pipeline, **on by default** via Dazzi Models when signed in (OpenRouter otherwise): it routes each question to a direct answer (intrinsic knowledge) or local search (everything needing more information; web search is left to the agent after the fast answer), splits multi-part questions into up to five parallel searches (`dazzi/openai/gpt-6-luna` when signed in, else `openrouter/qwen/qwen3.7-flash`), picks which registered datasources to search before the fast answer, and ends the run after the fast answer when that answer is complete. Also covers the `jev` judgment tool, backends (OpenRouter, TypeSafe, Vercel AI Gateway), and how to opt out.
732
+ - **[Apple Calendar & Reminders via EventKit MCP](docs/eventkit-mcp.md):** macOS-only: read Calendar events and Reminders (Google/iCloud/Exchange accounts already in Calendar.app) by running `mcp-server-apple-events` beside `autorag-mcp`. Live, read-only; not indexed.
733
+ - **[Jev Decisions](docs/jev-decisions.md):** Jev query pipeline, **on by default** via Dazzi Models when signed in (OpenRouter otherwise): it routes each question to a direct answer (intrinsic knowledge), local search (everything needing more information; web search is left to the agent after the fast answer), `organize` (move, rename, convert, or sort files and folders), or `extra` (any other action such as committing code; no retrieval), splits multi-part questions into up to five parallel searches (`dazzi/openai/gpt-6-luna` when signed in, else `openrouter/qwen/qwen3.7-flash`), picks which registered datasources to search before the fast answer, and ends the run after the fast answer when that answer is complete. Also covers the `jev` judgment tool, backends (OpenRouter, TypeSafe, Vercel AI Gateway), and how to opt out.
696
734
  - **[Manual QA & Datasource Test Harnesses](docs/manual-qa-datasources.md):** Real-world testing guides for Discord, KakaoTalk, Slack, Notion, and email.
697
735
  - **[Supply Chain Security & License Audits](docs/supply-chain.md):** Software bill of materials (SBOM) and dependency gate policies.
698
736
  - **[Competitive Landscape Study](docs/competitive-landscape-2026-09.md):** In-depth analysis of why in-place federation outperforms centralized RAG.
@@ -705,6 +743,7 @@ Deep dive into AutoRAG Agent's architecture, security, and integration guides:
705
743
  AutoRAG Agent is an open-source project built by the community. We welcome contributions, bug reports, datasource connectors, and ideas!
706
744
 
707
745
  - **Contributing:** Feel free to open an issue or pull request. Start with [CONTRIBUTING.md](CONTRIBUTING.md) — development setup, the `make ci` check we ask for, the `Signed-off-by` trailer every commit needs, and when to run the live end-to-end lanes. [MAINTAINERS](MAINTAINERS) lists who reviews which area. AI tools are allowed; unverified dumps are not — see [AI_POLICY.md](AI_POLICY.md).
746
+ - **Discussions:** For questions, usage help, ideas, and open-ended design talk, please use [GitHub Discussions](https://github.com/Marker-Inc-Korea/AutoRAG/discussions) instead of opening an issue. Keep issues for confirmed bugs and concrete, actionable work.
708
747
  - **Security:** Private vulnerability reports and the response SLA live in [SECURITY.md](SECURITY.md).
709
748
  - **GitHub Contributors:** [View all contributors](https://github.com/Marker-Inc-Korea/AutoRAG/graphs/contributors) on GitHub.
710
749
 
@@ -719,8 +758,10 @@ AutoRAG Agent stands on the shoulders of fantastic open-source projects:
719
758
  - **[Jikji](https://github.com/NomaDamas/jikji)** by [NomaDamas](https://github.com/NomaDamas) — High-performance find-first local document discovery.
720
759
  - **[Everything](https://www.voidtools.com/)** and **[ES](https://github.com/voidtools/ES)** by voidtools (David Carpenter) — Instant Windows file-name indexing and its command-line interface, bundled under the MIT License.
721
760
  - **[FSearch](https://github.com/cboxdoerfer/fsearch)** and **[fsearch-cli](https://github.com/NomaDamas/fsearch-mac)** — Everything-style file-name search for macOS/Linux (GPL-2.0-or-later). Never bundled or linked: users install fsearch-cli separately and AutoRAG spawns it as a separate process (mere aggregation per the FSF GPL FAQ).
761
+ - **[Hister](https://github.com/asciimoo/hister)** by [asciimoo](https://github.com/asciimoo) and contributors — Self-hosted browser web-history search (AGPL-3.0-or-later). Never bundled, linked, copied, or modified: users run Hister as a separate program and AutoRAG only calls its public HTTP search API (mere aggregation). Hister is always named as the backend of the `hister` datasource.
722
762
  - **[dupey](https://github.com/NomaDamas/dupey)** by [NomaDamas](https://github.com/NomaDamas) — Fast duplicate and near-duplicate document family detection.
723
- - **Federated CLI Authors:** External datasource tools [`lazykatok`](https://github.com/changeroa/lazykatok), [`discrawl`](https://github.com/openclaw/discrawl), [`mailcrawl`](https://github.com/NomaDamas/mailcrawl), [`wacrawl`](https://github.com/openclaw/wacrawl), [`telecrawl`](https://github.com/openclaw/telecrawl), [`slacrawl`](https://github.com/openclaw/slacrawl), [`notcrawl`](https://github.com/openclaw/notcrawl), [`qmd`](https://github.com/tobi/qmd), and [`rclone`](https://rclone.org).
763
+ - **[Filee](https://github.com/KnifeLemon/Filee)** by [KnifeLemon](https://github.com/KnifeLemon) — Offline conversion of 240+ file formats (MIT). Never bundled or linked: AutoRAG downloads the SHA-256-pinned [`filee-cli`](https://github.com/NomaDamas/filee-cli) release (NomaDamas' CLI-only redistribution, MIT) into `<AUTORAG_HOME>/tools/filee-cli/` on `autorag setup` / first conversion and spawns it as a separate process. An existing `filee`/`filee-cli` on `PATH` or `filee.binaryPath` wins. Filee downloads its own engines (FFmpeg, Pandoc, LibreOffice, …) on first use.
764
+ - **Federated CLI Authors:** External datasource tools [`lazykatok`](https://github.com/changeroa/lazykatok), [`discrawl`](https://github.com/openclaw/discrawl), [`mailcrawl`](https://github.com/NomaDamas/mailcrawl), [`wacrawl`](https://github.com/openclaw/wacrawl), [`telecrawl`](https://github.com/openclaw/telecrawl), [`slacrawl`](https://github.com/openclaw/slacrawl), [`notcrawl`](https://github.com/openclaw/notcrawl), and [`rclone`](https://rclone.org).
724
765
  - **[kordoc](https://github.com/chrisryugj/kordoc)** by [chrisryugj](https://github.com/chrisryugj) — HWP/HWPX/HWPML, PDF, DOCX and XLSX parsing with nested-table fidelity, used as AutoRAG's default document parser.
725
766
 
726
767
  ---
@@ -765,7 +806,7 @@ Common failures and their fix:
765
806
  | Windows file-name search fails during refresh | `everything-index-failed` | read the ES exit code and stderr in the message, then `autorag refresh --method everything --json` |
766
807
  | Every search does a full local search and verification, even for small talk | `query-route-fallback` | sign in to Dazzi Models with `/login`, or set `OPENROUTER_API_KEY` (Jev routing and decomposition are on by default) |
767
808
 
768
- Native datasource stores stay owned by their CLIs — AutoRAG never rebuilds them. Fix a broken archive with `lazykatok doctor`, `discrawl --json metadata`, `slacrawl --json doctor`, `wacrawl --json doctor`, `telecrawl --json doctor`, `notcrawl doctor`, `qmd status`, or `mailcrawl doctor`, then re-run `autorag refresh --method datasources --json`.
809
+ Native datasource stores stay owned by their CLIs — AutoRAG never rebuilds them. Fix a broken archive with `lazykatok doctor`, `discrawl --json metadata`, `slacrawl --json doctor`, `wacrawl --json doctor`, `telecrawl --json doctor`, `notcrawl doctor`, or `mailcrawl doctor`, then re-run `autorag refresh --method datasources --json`.
769
810
 
770
811
  ---
771
812
 
@@ -776,3 +817,4 @@ Native datasource stores stay owned by their CLIs — AutoRAG never rebuilds the
776
817
  - Production third-party notices and licenses are documented in [`NOTICE`](NOTICE).
777
818
  - The bundled Windows binaries keep their own licenses: Everything (MIT, plus PCRE BSD-3-Clause) in [`licenses/everything-MIT-and-PCRE-BSD.txt`](licenses/everything-MIT-and-PCRE-BSD.txt) and ES (MIT) in [`licenses/es-MIT.txt`](licenses/es-MIT.txt). Everything's source code is not public; AutoRAG redistributes the unmodified voidtools portable ZIPs.
778
819
  - FSearch/fsearch-cli (GPL-2.0-or-later) are **not** distributed with AutoRAG: no code is copied, linked, or bundled. Users install fsearch-cli themselves and AutoRAG communicates with it only through its command-line interface and daemon socket — separate programs, per the [FSF mere-aggregation FAQ](https://www.gnu.org/licenses/gpl-faq.html#MereAggregation). Source: https://github.com/NomaDamas/fsearch-mac.
820
+ - Hister (AGPL-3.0-or-later) is **not** distributed with AutoRAG: no Hister code is copied, linked, bundled, or modified. Users install an unmodified Hister release themselves and AutoRAG talks to that separate process only over its public HTTP API. Notice: [`licenses/hister-AGPL-3.0-notice.txt`](licenses/hister-AGPL-3.0-notice.txt). If you run Hister as a service for other people, AGPL section 13 applies to you as its operator.
@@ -1,5 +1,6 @@
1
1
  import type { Agent, AgentTool } from "@earendil-works/pi-agent-core";
2
2
  import type { Api, ImageContent, Model } from "@earendil-works/pi-ai";
3
+ import { type FileeCliOptions, type FileeConvertRequest } from "../convert/index.js";
3
4
  import { type DatasourceRetryOptions } from "../datasource/retry.js";
4
5
  import type { DatasourceIndexResult, DatasourceSkill } from "../datasource/types.js";
5
6
  import { type DupeyCliOptions } from "../dupey/index.js";
@@ -15,10 +16,12 @@ import { RetrievalEngine } from "../retrieval/engine.js";
15
16
  import { RetrievalMethodRegistry } from "../retrieval/registry.js";
16
17
  import type { DatasourceCatalogEntry } from "../retrieval/selection.js";
17
18
  import type { RetrievalDiagnostic, RetrievalOptions, RetrievalResult } from "../retrieval/types.js";
19
+ import { type ConvertFilesDetails } from "./convert-tool.js";
18
20
  import { type DatasourceAgentSkill } from "./datasource-skill.js";
19
21
  import { type ScanDuplicateDocumentsDetails } from "./dupey-tool.js";
20
22
  import { type JevToolOptions } from "./jev-extension.js";
21
23
  import { type JikjiFindProviderResult } from "./jikji-find-tool.js";
24
+ import { PermissionController, type PermissionMode } from "./permission-gate.js";
22
25
  import { type AutoRAGPiInteractiveRuntime, type AutoRAGPiSession } from "./pi-session.js";
23
26
  import { type RefreshProgressCounts, type RefreshProgressPhase } from "./refresh-progress.js";
24
27
  import { type SearchDocumentDiagnostic, type SearchDocumentsResponse, type SearchDocumentsStreamEvent } from "./search-documents.js";
@@ -256,6 +259,12 @@ export interface AutoRAGAgentOptions {
256
259
  autoRefresh?: AutoRefreshOptions;
257
260
  parserOptions?: DefaultParserRegistryOptions;
258
261
  dupey?: DupeyCliOptions | false;
262
+ /**
263
+ * Filee command line behind `convert_files` and `list_file_conversions`.
264
+ * `false` leaves both tools out. The duplicate-family check on converted
265
+ * copies follows `dupey`.
266
+ */
267
+ filee?: FileeCliOptions | false;
259
268
  /**
260
269
  * Jev (TypeSafe's judgment model: typed questions in, calibrated
261
270
  * probabilities out). When set, the two-phase search asks Jev before the
@@ -345,6 +354,8 @@ export interface AutoRAGAgentOptions {
345
354
  * a launch.
346
355
  */
347
356
  updateNotice?: () => Promise<string | undefined>;
357
+ /** Interactive only: show the AutoRAG welcome banner (with this version) instead of pi's startup header. */
358
+ welcomeVersion?: string;
348
359
  /** Extension entry files (installed pi packages) loaded into the interactive session. */
349
360
  piExtensionPaths?: readonly string[];
350
361
  /** Flag values for the flags those extensions register. */
@@ -356,6 +367,15 @@ export interface AutoRAGAgentOptions {
356
367
  * owner pairing live in pi's `telegram.json`, never in AutoRAG config.
357
368
  */
358
369
  telegram?: boolean;
370
+ /**
371
+ * Approval gate for what the agent does to existing files. `full` (the programmatic default) installs a
372
+ * gate that never asks; `ask` and `auto` approve deletes, moves, renames, and in-place edits of originals
373
+ * (copying and creating new files never ask). `auto` asks Jev first and only falls back to the user when
374
+ * Jev will not approve. See {@link PermissionMode}.
375
+ */
376
+ permissionMode?: PermissionMode;
377
+ /** Share one controller (mode, session grants) with a host that switches modes itself. Wins over `permissionMode`. */
378
+ permissionController?: PermissionController;
359
379
  }
360
380
  /** Post-merge reranking options. Mirrors the CLI `RerankConfig` (secrets via env). */
361
381
  export interface RerankAgentOptions {
@@ -379,7 +399,7 @@ export interface AutoRAGSearchSession {
379
399
  readonly piSession?: AutoRAGPiSession["session"];
380
400
  prompt(text: string): Promise<void>;
381
401
  abort(): Promise<void> | void;
382
- dispose(): void;
402
+ dispose(): void | Promise<void>;
383
403
  }
384
404
  export type AutoRAGJikjiPrepareResult = {
385
405
  readonly ok: true;
@@ -404,6 +424,8 @@ export declare class AutoRAGAgent {
404
424
  private readonly memory;
405
425
  private readonly runLogger;
406
426
  private lastQuery;
427
+ /** What the user has said in this conversation; Jev's permission gate judges file changes against it. */
428
+ private readonly userRequests;
407
429
  private lastSessionId;
408
430
  private activeRun;
409
431
  /**
@@ -414,6 +436,8 @@ export declare class AutoRAGAgent {
414
436
  * state for `searchDocuments()` / `searchDocumentsStream()` callers.
415
437
  */
416
438
  private readonly interactive;
439
+ /** What the running search is doing, shown as a live widget in the TUI. */
440
+ private readonly searchProgress;
417
441
  /** Aborted by {@link abort} and by the run's timeout: gates publishing and the run's own requests. */
418
442
  private activeRunAbort;
419
443
  private modelNativeSearchAuth;
@@ -424,6 +448,10 @@ export declare class AutoRAGAgent {
424
448
  * run starts from an empty ledger.
425
449
  */
426
450
  private readonly evidenceLedger;
451
+ /** The result numbers (`[n]`) this conversation has shown, kept next to the ledger's `e<N>` ordinals. */
452
+ private readonly citationNumbers;
453
+ /** Everything the user typed in this conversation; Jev reads it to judge whether a citation relates to what was asked. */
454
+ private readonly conversationQueries;
427
455
  private preliminaryCallback;
428
456
  /** Per-phase thinking levels of the two-phase search. */
429
457
  private readonly fastThinkingLevel;
@@ -456,10 +484,14 @@ export declare class AutoRAGAgent {
456
484
  private readonly datasourceAgentSkills;
457
485
  private readonly parserOptions;
458
486
  private readonly dupeyOptions;
487
+ private readonly fileeOptions;
459
488
  /** pi extension registering the optional `jev` tool; undefined when disabled. */
460
489
  private readonly jevExtension;
461
490
  /** Jev judge shared by the `jev` tool and the query router; undefined when disabled. */
462
491
  private readonly jevJudge;
492
+ /** Mode and grants of the file-change approval gate; shared by every pi session this agent creates. */
493
+ private readonly permissions;
494
+ private readonly permissionGate;
463
495
  /** Self-configuration, enabled only with Jev on a local session. */
464
496
  private readonly selfConfig;
465
497
  private readonly queryDecompositionModel;
@@ -475,6 +507,7 @@ export declare class AutoRAGAgent {
475
507
  private readonly piSessionDir;
476
508
  private readonly persistPiSessions;
477
509
  private readonly updateNotice;
510
+ private readonly welcomeVersion;
478
511
  private readonly piExtensionPaths;
479
512
  private readonly piExtensionFlags;
480
513
  private readonly telegram;
@@ -492,11 +525,15 @@ export declare class AutoRAGAgent {
492
525
  /** The memory context loaded for the in-flight run; cleared whenever a run starts. */
493
526
  private memoryContextCache;
494
527
  private readonly discordRemote;
528
+ /** Whether the bound interactive session offers `ask_user`; the phase prompts name it only then. */
529
+ private askUserOffered;
495
530
  private activeRetrievalOptions;
496
531
  private readonly toolBurstGuard;
497
532
  private readonly limits;
498
533
  private readonly refreshLimits;
499
534
  constructor(options: AutoRAGAgentOptions);
535
+ convertFiles(request: FileeConvertRequest, signal?: AbortSignal): Promise<ConvertFilesDetails>;
536
+ listFileConversions(from?: string, signal?: AbortSignal): Promise<string>;
500
537
  scanDuplicateDocuments(): Promise<ScanDuplicateDocumentsDetails>;
501
538
  /**
502
539
  * Reference memory for the current question: everything judged earlier in
@@ -539,6 +576,8 @@ export declare class AutoRAGAgent {
539
576
  private configureSearchSession;
540
577
  private recordSearchToolEvent;
541
578
  private currentSystemPromptConfig;
579
+ /** The approval gate's controller: read or switch the permission mode of this agent's sessions. */
580
+ get permissionControl(): PermissionController;
542
581
  subscribe(listener: Parameters<Agent["subscribe"]>[0]): () => void;
543
582
  createPiInteractiveRuntime(): Promise<AutoRAGPiInteractiveRuntime>;
544
583
  /**
@@ -560,7 +599,12 @@ export declare class AutoRAGAgent {
560
599
  * matters, so the steer reaches the model before the next request.
561
600
  */
562
601
  private interruptibleBySteer;
563
- /** Resolve the model's inline `[eN]` citations against this run's evidence and derive the structured results. */
602
+ /**
603
+ * Resolve the model's inline `[eN]` citations against this run's evidence and derive the structured results.
604
+ * With Jev on, every cited chunk is first checked for relevance to the sentence that cites it and to what
605
+ * the user typed in this conversation; a chunk Jev finds unrelated (a table of contents, a footer) is dropped
606
+ * from the citations before the answer is returned or judged for memory.
607
+ */
564
608
  private deriveAnswer;
565
609
  /**
566
610
  * Routes one TUI input the way pi routes typed input for its own turns. With
@@ -713,6 +757,12 @@ export declare class AutoRAGAgent {
713
757
  * continues on the retrieval-order fallback.
714
758
  */
715
759
  private reportRerankFailure;
760
+ /**
761
+ * Sentence for the phase prompts that forbid tool calls: `ask_user` is not a search tool, and a request
762
+ * that hinges on a choice only the user can make must be asked, not guessed. Empty when the session does
763
+ * not offer the tool.
764
+ */
765
+ private askUserException;
716
766
  /**
717
767
  * Fast-phase prompt for two-phase searches. The baseline retrieval context
718
768
  * is already gathered, so the model answers immediately with minimal thinking,
@@ -731,6 +781,24 @@ export declare class AutoRAGAgent {
731
781
  * reply is the final answer.
732
782
  */
733
783
  buildDirectAnswerPrompt(query: string): string;
784
+ /**
785
+ * Tools an `organize` turn keeps: pi's file tools plus the converter, the
786
+ * duplicate scan, and file-name discovery, whichever this agent registered.
787
+ * The retrieval, datasource, and web tools stay out: the turn acts on files.
788
+ */
789
+ private organizeToolNames;
790
+ /**
791
+ * Prompt for a request Jev routed to `organize`: act on files and folders
792
+ * (move, rename, convert, sort). No retrieval ran and no verification
793
+ * follows; the model's plain final message is the answer.
794
+ */
795
+ buildOrganizePrompt(query: string): string;
796
+ /**
797
+ * Prompt for a request Jev routed to `extra`: a task that is neither
798
+ * knowledge, the user's records, file organization, nor configuration.
799
+ * The model acts with every tool it has; there is no retrieval or verification phase.
800
+ */
801
+ buildExtraPrompt(query: string): string;
734
802
  /** Discovery-tool hint naming only the registered discovery tools; empty when none. */
735
803
  private discoveryHint;
736
804
  /**
@@ -1,3 +1,4 @@
1
+ import type { CitationNumbers } from "./citation-numbers.js";
1
2
  import { type EvidenceLedger } from "./evidence-ledger.js";
2
3
  import type { AutoRAGResultsDetails } from "./results.js";
3
4
  import type { SearchDocumentDiagnostic } from "./search-documents.js";
@@ -5,6 +6,31 @@ export interface DerivedAnswer {
5
6
  readonly details: AutoRAGResultsDetails;
6
7
  readonly diagnostics: readonly SearchDocumentDiagnostic[];
7
8
  }
9
+ /**
10
+ * Identity of one cited chunk: the source plus the recorded chunk text. A
11
+ * source can back several chunks, so a chunk is judged and excluded on its own.
12
+ */
13
+ export declare function citedChunkKey(ref: {
14
+ readonly source: string;
15
+ readonly content?: string;
16
+ }): string;
17
+ /** One chunk the answer cites, with the sentences that cite it. */
18
+ export interface CitedChunk {
19
+ /** {@link citedChunkKey} of the chunk. */
20
+ readonly key: string;
21
+ readonly source: string;
22
+ readonly content: string;
23
+ /** Each distinct sentence ending in a marker that cites this chunk, in answer order. */
24
+ readonly sentences: readonly string[];
25
+ }
26
+ /**
27
+ * Every chunk the answer cites, read from the raw markers. It resolves ids the
28
+ * way {@link deriveResultsFromAnswer} does but numbers nothing, so judging a
29
+ * citation never touches the conversation's result numbers.
30
+ */
31
+ export declare function citedChunks(text: string, ledger: EvidenceLedger, options: {
32
+ readonly allowLocalFiles: boolean;
33
+ }): CitedChunk[];
8
34
  /**
9
35
  * Turn the model's plain answer into the structured results the rest of the
10
36
  * harness consumes. The model cites with the evidence ids the retrieval tools
@@ -12,11 +38,17 @@ export interface DerivedAnswer {
12
38
  * itself. Each id is resolved against the run's evidence ledger, so a source,
13
39
  * method, and chunk always come from recorded evidence, never from model text.
14
40
  *
15
- * Results are one per cited source, numbered by first appearance, and every
16
- * marker in the returned answer is rewritten to its result number (`[1]`).
41
+ * Results are one per cited source, in order of first appearance in this answer. A source's
42
+ * number comes from the conversation's {@link CitationNumbers}: a source
43
+ * numbered in an earlier answer (or an earlier phase of this turn) keeps its
44
+ * number, a new source gets the next unused one, and every marker in the
45
+ * returned answer is rewritten to its result number (`[1]`).
17
46
  * A marker that matches no evidence, and any numeric marker the model wrote on
18
47
  * its own, is dropped and reported: it can never point at the wrong result.
19
48
  */
20
49
  export declare function deriveResultsFromAnswer(text: string, ledger: EvidenceLedger, options: {
21
50
  readonly allowLocalFiles: boolean;
51
+ readonly numbers: CitationNumbers;
52
+ /** Chunks ({@link citedChunkKey}) a relevance judgment rejected: a citation of only these is dropped silently. */
53
+ readonly excludedChunks?: ReadonlySet<string>;
22
54
  }): DerivedAnswer;
@@ -10,11 +10,32 @@ export declare const ANSWER_IMAGE_EMBED_RULE = "**Images**: when a retrieved res
10
10
  * already showed.
11
11
  */
12
12
  export declare const ANSWER_IMAGE_DELTA_RULE = "An image already embedded in the first answer must not be embedded again.";
13
+ /**
14
+ * Answer readability rules. Every surface that tells the model how to write the
15
+ * answer (system prompt, fast/complete/delta/search phase prompts, report
16
+ * schema) carries the same wording, so the answer's shape does not depend on
17
+ * which phase produced it. Each rule yields to an explicit user request for a
18
+ * different format.
19
+ */
20
+ /**
21
+ * Conclusion first. Only complete answers get a lead line: a delta answer holds
22
+ * only corrections and new findings, and a lead conclusion would restate the
23
+ * first answer. The lead is outside the 5-bullet cap so the cap stays intact.
24
+ */
25
+ export declare const ANSWER_LEAD_RULE = "**Lead with the conclusion**: unless the user explicitly requests a different format, start the answer with one line that states the conclusion in **bold**, followed by the supporting bullet points. The lead line is not counted in the 5-bullet cap. When the whole answer is a single fact, the lead line alone is enough and no bullets are needed.";
26
+ /** One claim per bullet; flat list. */
27
+ export declare const ANSWER_BULLET_RULE = "**One claim per bullet**: each bullet makes one claim in one or two sentences. Never nest bullets; split a bullet that carries two claims into two bullets.";
28
+ /** Bold the values a reader scans for; tabulate real comparisons. */
29
+ export declare const ANSWER_EMPHASIS_RULE = "**Emphasis**: put the values a reader scans for (dates, amounts, names, statuses, deadlines) in **bold**, and nothing else. When comparing three or more items across the same attributes, use a markdown table instead of bullets.";
30
+ /** Answer language follows the question, not the sources. */
31
+ export declare const ANSWER_LANGUAGE_RULE = "**Answer language**: write the answer in the language of the user's question (a Korean question gets a Korean answer) even when the sources are in another language; if the user asks for a specific language, use that one. Keep proper nouns, identifiers, code, and terms quoted from sources in their original form.";
32
+ /** Uncertainty goes last so it never buries the conclusion. */
33
+ export declare const ANSWER_UNCERTAINTY_RULE = "**Uncertainty placement**: when the answer is incomplete or uncertain, state that in one short sentence on the last line of the answer, never before or ahead of the conclusion. Do not hedge the conclusion itself.";
13
34
  /**
14
35
  * Inline evidence citations. The model writes the id the retrieval tools print
15
36
  * next to each result; the harness resolves it to the recorded source and
16
- * renumbers the markers `[1]`, `[2]`, ... in order of first appearance, so the
17
- * caller only ever sees numbered citations backed by recorded evidence.
37
+ * renumbers the markers `[1]`, `[2]`, ... (a source keeps its number for the whole
38
+ * conversation), so the caller only ever sees numbered citations backed by recorded evidence.
18
39
  */
19
40
  export declare const ANSWER_CITATION_RULE = "**Citations**: cite supporting evidence inline with the evidence id shown next to each retrieved result, in square brackets (e.g. [e3], or [e3][e7] for two). Copy ids exactly; never invent one. For a local file you opened yourself with `bash`, cite `[file:<absolute path>]`. Cite the evidence that backs a sentence at the end of that sentence. Do not cite numbers, paths, or anything else.";
20
41
  /**
@@ -27,7 +48,7 @@ export declare const ANSWER_CITATION_RULE = "**Citations**: cite supporting evid
27
48
  * concise by stating the created file's location and briefly summarizing what
28
49
  * was generated (citing only the underlying source evidence).
29
50
  */
30
- export declare const ANSWER_DELIVERABLE_RULE = "**Deliverables and artifacts**: if the user asks you to draft, write, generate, or prepare a deliverable or artifact (a reply email, letter, legal opinion, summary document, standard-format case citation block, checklist, report, or workflow document \u2014 including requests phrased as \"how should I reply...\" to a specific message), produce the finished, ready-to-use artifact as a file (using `write`, `edit`, or `bash` in local sessions, without overwriting existing source files) in a file format, extension, and structure aligned with the context and domain (e.g. `.eml` or `.md`/`.txt` with headers for an email reply; `.md`, `.txt`, `.docx`, `.hwp`, or `.pdf` matching workspace conventions for a legal opinion, insertable case-citation block, or summary document; `.csv`, `.xlsx`, or `.json` for structured tabular data), containing the complete unabridged artifact (including required headers, precedent passages, pinpoint paragraphs, and standard-format citations) inside the file instead of merely describing how to produce it. Do NOT dump the full artifact text into your reply: unless the user explicitly requests otherwise, keep your reply concise within the at-most-5-bullet direct-answer format, clearly stating the created file's exact path/location and briefly summarizing what was generated with inline citations to the underlying source evidence (`[eN]` or `[file:<source path>]`); never cite the newly created deliverable file itself as `[file:...]`.";
51
+ export declare const ANSWER_DELIVERABLE_RULE = "**Deliverables and artifacts**: if the user asks you to draft, write, generate, or prepare a deliverable or artifact (a reply email, letter, legal opinion, summary document, standard-format case citation block, checklist, report, or workflow document \u2014 including requests phrased as \"how should I reply...\" to a specific message), produce the finished, ready-to-use artifact as a file (using `write`, `edit`, or `bash` in local sessions) in a file format, extension, and structure aligned with the context and domain (e.g. `.eml` or `.md`/`.txt` with headers for an email reply; `.md`, `.txt`, `.docx`, `.hwp`, or `.pdf` matching workspace conventions for a legal opinion, insertable case-citation block, or summary document; `.csv`, `.xlsx`, or `.json` for structured tabular data), containing the complete unabridged artifact (including required headers, precedent passages, pinpoint paragraphs, and standard-format citations) inside the file instead of merely describing how to produce it. Do NOT dump the full artifact text into your reply: unless the user explicitly requests otherwise, keep your reply concise within the at-most-5-bullet direct-answer format, clearly stating the created file's exact path/location and briefly summarizing what was generated with inline citations to the underlying source evidence (`[eN]` or `[file:<source path>]`); never cite the newly created deliverable file itself as `[file:...]`.";
31
52
  /**
32
53
  * Verification-phase deliverable rule: create the context-aligned deliverable
33
54
  * file (in local sessions) and report its location and concise summary if the
@@ -0,0 +1,8 @@
1
+ /** Tool the `pi-ask-user` extension registers; pi's allow-list must name it to keep it active. */
2
+ export declare const ASK_USER_TOOL_NAME = "ask_user";
3
+ /**
4
+ * Entry file of the community `pi-ask-user` extension (the most-installed pi package for this: Claude
5
+ * Code's AskUserQuestion, with a searchable single/multi-select sheet, freeform answers, and 2-4 question
6
+ * batches). It ships TypeScript source and no `main`, so pi's own extension loader runs it from this path.
7
+ */
8
+ export declare function resolveAskUserExtensionPath(): string;
@@ -0,0 +1,45 @@
1
+ import type { AgentTool } from "@earendil-works/pi-agent-core";
2
+ import { Type } from "typebox";
3
+ import type { AutomationRunRecord } from "../automation/run.js";
4
+ import { type ServiceCommandExec } from "../automation/service.js";
5
+ export declare const MANAGE_AUTOMATIONS_TOOL_NAME = "manage_automations";
6
+ declare const manageAutomationsSchema: Type.TObject<{
7
+ action: Type.TUnion<[Type.TLiteral<"list">, Type.TLiteral<"save">, Type.TLiteral<"delete">, Type.TLiteral<"run">, Type.TLiteral<"install_service">, Type.TLiteral<"uninstall_service">]>;
8
+ id: Type.TOptional<Type.TString>;
9
+ automation: Type.TOptional<Type.TObject<{
10
+ paths: Type.TArray<Type.TString>;
11
+ events: Type.TOptional<Type.TArray<Type.TUnion<[Type.TLiteral<"create">, Type.TLiteral<"update">, Type.TLiteral<"delete">]>>>;
12
+ include: Type.TOptional<Type.TArray<Type.TString>>;
13
+ exclude: Type.TOptional<Type.TArray<Type.TString>>;
14
+ run: Type.TOptional<Type.TArray<Type.TString>>;
15
+ agent: Type.TOptional<Type.TObject<{
16
+ profile: Type.TString;
17
+ task: Type.TString;
18
+ retrieval: Type.TOptional<Type.TObject<{
19
+ searchAll: Type.TOptional<Type.TBoolean>;
20
+ datasources: Type.TOptional<Type.TArray<Type.TString>>;
21
+ }>>;
22
+ }>>;
23
+ appendFiles: Type.TOptional<Type.TBoolean>;
24
+ debounceMs: Type.TOptional<Type.TInteger>;
25
+ timeoutMs: Type.TOptional<Type.TInteger>;
26
+ }>>;
27
+ events: Type.TOptional<Type.TArray<Type.TObject<{
28
+ type: Type.TUnion<[Type.TLiteral<"create">, Type.TLiteral<"update">, Type.TLiteral<"delete">]>;
29
+ path: Type.TString;
30
+ }>>>;
31
+ }>;
32
+ export interface ManageAutomationsToolOptions {
33
+ readonly home?: string;
34
+ readonly env?: NodeJS.ProcessEnv;
35
+ readonly platform?: NodeJS.Platform;
36
+ readonly exec?: ServiceCommandExec;
37
+ readonly waitForRunningMs?: number;
38
+ }
39
+ export interface ManageAutomationsDetails {
40
+ readonly action: string;
41
+ readonly id?: string;
42
+ readonly run?: AutomationRunRecord;
43
+ }
44
+ export declare function createManageAutomationsTool(options?: ManageAutomationsToolOptions): AgentTool<typeof manageAutomationsSchema, ManageAutomationsDetails>;
45
+ export {};
@@ -0,0 +1,23 @@
1
+ import type { ExtensionFactory } from "@earendil-works/pi-coding-agent";
2
+ import { type EvidenceLedger } from "./evidence-ledger.js";
3
+ /** `file://` URL of an absolute local path, an http(s) URL as is, otherwise undefined (a datasource id, a message id). */
4
+ export declare function openableTarget(source: string): string | undefined;
5
+ /**
6
+ * Rewrite the citation markers of an assistant answer into Markdown links, so
7
+ * pi renders them as terminal hyperlinks that open the cited file or page.
8
+ *
9
+ * `[e3]` and `[e3, e7]` keep their brackets and ids; each id that resolves to
10
+ * an openable source becomes a link. `[file:/abs/path]` becomes `[<file name>]`
11
+ * linked to that file. Markers that resolve to nothing openable stay as the
12
+ * model wrote them.
13
+ *
14
+ * `sourceOf` maps an evidence id to its recorded source; `isFile` says whether
15
+ * a `[file:...]` path is a real local file.
16
+ */
17
+ export declare function linkCitations(markdown: string, sourceOf: (id: string) => string | undefined, isFile: (path: string) => boolean): string;
18
+ /**
19
+ * pi extension that makes the citations in the interactive transcript
20
+ * clickable. The model cites by evidence id; the ledger recorded the source
21
+ * each id names, so the link target is never model-written text.
22
+ */
23
+ export declare function createCitationLinks(ledger: EvidenceLedger): ExtensionFactory;