@markusylisiurunen/tau 0.3.82 → 0.3.83
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.
- package/README.md +1 -3
- package/dist/core/agent/agent_runtime.js +6 -4
- package/dist/core/agent/agent_runtime.js.map +1 -1
- package/dist/core/cli.js +2 -2
- package/dist/core/cli.js.map +1 -1
- package/dist/core/code_mode/models.js +61 -22
- package/dist/core/code_mode/models.js.map +1 -1
- package/dist/core/history/cli.js +48 -0
- package/dist/core/history/cli.js.map +1 -1
- package/dist/core/history/history_manager.js +9 -3
- package/dist/core/history/history_manager.js.map +1 -1
- package/dist/core/history/local_history_store.js +9 -2
- package/dist/core/history/local_history_store.js.map +1 -1
- package/dist/core/history/remote_history_client.js +18 -3
- package/dist/core/history/remote_history_client.js.map +1 -1
- package/dist/core/models/openrouter.js +17 -5
- package/dist/core/models/openrouter.js.map +1 -1
- package/dist/core/models/openrouter_decisions.js +16 -1
- package/dist/core/models/openrouter_decisions.js.map +1 -1
- package/dist/core/static/tau_docs/client-tools.md +53 -53
- package/dist/core/static/tau_docs/config-reference.md +46 -43
- package/dist/core/static/tau_docs/configuration.md +40 -36
- package/dist/core/static/tau_docs/credentials.md +32 -31
- package/dist/core/static/tau_docs/getting-started.md +28 -28
- package/dist/core/static/tau_docs/history.md +114 -79
- package/dist/core/static/tau_docs/image-generation.md +20 -18
- package/dist/core/static/tau_docs/index.md +30 -31
- package/dist/core/static/tau_docs/manifest.json +1 -0
- package/dist/core/static/tau_docs/models.md +17 -17
- package/dist/core/static/tau_docs/node-sdk.md +69 -69
- package/dist/core/static/tau_docs/nook.md +75 -69
- package/dist/core/static/tau_docs/openrouter.md +28 -13
- package/dist/core/static/tau_docs/ownership-and-scope.md +21 -23
- package/dist/core/static/tau_docs/pdf-unpacking.md +6 -6
- package/dist/core/static/tau_docs/personas.md +29 -27
- package/dist/core/static/tau_docs/prompts-and-project-context.md +41 -39
- package/dist/core/static/tau_docs/remote-sessions.md +38 -38
- package/dist/core/static/tau_docs/sdk-diff-review.md +16 -12
- package/dist/core/static/tau_docs/security.md +72 -72
- package/dist/core/static/tau_docs/session-protocol-methods.md +45 -45
- package/dist/core/static/tau_docs/session-protocol.md +43 -43
- package/dist/core/static/tau_docs/sessions.md +99 -88
- package/dist/core/static/tau_docs/skills.md +25 -20
- package/dist/core/static/tau_docs/speech-generation.md +5 -5
- package/dist/core/static/tau_docs/subagents.md +42 -44
- package/dist/core/static/tau_docs/telegram-projects.md +142 -0
- package/dist/core/static/tau_docs/telegram.md +64 -181
- package/dist/core/static/tau_docs/tools.md +72 -80
- package/dist/core/static/tau_docs/troubleshooting.md +94 -149
- package/dist/core/static/tau_docs/tui.md +124 -80
- package/dist/core/tool/image_generate.js +5 -17
- package/dist/core/tool/image_generate.js.map +1 -1
- package/dist/core/tool/openrouter.js +21 -2
- package/dist/core/tool/openrouter.js.map +1 -1
- package/dist/core/utils/gemini_transcription.js +43 -13
- package/dist/core/utils/gemini_transcription.js.map +1 -1
- package/dist/core/utils/model_stream.js +17 -1
- package/dist/core/utils/model_stream.js.map +1 -1
- package/dist/core/version.js +2 -2
- package/dist/diff_tool/app/dist/assets/{angular-html-D20byCHL.js → angular-html-x29PkEoY.js} +1 -1
- package/dist/diff_tool/app/dist/assets/{angular-ts-CvVQslm2.js → angular-ts-CsWCqoCf.js} +1 -1
- package/dist/diff_tool/app/dist/assets/{apl-DNIxlYWe.js → apl-CEvdc7jl.js} +1 -1
- package/dist/diff_tool/app/dist/assets/{astro-DDOw4EUG.js → astro-Cgi6YxH2.js} +1 -1
- package/dist/diff_tool/app/dist/assets/{blade-DlhB-SLW.js → blade-B0pr7Zx6.js} +1 -1
- package/dist/diff_tool/app/dist/assets/{c-C1f4vhDm.js → c-DDVLgtVy.js} +1 -1
- package/dist/diff_tool/app/dist/assets/{chapel-Ctt8xOX1.js → chapel-Bk9M7Jej.js} +1 -1
- package/dist/diff_tool/app/dist/assets/{cobol-BXw71PAA.js → cobol-DyEvnPuC.js} +1 -1
- package/dist/diff_tool/app/dist/assets/{coffee-CRh_5Nmr.js → coffee-Di2-m3Jq.js} +1 -1
- package/dist/diff_tool/app/dist/assets/{cpp-IlI-zWOZ.js → cpp-CWpAaUgO.js} +1 -1
- package/dist/diff_tool/app/dist/assets/{crystal-CXeL28i7.js → crystal-CUker9Zt.js} +1 -1
- package/dist/diff_tool/app/dist/assets/{css-BfST9hFI.js → css-D4XpBIiJ.js} +1 -1
- package/dist/diff_tool/app/dist/assets/{edge--Q22k_ty.js → edge-CVxhhF7L.js} +1 -1
- package/dist/diff_tool/app/dist/assets/{elixir-CIfC_rQx.js → elixir-B_FS9APl.js} +1 -1
- package/dist/diff_tool/app/dist/assets/{elm-OkZ29XRO.js → elm-1KyefTkH.js} +1 -1
- package/dist/diff_tool/app/dist/assets/{erb-B8ZXgEqv.js → erb-CCgO9dRW.js} +1 -1
- package/dist/diff_tool/app/dist/assets/{git-rebase-CxkO_WGd.js → git-rebase-D0VYo_oY.js} +1 -1
- package/dist/diff_tool/app/dist/assets/{glimmer-js-BVadyIrr.js → glimmer-js-Ce07ngjZ.js} +1 -1
- package/dist/diff_tool/app/dist/assets/{glimmer-ts-D5J3Qb7n.js → glimmer-ts-BmOM4djO.js} +1 -1
- package/dist/diff_tool/app/dist/assets/{glsl-B6iy73-Y.js → glsl-D-jkLYJ8.js} +1 -1
- package/dist/diff_tool/app/dist/assets/{graphql-Dc3rUXf5.js → graphql-DZOwJE5e.js} +1 -1
- package/dist/diff_tool/app/dist/assets/{hack-q8Utf8Jp.js → hack-Cgvn19h8.js} +1 -1
- package/dist/diff_tool/app/dist/assets/{haml-mjMIlj_2.js → haml-JTmDSYQl.js} +1 -1
- package/dist/diff_tool/app/dist/assets/{handlebars-CA-BL8Ks.js → handlebars-CChh7Dy5.js} +1 -1
- package/dist/diff_tool/app/dist/assets/{html-BmPxhYCX.js → html-BKgzx_cb.js} +1 -1
- package/dist/diff_tool/app/dist/assets/{html-derivative-CvknIjuB.js → html-derivative-CdFl0BmX.js} +1 -1
- package/dist/diff_tool/app/dist/assets/{http-DNxLDRIi.js → http-DZeL7KvH.js} +1 -1
- package/dist/diff_tool/app/dist/assets/{hurl-kbd3Eq2V.js → hurl-CqKevOlQ.js} +1 -1
- package/dist/diff_tool/app/dist/assets/index-BXyr8GCM.js +341 -0
- package/dist/diff_tool/app/dist/assets/{java-BuZshgf1.js → java-Sq3MCkId.js} +1 -1
- package/dist/diff_tool/app/dist/assets/{javascript-DfL2oeFU.js → javascript-CHZB4Nse.js} +1 -1
- package/dist/diff_tool/app/dist/assets/{jinja-Bu0KQihU.js → jinja-C4ucJVla.js} +1 -1
- package/dist/diff_tool/app/dist/assets/{jison-Bqn7Mf3Q.js → jison-D3mprebA.js} +1 -1
- package/dist/diff_tool/app/dist/assets/{json-BuX5LKaB.js → json-DgPfCYJ1.js} +1 -1
- package/dist/diff_tool/app/dist/assets/{jsx-DdVJ-ZBp.js → jsx-BG-Tx0cw.js} +1 -1
- package/dist/diff_tool/app/dist/assets/{julia-CQeijOoQ.js → julia-B1GnFeUC.js} +1 -1
- package/dist/diff_tool/app/dist/assets/{just-vzAktFGR.js → just-_MZzo0MF.js} +1 -1
- package/dist/diff_tool/app/dist/assets/{latex-Dm60cg0k.js → latex-DI0kqjQy.js} +1 -1
- package/dist/diff_tool/app/dist/assets/{liquid-vxKzm2P8.js → liquid-BtMAPeHl.js} +1 -1
- package/dist/diff_tool/app/dist/assets/{lua-DIoqi4dd.js → lua-CFxaP0To.js} +1 -1
- package/dist/diff_tool/app/dist/assets/{marko-BTHgFKby.js → marko-BIJocuFI.js} +1 -1
- package/dist/diff_tool/app/dist/assets/{mdc-CEfz8gZ9.js → mdc-BAgrdjTH.js} +1 -1
- package/dist/diff_tool/app/dist/assets/{nginx-DNlFDEfJ.js → nginx-DE-3CsYn.js} +1 -1
- package/dist/diff_tool/app/dist/assets/{nim-DnvT_0lZ.js → nim-DOxeXLhb.js} +1 -1
- package/dist/diff_tool/app/dist/assets/{org-BbD-ElVf.js → org-KTfP0tHA.js} +1 -1
- package/dist/diff_tool/app/dist/assets/{perl-DTsbnAmK.js → perl-BH-NxpgK.js} +1 -1
- package/dist/diff_tool/app/dist/assets/{php-CwEsJe-W.js → php-vuiVEXZK.js} +1 -1
- package/dist/diff_tool/app/dist/assets/{pug-BOttMVH-.js → pug-VlIlTMUy.js} +1 -1
- package/dist/diff_tool/app/dist/assets/{qml-C8KkSItN.js → qml-k6wTtGG-.js} +1 -1
- package/dist/diff_tool/app/dist/assets/{r-K4ksJj_R.js → r-Ccjcb2zh.js} +1 -1
- package/dist/diff_tool/app/dist/assets/{razor-yuWRrrG6.js → razor-BNhYgSCv.js} +1 -1
- package/dist/diff_tool/app/dist/assets/{regexp-CV-jhnUz.js → regexp-C4LFejPu.js} +1 -1
- package/dist/diff_tool/app/dist/assets/{rst-CLA3Attc.js → rst-DXLxI-UJ.js} +1 -1
- package/dist/diff_tool/app/dist/assets/{ruby-DiHR2-DX.js → ruby-BPuL4jDV.js} +1 -1
- package/dist/diff_tool/app/dist/assets/{sas-DxIjbYJ5.js → sas-B3Yz8snb.js} +1 -1
- package/dist/diff_tool/app/dist/assets/{scss-CShwEaV4.js → scss-B2AJ5vpk.js} +1 -1
- package/dist/diff_tool/app/dist/assets/{shellscript-CeezOnrF.js → shellscript-zyDexxnC.js} +1 -1
- package/dist/diff_tool/app/dist/assets/{shellsession-CjSS2r7j.js → shellsession-C8b8xluk.js} +1 -1
- package/dist/diff_tool/app/dist/assets/{soy-CI_v23nJ.js → soy-DKWe_XML.js} +1 -1
- package/dist/diff_tool/app/dist/assets/{sql-D9GaB00A.js → sql-uEbz-Epf.js} +1 -1
- package/dist/diff_tool/app/dist/assets/{stata-hK92TPE_.js → stata-DieRPmHY.js} +1 -1
- package/dist/diff_tool/app/dist/assets/{surrealql-UO8LtPJG.js → surrealql-Dbk3Sp1P.js} +1 -1
- package/dist/diff_tool/app/dist/assets/{svelte-kIlaw_oh.js → svelte-CjPbRmkM.js} +1 -1
- package/dist/diff_tool/app/dist/assets/{templ-DFRz1JP6.js → templ-Do_f5vc4.js} +1 -1
- package/dist/diff_tool/app/dist/assets/{tex-CfxIXk_z.js → tex-UjLP4qUm.js} +1 -1
- package/dist/diff_tool/app/dist/assets/{ts-tags-BtUHl0ff.js → ts-tags-5L2FutA6.js} +1 -1
- package/dist/diff_tool/app/dist/assets/{tsx-Cd4SAe2C.js → tsx-B1pNtpUr.js} +1 -1
- package/dist/diff_tool/app/dist/assets/{twig-CWk4q5Y3.js → twig-O41Vg_IM.js} +1 -1
- package/dist/diff_tool/app/dist/assets/{typescript-BqxGJiP0.js → typescript-Bj9uwnnJ.js} +1 -1
- package/dist/diff_tool/app/dist/assets/{typst-D9nAun2p.js → typst-DsibO7oD.js} +1 -1
- package/dist/diff_tool/app/dist/assets/{vue-D6HYhg6_.js → vue-DPhaEurv.js} +1 -1
- package/dist/diff_tool/app/dist/assets/{vue-html-1VRlaENS.js → vue-html-DDV9NSy1.js} +1 -1
- package/dist/diff_tool/app/dist/assets/{vue-vine-BaH0We9y.js → vue-vine-Dh4jOifx.js} +1 -1
- package/dist/diff_tool/app/dist/assets/{xml-C4RWnUuj.js → xml-DtIulkQk.js} +1 -1
- package/dist/diff_tool/app/dist/assets/{xsl-D1iD38ga.js → xsl-DoWtb58Z.js} +1 -1
- package/dist/diff_tool/app/dist/assets/{yaml-yAb4W0G-.js → yaml-CZC-l1Dg.js} +1 -1
- package/dist/diff_tool/app/dist/index.html +1 -1
- package/dist/history/worker/index.js +87 -83
- package/dist/history/worker/index.js.map +1 -1
- package/dist/main.js +6 -7
- package/dist/main.js.map +1 -1
- package/dist/tui/session_chat_controller.js +14 -3
- package/dist/tui/session_chat_controller.js.map +1 -1
- package/dist/tui/ui/footer.js +2 -4
- package/dist/tui/ui/footer.js.map +1 -1
- package/package.json +9 -9
- package/dist/diff_tool/app/dist/assets/index-D8ZI_2RC.js +0 -340
- package/dist/nook/README.md +0 -123
|
@@ -1,32 +1,32 @@
|
|
|
1
1
|
# Models
|
|
2
2
|
|
|
3
|
-
A model definition tells Tau how to call a provider model and
|
|
3
|
+
A model definition tells Tau how to call a provider's model and what the model can do, including its limits and cost. A persona picks one provider and model, and credentials authorize the request. Because these are separate, model metadata can be updated without changing personas.
|
|
4
4
|
|
|
5
|
-
Tau ships a
|
|
5
|
+
Tau ships a model catalog and refreshes compatible metadata from `pi.dev`. The catalog a session sees therefore depends on the installed Tau version and on the host's cached copy of the remote catalog.
|
|
6
6
|
|
|
7
7
|
## Providers, models, and personas
|
|
8
8
|
|
|
9
|
-
A **provider**
|
|
9
|
+
A **provider** has its own authentication and one or more request APIs. A **model** is named by a provider ID and an exact model ID, such as `openai/gpt-6.1-sol`. A [persona](personas.md) combines a model with a system prompt, settings, tools, and subagents.
|
|
10
10
|
|
|
11
|
-
The bundled catalog comes from Tau's model
|
|
11
|
+
The bundled catalog comes from Tau's model library, `pi-ai`. It lists known provider IDs and model IDs, with request API names, endpoints, capabilities, token limits, and pricing. A model in the catalog is not necessarily usable: the provider may lack credentials, the account may not have access to the model, or the endpoint may reject it. See [credentials](credentials.md).
|
|
12
12
|
|
|
13
13
|
## Remote catalog
|
|
14
14
|
|
|
15
|
-
A
|
|
15
|
+
A Tau host that runs models loads cached catalogs from `~/.config/tau/models-store.json` at startup. If the cache is older than four hours, it checks `pi.dev` in the background. This check happens only at startup; there is no recurring refresh. Set `TAU_OFFLINE` to skip it.
|
|
16
16
|
|
|
17
|
-
Tau requests
|
|
17
|
+
Tau requests the catalog separately for each provider that its `pi-ai` version supports. Each request has a 15-second timeout. A successful provider is cached even when another fails. A failed provider keeps its previous cached data, or the bundled data if there is none. Run `tau models refresh` on the host to refresh immediately, regardless of cache age. It keeps every successful update and exits nonzero if any provider failed.
|
|
18
18
|
|
|
19
|
-
Remote data replaces
|
|
19
|
+
Remote data replaces matching model records completely and can add new model IDs. Tau sends its `pi-ai` version to `pi.dev` so the service returns compatible records. Cached data older than the bundled catalog is ignored.
|
|
20
20
|
|
|
21
|
-
A session
|
|
21
|
+
A session keeps the catalog that was available when it was created. A background refresh does not change it. Run `/reload` to use the host's latest cache. Switching personas keeps the session's current catalog.
|
|
22
22
|
|
|
23
23
|
## Unbundled model IDs
|
|
24
24
|
|
|
25
|
-
Custom personas and subagent launch allowlists may name
|
|
25
|
+
Custom personas and subagent launch allowlists may name a model ID that is not in the catalog, as long as the provider is known. Tau then builds the model from that provider's default template. This lets you use newly released models, but Tau does not know their real capabilities or prices. Prefer IDs from the catalog when accurate metadata matters.
|
|
26
26
|
|
|
27
27
|
## Model system notices
|
|
28
28
|
|
|
29
|
-
`modelSystemNotices`
|
|
29
|
+
`modelSystemNotices` is set in `config.json`, and its keys are checked against the model catalog:
|
|
30
30
|
|
|
31
31
|
```json
|
|
32
32
|
{
|
|
@@ -36,22 +36,22 @@ Custom personas and subagent launch allowlists may name an unbundled model ID wh
|
|
|
36
36
|
}
|
|
37
37
|
```
|
|
38
38
|
|
|
39
|
-
Keys use exact `<provider>/<model
|
|
39
|
+
Keys use the exact form `<provider>/<model>`. Provider IDs must be known. Model IDs are case-sensitive and must be in the catalog. Values must be non-empty strings. The map merges by key across configuration levels, and the nearest notice wins.
|
|
40
40
|
|
|
41
|
-
When
|
|
41
|
+
When a main agent or subagent using that model receives user input, Tau adds the notice to the start of the input as a system block that the model sees and the transcript hides. The block is saved with the user message, and later compaction treats it as part of the history. Maintenance prompts and compaction messages do not get a new notice. Ephemeral agents never receive model system notices.
|
|
42
42
|
|
|
43
|
-
Use notices for
|
|
43
|
+
Use notices for guidance specific to one model. Never put credentials or other secrets in them, because the notice is saved in the session.
|
|
44
44
|
|
|
45
45
|
## Applying and verifying changes
|
|
46
46
|
|
|
47
|
-
Run `/reload` in an idle TUI session after refreshing the model catalog or changing `modelSystemNotices`. Reload
|
|
47
|
+
Run `/reload` in an idle TUI session after refreshing the model catalog or changing `modelSystemNotices`. Reload loads the session's configuration and content again, reapplies the active persona if its ID still exists, and reports model or configuration warnings. The TUI refuses to reload while a turn is running.
|
|
48
48
|
|
|
49
|
-
|
|
49
|
+
To check, without starting the TUI, that a persona resolves to the expected provider and model for a new local session:
|
|
50
50
|
|
|
51
51
|
```sh
|
|
52
52
|
tau --debug --persona release-coder
|
|
53
53
|
```
|
|
54
54
|
|
|
55
|
-
Debug output shows
|
|
55
|
+
Debug output shows persona IDs and the selected model IDs, but not every metadata field. It also prints the full system prompt and project context, so be careful where you share it. A small real request is the final check for the endpoint, API compatibility, model access, and credentials.
|
|
56
56
|
|
|
57
|
-
Unknown providers,
|
|
57
|
+
Unknown providers, persona models that cannot be resolved, and notices for IDs missing from the catalog produce configuration warnings. In a remote session, the warnings name files on the session's execution environment. See [troubleshooting](troubleshooting.md).
|
|
@@ -1,8 +1,8 @@
|
|
|
1
1
|
# Node SDK
|
|
2
2
|
|
|
3
|
-
Tau's Node SDK
|
|
3
|
+
Tau's Node SDK is a typed client for creating, observing, and controlling sessions without handling the wire protocol yourself. Use the in-process client when your application should run the host itself, the WebSocket client to connect to a long-running `tau serve` host, or the transport adapter to bring your own connection.
|
|
4
4
|
|
|
5
|
-
The SDK
|
|
5
|
+
The SDK speaks the same [session protocol](session-protocol.md) as the TUI, so sessions behave the same in local applications, remote integrations, and the terminal.
|
|
6
6
|
|
|
7
7
|
## Install and import
|
|
8
8
|
|
|
@@ -32,7 +32,7 @@ const client = await createTauSdkClient({
|
|
|
32
32
|
});
|
|
33
33
|
```
|
|
34
34
|
|
|
35
|
-
The host uses the current
|
|
35
|
+
The host uses the current user's Tau session store and history database. The `cwd` option decides which configuration the host reads at startup, for host-wide services, and defaults to `process.cwd()`. Each session reads its own configuration and content from the execution environment and `cwd` passed to `client.sessions.create()`.
|
|
36
36
|
|
|
37
37
|
The in-process options are:
|
|
38
38
|
|
|
@@ -50,13 +50,13 @@ type TauSdkClientOptions = {
|
|
|
50
50
|
};
|
|
51
51
|
```
|
|
52
52
|
|
|
53
|
-
`persona`, `reasoning`, and `noAgentContextFiles`
|
|
53
|
+
`persona`, `reasoning`, and `noAgentContextFiles` apply to sessions created by this host. `connectTimeoutMs` defaults to 5,000 ms. Default initialization metadata is `{ client: { name: "tau-sdk", version: "1" } }`.
|
|
54
54
|
|
|
55
|
-
The in-process host
|
|
55
|
+
The in-process host never writes background diagnostics to stdout or stderr. Set `onDiagnostic` to receive them as structured objects, such as history replication failures that will be retried, and route them to your application's logging.
|
|
56
56
|
|
|
57
|
-
By default, creating an in-process client starts one
|
|
57
|
+
By default, creating an in-process client starts one background check of the model catalog against `pi.dev`. The host loads `~/.config/tau/models-store.json` first, never refreshes on a timer, and keeps each session on the catalog it started with until `session.reload()`. Set `refreshModelCatalog: false` to skip this client's check, or set `TAU_OFFLINE` to skip automatic checks for the whole process. Neither removes an existing cache or blocks an explicit `tau models refresh`. See [models](models.md) for details and [security](security.md) for why the catalog is trusted.
|
|
58
58
|
|
|
59
|
-
Closing this client shuts down its host
|
|
59
|
+
Closing this client saves live sessions and shuts down its host. It also cancels its catalog refresh and waits for it. A refresh shared with another in-process client continues until the last of them closes.
|
|
60
60
|
|
|
61
61
|
### Connect to `tau serve`
|
|
62
62
|
|
|
@@ -74,13 +74,13 @@ const client = await createTauSdkWebSocketClient({
|
|
|
74
74
|
});
|
|
75
75
|
```
|
|
76
76
|
|
|
77
|
-
Options
|
|
77
|
+
Options are `url`, optional `authToken`, `connectTimeoutMs`, `initialize`, `clientTools`, and an optional `webSocketFactory` for runtimes that need their own WebSocket implementation. Closing the client closes only its connection; the sessions stay on the server.
|
|
78
78
|
|
|
79
|
-
WebSocket
|
|
79
|
+
The WebSocket token gives full access to all sessions. See [remote sessions](remote-sessions.md) for deployment and TLS, and [security](security.md) for the trust model.
|
|
80
80
|
|
|
81
81
|
### Supply a protocol transport
|
|
82
82
|
|
|
83
|
-
`createTauSdkClientFromTransport(transport, options?)` builds the same client
|
|
83
|
+
`createTauSdkClientFromTransport(transport, options?)` builds the same client on top of any `SessionProtocolTransport`, so you can use another transport with the same session behavior.
|
|
84
84
|
|
|
85
85
|
A custom transport implements:
|
|
86
86
|
|
|
@@ -99,11 +99,11 @@ type SessionProtocolTransport = {
|
|
|
99
99
|
};
|
|
100
100
|
```
|
|
101
101
|
|
|
102
|
-
|
|
102
|
+
When the transport fails for good, it must call the `onFailure` listeners, so the SDK can abort client tools and reject open requests.
|
|
103
103
|
|
|
104
104
|
## Create and run a session
|
|
105
105
|
|
|
106
|
-
A typical integration creates
|
|
106
|
+
A typical integration creates a session (which also observes it), listens for updates, submits work, and closes cleanly:
|
|
107
107
|
|
|
108
108
|
```ts
|
|
109
109
|
import {
|
|
@@ -147,64 +147,64 @@ try {
|
|
|
147
147
|
}
|
|
148
148
|
```
|
|
149
149
|
|
|
150
|
-
`client.sessions.create(input)` sends `session.create`, then observes the new session before
|
|
150
|
+
`client.sessions.create(input)` sends `session.create`, then observes the new session before returning. `client.sessions.observe(sessionId)` observes an existing session. `client.sessions.list()` returns `{ sessionId, lifecycle }` for each session.
|
|
151
151
|
|
|
152
|
-
|
|
152
|
+
Creating a session requires the full execution environment and the creation attributes, which never change afterward. The `cwd` must be absolute and is a path in the chosen environment, which may not be where the SDK runs. A Fly Sprite session refers to an existing Sprite that the host is configured to reach. See [sessions](sessions.md) for creation attributes and [ownership and scope](ownership-and-scope.md) for which machine owns which paths.
|
|
153
153
|
|
|
154
|
-
`session.unobserve()` stops
|
|
154
|
+
`session.unobserve()` stops observing, and that `TauSdkSession` object can no longer be used. The session itself is not deleted. `client.close()` closes the whole client and is safe to call more than once.
|
|
155
155
|
|
|
156
156
|
The connected `TauSdkClient` exposes:
|
|
157
157
|
|
|
158
158
|
| Member | Purpose |
|
|
159
159
|
| --- | --- |
|
|
160
160
|
| `ready` | The validated server `ready` message and advertised methods. |
|
|
161
|
-
| `sessions.create(input)` | Create
|
|
161
|
+
| `sessions.create(input)` | Create and observe a session, and return its object. |
|
|
162
162
|
| `sessions.list()` | List hosted session summaries. |
|
|
163
|
-
| `sessions.observe(sessionId)` | Observe an existing session and return
|
|
163
|
+
| `sessions.observe(sessionId)` | Observe an existing session and return its object. |
|
|
164
164
|
| `subscribe(listener)` | Receive deltas for every observed session on this connection. |
|
|
165
165
|
| `subscribePendingUserMessages(listener)` | Receive pending-state replacements across observed sessions. |
|
|
166
166
|
| `subscribeSubagentActivities(listener)` | Receive subagent-activity changes across observed sessions. |
|
|
167
|
-
| `subscribeEphemeral(listener)` | Receive
|
|
168
|
-
| `close()` | Close the client and
|
|
167
|
+
| `subscribeEphemeral(listener)` | Receive ephemeral events, which are not guaranteed, across observed sessions. |
|
|
168
|
+
| `close()` | Close the client and everything it owns. |
|
|
169
169
|
|
|
170
170
|
Each subscription returns an unsubscribe function.
|
|
171
171
|
|
|
172
|
-
## Use the session
|
|
172
|
+
## Use the session object
|
|
173
173
|
|
|
174
|
-
`TauSdkSession.id` is the
|
|
174
|
+
`TauSdkSession.id` is the session's ID. Each method corresponds to a protocol method; the [method reference](session-protocol-methods.md) gives exact results, turn outcomes, and when a call returns `busy` or interrupts work.
|
|
175
175
|
|
|
176
176
|
| SDK method | Purpose |
|
|
177
177
|
| --- | --- |
|
|
178
178
|
| `record(text, options?)` | Append user text without running a turn. |
|
|
179
179
|
| `submit(text, options?)` | Append user text and run an idle session turn. |
|
|
180
|
-
| `queue(text, options?)` | Run now or
|
|
181
|
-
| `steer(text)` |
|
|
182
|
-
| `cancelPendingMessages()` | Cancel all queued and
|
|
180
|
+
| `queue(text, options?)` | Run now, or after the running turn. |
|
|
181
|
+
| `steer(text)` | Change the running turn's direction at its next safe point. |
|
|
182
|
+
| `cancelPendingMessages()` | Cancel all queued messages and steering not yet applied. |
|
|
183
183
|
| `retry()` | Run from current history without appending user text. |
|
|
184
|
-
| `exec(command, options?)` | Run
|
|
185
|
-
| `sample({ context, options })` | Run
|
|
186
|
-
| `interrupt()` |
|
|
187
|
-
| `snapshot()` | Read the complete
|
|
188
|
-
| `setReasoning(reasoning)` | Set reasoning
|
|
184
|
+
| `exec(command, options?)` | Run a command in a login Bash in the execution environment. |
|
|
185
|
+
| `sample({ context, options })` | Run a standalone model call without changing the session. |
|
|
186
|
+
| `interrupt()` | Ask the session's running work to stop. |
|
|
187
|
+
| `snapshot()` | Read the complete current snapshot. |
|
|
188
|
+
| `setReasoning(reasoning)` | Set reasoning, starting with the next turn. |
|
|
189
189
|
| `setPersona(personaId)` | Change persona and return the updated snapshot. |
|
|
190
190
|
| `resolvePrompt(promptId)` | Load a current prompt body from the execution environment. |
|
|
191
|
-
| `autocompletePaths({ query, limit })` |
|
|
192
|
-
| `reload()` | Reload session
|
|
191
|
+
| `autocompletePaths({ query, limit })` | Get a limited list of path suggestions from the execution environment. |
|
|
192
|
+
| `reload()` | Reload the session's configuration and content. |
|
|
193
193
|
| `compact(mode, options?)` | Manually compact model context. |
|
|
194
194
|
| `rewindToHistoryEntryId(id)` | Rewind from one user history entry while idle. |
|
|
195
195
|
| `interruptSubagent(subagentId)` | Interrupt one live subagent run. |
|
|
196
|
-
| `createEphemeralContext(options)` | Create
|
|
196
|
+
| `createEphemeralContext(options)` | Create an agent context on the host that is not saved. |
|
|
197
197
|
| `submitEphemeralThread(options)` | Run or continue one ephemeral thread. |
|
|
198
198
|
| `closeEphemeralContext(contextId)` | Close an ephemeral context and its threads. |
|
|
199
|
-
| `unobserve()` | Stop
|
|
199
|
+
| `unobserve()` | Stop observing; this object can no longer be used. |
|
|
200
200
|
|
|
201
|
-
`submit`, `queue`, and `record` accept `{ historyEntryId?: string }
|
|
201
|
+
`submit`, `queue`, and `record` accept `{ historyEntryId?: string }`; without it, Tau generates the ID. Use `getTauSdkSessionTurnRecord(snapshot, id)` to tell whether an accepted turn is unknown, running, or finished, or `getTauSdkSessionTurnOutcome(snapshot, id)` when you only need the final outcome.
|
|
202
202
|
|
|
203
|
-
`createEphemeralContext` and `submitEphemeralThread` accept an optional `reasoning` effort.
|
|
203
|
+
`createEphemeralContext` and `submitEphemeralThread` accept an optional `reasoning` effort. Without it, a new context uses the session's current effort. On submission, the given effort becomes the thread's effort before the turn runs. A fork copies the source thread's effort, then applies any given effort.
|
|
204
204
|
|
|
205
205
|
### Execute a command
|
|
206
206
|
|
|
207
|
-
`exec` generates a unique
|
|
207
|
+
`exec` generates a unique execution ID for you. It supports exact positional arguments, environment variables other than `HOME`, binary stdin, a starting `cwd`, a timeout, a capture limit, and a cancellation signal:
|
|
208
208
|
|
|
209
209
|
```ts
|
|
210
210
|
const controller = new AbortController();
|
|
@@ -219,11 +219,11 @@ const result = await session.exec('exec "$0" "$@"', {
|
|
|
219
219
|
console.log(result.exitCode, result.output);
|
|
220
220
|
```
|
|
221
221
|
|
|
222
|
-
Aborting the signal
|
|
222
|
+
Aborting the signal cancels only this command, with `session.cancelExec`, and rejects the call. Turns and other commands keep running. The command is never added to the conversation.
|
|
223
223
|
|
|
224
224
|
### Sample a model
|
|
225
225
|
|
|
226
|
-
`sample` uses the session's
|
|
226
|
+
`sample` uses the session's current model and credentials, but only the context you supply, in Tau's provider-independent format:
|
|
227
227
|
|
|
228
228
|
```ts
|
|
229
229
|
const sampled = await session.sample({
|
|
@@ -243,21 +243,21 @@ const sampled = await session.sample({
|
|
|
243
243
|
console.log(sampled.message.content);
|
|
244
244
|
```
|
|
245
245
|
|
|
246
|
-
|
|
246
|
+
You can reuse the returned assistant message in a later sample's context. If you pass tool schemas, the model may return tool calls, but Tau never runs them. Sampling sends no deltas, changes neither the snapshot revision nor the cost, and adds nothing to the conversation.
|
|
247
247
|
|
|
248
248
|
## Consume streamed state
|
|
249
249
|
|
|
250
|
-
|
|
250
|
+
`TauSdkClient` has subscriptions for all sessions on the connection, and `TauSdkSession` has subscriptions for one session. Prefer the session's own unless one component handles several sessions.
|
|
251
251
|
|
|
252
252
|
### Snapshot deltas
|
|
253
253
|
|
|
254
|
-
`session.onDelta(listener)` receives only that session's `TauSdkDelta` messages.
|
|
254
|
+
`session.onDelta(listener)` receives only that session's `TauSdkDelta` messages. Deltas that arrive before the first listener is added are kept and delivered to it. Apply them to your snapshot with `applySessionProtocolDelta`. If a revision is missing or a change is invalid, fetch a fresh copy with `session.snapshot()`.
|
|
255
255
|
|
|
256
|
-
|
|
256
|
+
Methods that return a full snapshot, such as reload, compact, rewind, and persona change, let the session object drop the kept deltas up to that revision. Do not replay UI effects from those dropped deltas.
|
|
257
257
|
|
|
258
258
|
### Pending input
|
|
259
259
|
|
|
260
|
-
`session.pendingUserMessages()` returns a
|
|
260
|
+
`session.pendingUserMessages()` returns a copy of the full pending-message state. `session.onPendingUserMessages(listener)` sends the current state right away, then each newer full replacement. Its revision is separate from the snapshot's.
|
|
261
261
|
|
|
262
262
|
```ts
|
|
263
263
|
const stopPending = session.onPendingUserMessages(({ state }) => {
|
|
@@ -265,29 +265,29 @@ const stopPending = session.onPendingUserMessages(({ state }) => {
|
|
|
265
265
|
});
|
|
266
266
|
```
|
|
267
267
|
|
|
268
|
-
|
|
268
|
+
All clients observing the live session share pending input. It is empty after recovery.
|
|
269
269
|
|
|
270
270
|
### Subagent activity
|
|
271
271
|
|
|
272
|
-
`session.subagentActivities()` returns the current
|
|
272
|
+
`session.subagentActivities()` returns the current live activity. `session.onSubagentActivities(listener)` sends the current subagents right away as `agent.set` changes, then later replacements and removals for each subagent.
|
|
273
273
|
|
|
274
|
-
|
|
274
|
+
To keep your own copy, use `applySessionProtocolSubagentActivitiesMessage`. This channel has its own revision and does not replace the saved `snapshot.agents`.
|
|
275
275
|
|
|
276
276
|
### Ephemeral events
|
|
277
277
|
|
|
278
|
-
`session.onEphemeral(listener)` receives
|
|
278
|
+
`session.onEphemeral(listener)` receives footer notices, ephemeral thread progress, and timeline notices that are not saved. Delivery is not guaranteed, and these events are never replayed or included in `session.snapshot()`.
|
|
279
279
|
|
|
280
|
-
If
|
|
280
|
+
If you show `timeline.item` events, accept only the current epoch and place each by its sequence number. Compaction and rewind causes decide which of these items you keep. The [session protocol](session-protocol.md) gives the application rules.
|
|
281
281
|
|
|
282
282
|
## Host a browser diff review
|
|
283
283
|
|
|
284
|
-
`startTauSdkDiffReview()` starts the built-in browser review UI for an observed session without
|
|
284
|
+
`startTauSdkDiffReview()` starts the built-in browser review UI for an observed session, without the TUI and without opening a browser. Your application can put it behind its own reverse proxy, store review state, restore earlier conversations, and receive the submitted review once through a callback.
|
|
285
285
|
|
|
286
|
-
See [SDK browser diff review](sdk-diff-review.md) for
|
|
286
|
+
See [SDK browser diff review](sdk-diff-review.md) for startup, storage, submission, and lifecycle.
|
|
287
287
|
|
|
288
288
|
## Provide client tools
|
|
289
289
|
|
|
290
|
-
Pass `TauSdkClientTool` entries in `clientTools`
|
|
290
|
+
Pass `TauSdkClientTool` entries in `clientTools` to give the model tools that run in your process:
|
|
291
291
|
|
|
292
292
|
```ts
|
|
293
293
|
import {
|
|
@@ -338,19 +338,19 @@ const client = await createTauSdkClient({
|
|
|
338
338
|
});
|
|
339
339
|
```
|
|
340
340
|
|
|
341
|
-
The handler receives `sessionId`,
|
|
341
|
+
The handler receives `sessionId`, the calling `agentId`, `callId`, an `AbortSignal`, and the execution-environment API. The handler runs on the client machine, while `context.executionEnvironment.exec()` runs commands in the session's execution environment.
|
|
342
342
|
|
|
343
|
-
`describe` is optional.
|
|
343
|
+
`describe` is optional. If present, the SDK calls it before accepting the call, with the arguments and a smaller context of `sessionId`, `agentId`, `callId`, and `signal`, without execution-environment access. It may return a partial presentation for the running card, with `subject`, `subjectWrap`, `details`, or `metadata`. Tau sets the action and operation, fills in omitted fields, and acknowledges with the result before calling `execute`.
|
|
344
344
|
|
|
345
|
-
The execution result may
|
|
345
|
+
The execution result may include the same partial shape for the finished card. Return a string or `{ content, presentation? }` for success, or `{ ok: false, error, presentation? }` for a handled failure. `content` may be a string, sent as one text block, or an ordered array of text and image blocks. Omitted presentation fields get Tau's defaults, and an empty `details` or `metadata` array hides that default. If `describe` throws, the SDK reports a preparation error and does not call `execute`. If no result is returned, because of cancellation, timeout, detach, or another failure, the host shows a complete default card.
|
|
346
346
|
|
|
347
|
-
Tau
|
|
347
|
+
Tau keeps every presentation field you set, up to the protocol limits, without truncating or normalizing it. `truncateTauClientToolText` truncates text for you by lines and characters, keeping the start or the middle. Use its result directly as a subject. For a block of detail text, split the result on `\n` and make each line one `details` entry; use `maxLines: 1` when the result goes into a single entry. The helper does not replace protocol validation. The SDK aborts handlers when the host cancels, the client closes, or the transport fails, and `client.close()` waits for running handlers to finish.
|
|
348
348
|
|
|
349
|
-
|
|
349
|
+
Each assistant turn keeps the tool definitions it started with. Client tools are not affected by the persona's tool list. Names must not match host tools or tools of another observing client. See [client tools](client-tools.md) for authority, limits, command-backed tools, and disconnect behavior.
|
|
350
350
|
|
|
351
351
|
### Build a code-mode tool
|
|
352
352
|
|
|
353
|
-
`createTauCodeModeClientTool()`
|
|
353
|
+
`createTauCodeModeClientTool()` turns an API you define into a client tool that runs one-off JavaScript programs against it:
|
|
354
354
|
|
|
355
355
|
```ts
|
|
356
356
|
import {
|
|
@@ -372,40 +372,40 @@ const tickets = createTauCodeModeClientTool({
|
|
|
372
372
|
});
|
|
373
373
|
```
|
|
374
374
|
|
|
375
|
-
Pass `tickets` in `clientTools`.
|
|
375
|
+
Pass `tickets` in `clientTools`. The model's code receives your API namespace, `docs` (read on demand), `printText`, the async `printImage`, `truncate` and `truncateLines`, and the real `Date` and `Math`. API calls pass through a size-limited JSON bridge. The submitted code, truncated and wrapped, is the subject of the running and finished tool cards. You write the description; the description builder is optional.
|
|
376
376
|
|
|
377
|
-
Use `await printImage({ data, mimeType })` to
|
|
377
|
+
Use `await printImage({ data, mimeType })` to return a base64 image. Results contain an ordered `content` array of text and image blocks, and SDK client tools keep that order: consecutive text output forms one block, and each image splits the text before and after it. The helper validates and prepares JPEG, PNG, or WebP images outside the sandbox, creates no files, and uses the limits described in [tools](tools.md).
|
|
378
378
|
|
|
379
|
-
Code-mode
|
|
379
|
+
Code-mode calls and standalone runs accept an optional `maxOutputTokens` (1 through 65,536), with a default text budget of 8,192 tokens. Saving output to files is off unless the definition provides a `persistOutput` callback.
|
|
380
380
|
|
|
381
|
-
The SDK also exports `executeTauCodeMode` for standalone
|
|
381
|
+
The SDK also exports `executeTauCodeMode` for standalone runs. The separate `@markusylisiurunen/tau/code-mode` entry point also exports `runTauClientToolCommand` and `runTauCodeModeCommand` for command tools. Use these helpers instead of implementing the protocol yourself.
|
|
382
382
|
|
|
383
383
|
## Cancel and close deliberately
|
|
384
384
|
|
|
385
|
-
Most turn and
|
|
385
|
+
Most turn and session-changing methods do not accept an `AbortSignal`. Call `session.interrupt()` to stop running work on the host. `session.exec()` is the exception: its optional signal cancels only that command.
|
|
386
386
|
|
|
387
|
-
`session.unobserve()`
|
|
387
|
+
`session.unobserve()` ends one session object. `client.close()` ends the connection: it rejects open requests, aborts client tool handlers, waits for them to finish, and closes the transport. For the default in-process client, it also saves sessions and shuts down the host. Over WebSocket, the remote host and its sessions keep running.
|
|
388
388
|
|
|
389
|
-
Always close clients in `finally`.
|
|
389
|
+
Always close clients in `finally`. Never use a session object after `unobserve()`, or a client after `close()`.
|
|
390
390
|
|
|
391
391
|
## Handle errors
|
|
392
392
|
|
|
393
393
|
All exported SDK and transport errors extend `TauSessionClientError`:
|
|
394
394
|
|
|
395
395
|
- `TauSessionProtocolResponseError` means the host returned a protocol error. It exposes `code`, `message`, `requestId`, and optional `data`.
|
|
396
|
-
- `TauTransportError` means connection setup, framing, version
|
|
396
|
+
- `TauTransportError` means the connection failed: during setup, framing, version checks, a timeout, closing, or another fatal transport error.
|
|
397
397
|
|
|
398
398
|
Branch on a protocol error's `code`, not its message. A successful request can still return a failed, aborted, or blocked turn outcome, so inspect `result.turn.status` separately.
|
|
399
399
|
|
|
400
|
-
|
|
400
|
+
An exception in one listener does not stop delivery to others. Handle errors inside your listeners, and keep state updates deterministic.
|
|
401
401
|
|
|
402
402
|
## Use the public types and helpers
|
|
403
403
|
|
|
404
|
-
The SDK entry point exports
|
|
404
|
+
The SDK entry point exports every type an integration needs, so you never import from internal modules:
|
|
405
405
|
|
|
406
406
|
- `TauSdkClient`, `TauSdkSession`, client option types, session summaries, and request and result aliases;
|
|
407
407
|
- `TauSdkDelta`, `SessionProtocolSnapshot`, pending-message types, subagent-activity types, and ephemeral event types;
|
|
408
|
-
- `TauSdkClientTool`, its execution context and environment
|
|
408
|
+
- `TauSdkClientTool`, its execution context and execution-environment API, and code-mode definition and result types;
|
|
409
409
|
- `SessionProtocolTransport`, listener types, WebSocket options, and transport errors.
|
|
410
410
|
|
|
411
411
|
It also exports `applySessionProtocolDelta`, `applySessionProtocolSubagentActivitiesMessage`, the turn-ledger helpers, and user-text projection helpers:
|
|
@@ -418,4 +418,4 @@ import {
|
|
|
418
418
|
} from "@markusylisiurunen/tau/sdk";
|
|
419
419
|
```
|
|
420
420
|
|
|
421
|
-
Use `getTauUserDisplayText` before
|
|
421
|
+
Use `getTauUserDisplayText` before showing user text from a snapshot. It removes Tau metadata and leading hidden `<system>` blocks. `getTauUserModelText` removes Tau metadata but keeps the hidden blocks the model sees. `projectTauUserText` returns both. These helpers are for user messages only.
|