@hydraharness/harness-agent-tool-presentation 0.1.1-rc.5

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/LICENSE ADDED
@@ -0,0 +1,21 @@
1
+ MIT License
2
+
3
+ Copyright (c) 2026 DeepSeek
4
+
5
+ Permission is hereby granted, free of charge, to any person obtaining a copy
6
+ of this software and associated documentation files (the "Software"), to deal
7
+ in the Software without restriction, including without limitation the rights
8
+ to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
9
+ copies of the Software, and to permit persons to whom the Software is
10
+ furnished to do so, subject to the following conditions:
11
+
12
+ The above copyright notice and this permission notice shall be included in all
13
+ copies or substantial portions of the Software.
14
+
15
+ THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16
+ IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17
+ FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
18
+ AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
19
+ LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
20
+ OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
21
+ SOFTWARE.
package/README.md ADDED
@@ -0,0 +1,29 @@
1
+ # @hydraharness/harness-agent-tool-presentation
2
+
3
+ The row an [agent preset](../../preset/agent-presets/README.md) carries to say which form of its tools the model sees: `native` (every schema), `code` (only `run_code` plus a generated TypeScript SDK), or `both`.
4
+
5
+ ## Why a row rather than a registry
6
+
7
+ The tool registry cannot move into a preset. Its consumers are all host-plane — [`@hydraharness/harness-agent-loop`](../agent-loop/README.md) reads its scheduler, [`hydra-apiproxy`](../../host/apiproxy/README.md) reads its presenters to render tool cards, and every tool plugin registers into it — and a service only moves down when all of its consumers move with it.
8
+
9
+ What a preset can own is the **presentation** of that registry. `ctx.tools.presentAs()` declares it for the mounting agent alone, so a Code Mode session runs beside native ones in one process, each seeing its own catalog. The deployment's `mode` on the [`@hydraharness/harness-tools`](../tools/README.md) row remains the default that agents declaring nothing get.
10
+
11
+ ## What it does
12
+
13
+ `native` applies immediately. A code mode instead waits for `ctx.codeRuntime`, which is a host-plane service ([`@hydraharness/harness-code-runtime-worker-thread`](../../code-runtime/code-runtime-worker-thread/README.md)): a preset selecting Code Mode against a deployment composing no runtime then holds this row pending, and `@hydraharness/harness-agent-presets` refuses the mount naming this id. The alternative — applying optimistically — moves the failure to the session's first request, where the operator can act on neither the preset nor the composition.
14
+
15
+ `mode` is required rather than defaulted, because a preset without this row already gets the deployment default; an omitted value would mean the row was composed for nothing.
16
+
17
+ One agent declares one presentation. A second declaration in the same composition is refused rather than merged: two answers to "which form does the model see" is a contradiction, not an override.
18
+
19
+ ## Model Experience
20
+
21
+ Indirectly, through the projection it selects in `@hydraharness/harness-tools`: `code` presents `run_code` plus a generated SDK section and the rule that only `run_code` may be called directly, `native` presents every tool schema. The selection also decides what may EXECUTE: under `code` the registry resolves a model-direct call naming any other tool to `UNKNOWN_TOOL`, so this row is what keeps the announced surface and the callable surface the same for every agent it covers ([executor-collapse note](../../../.agents/notes/implemented/bug-fix/2026-08-07-code-mode-executor-collapse.md)).
22
+
23
+ #### KV Cache effect
24
+
25
+ No direct invalidation; the presentation is fixed when the agent is composed, so its request prefix is stable for the session's life.
26
+
27
+ ## Known Limitations and Deferred Work
28
+
29
+ - **The runtime stays host-plane** — a preset can select Code Mode but cannot supply the TypeScript runtime it needs; a deployment that composes none can compose no code-mode preset.
package/lib/index.js ADDED
@@ -0,0 +1,51 @@
1
+ import z from "@hydraharness/schemastery";
2
+ //#region lib/types/index.js
3
+ /**
4
+ * Agent-plane presentation selector: the row an agent preset carries to say
5
+ * which form of its tools the model sees.
6
+ *
7
+ * The tool registry itself stays on the host plane — the agent loop's
8
+ * scheduler, the API proxy's presenters, and every tool plugin are all its
9
+ * consumers, so it cannot move into a preset. What a preset CAN own is the
10
+ * presentation: `ctx.tools.presentAs()` declares it for the mounting SCOPE,
11
+ * which is the preset's standing mount, so the declaration covers every agent
12
+ * joined to that preset and a Code Mode preset runs beside native ones in one
13
+ * process. One row per composition, not one per session.
14
+ *
15
+ * A code mode needs a TypeScript code runtime, which is a host-plane service
16
+ * ([`@hydraharness/harness-code-runtime-worker-thread`](../../code-runtime/code-runtime-worker/README.md)).
17
+ * This row therefore waits for it rather than assuming it: a preset selecting
18
+ * Code Mode against a deployment that composes no runtime fails at mount, named
19
+ * in the preset's own activation audit, instead of at the first prompt.
20
+ * @module @hydraharness/harness-agent-tool-presentation
21
+ */
22
+ /** Cordis plugin name. */
23
+ const name = "tool-presentation";
24
+ /**
25
+ * Required services. `codeRuntime` is NOT listed: a `native` row must mount in
26
+ * a deployment that composes no runtime, and the mode-dependent wait is
27
+ * declared inside {@link apply} instead.
28
+ */
29
+ const inject = ["tools"];
30
+ /** Runtime schema. */
31
+ const Config = z.object({ mode: z.union([
32
+ "native",
33
+ "code",
34
+ "both"
35
+ ]).required() });
36
+ /**
37
+ * Declare the tool presentation for every agent this composition covers.
38
+ * @param ctx - the mounting composition's scope context (a preset's standing scope).
39
+ * @param config - the selected presentation.
40
+ */
41
+ function apply(ctx, config) {
42
+ if (config.mode === "native") {
43
+ ctx.tools.presentAs("native");
44
+ return;
45
+ }
46
+ ctx.inject(["codeRuntime"], (runtimeCtx) => {
47
+ runtimeCtx.tools.presentAs(config.mode);
48
+ });
49
+ }
50
+ //#endregion
51
+ export { Config, apply, inject, name };
@@ -0,0 +1,25 @@
1
+ //#region lib/types/invariant.js
2
+ /**
3
+ * Package-owned invariant companion for `@hydraharness/harness-agent-tool-presentation`.
4
+ * @module @hydraharness/harness-agent-tool-presentation/invariant
5
+ */
6
+ const PACKAGE_NAME = "@hydraharness/harness-agent-tool-presentation";
7
+ /** Cordis companion plugin name. */
8
+ const name = "tool-presentation-invariant";
9
+ /** Service required before the companion can reserve package ownership. */
10
+ const inject = ["invariants"];
11
+ /**
12
+ * No runtime invariant: this package makes exactly one scoped call into
13
+ * `ctx.tools` and owns no event or snapshot of its own; the relation it
14
+ * establishes — which presentation one agent's assembly uses — is the tool
15
+ * registry's to hold, and `@hydraharness/harness-tools` observes it there.
16
+ */
17
+ const install = () => {};
18
+ /**
19
+ * Register this package's invariant companion.
20
+ * @param ctx - Cordis context carrying the invariant service.
21
+ * @returns the installed registration's disposer after setup succeeds.
22
+ */
23
+ const apply = (ctx) => Promise.resolve(ctx.invariants.register(PACKAGE_NAME, install));
24
+ //#endregion
25
+ export { apply, inject, name };
@@ -0,0 +1,50 @@
1
+ /**
2
+ * Agent-plane presentation selector: the row an agent preset carries to say
3
+ * which form of its tools the model sees.
4
+ *
5
+ * The tool registry itself stays on the host plane — the agent loop's
6
+ * scheduler, the API proxy's presenters, and every tool plugin are all its
7
+ * consumers, so it cannot move into a preset. What a preset CAN own is the
8
+ * presentation: `ctx.tools.presentAs()` declares it for the mounting SCOPE,
9
+ * which is the preset's standing mount, so the declaration covers every agent
10
+ * joined to that preset and a Code Mode preset runs beside native ones in one
11
+ * process. One row per composition, not one per session.
12
+ *
13
+ * A code mode needs a TypeScript code runtime, which is a host-plane service
14
+ * ([`@hydraharness/harness-code-runtime-worker-thread`](../../code-runtime/code-runtime-worker/README.md)).
15
+ * This row therefore waits for it rather than assuming it: a preset selecting
16
+ * Code Mode against a deployment that composes no runtime fails at mount, named
17
+ * in the preset's own activation audit, instead of at the first prompt.
18
+ * @module @hydraharness/harness-agent-tool-presentation
19
+ */
20
+ import type { Context } from '@hydraharness/cordis';
21
+ import z from '@hydraharness/schemastery';
22
+ import type { ToolPresentationMode } from '@hydraharness/harness-tools';
23
+ /** Cordis plugin name. */
24
+ export declare const name = "tool-presentation";
25
+ /**
26
+ * Required services. `codeRuntime` is NOT listed: a `native` row must mount in
27
+ * a deployment that composes no runtime, and the mode-dependent wait is
28
+ * declared inside {@link apply} instead.
29
+ */
30
+ export declare const inject: string[];
31
+ /** Plugin config. */
32
+ export interface Config {
33
+ /**
34
+ * The form this agent's model sees. `native` sends every visible schema,
35
+ * `code` sends only `run_code` plus a generated SDK, `both` sends both.
36
+ * Required rather than defaulted: the deployment default is what a preset
37
+ * without this row already gets, so an omitted value would mean the row was
38
+ * composed for nothing.
39
+ */
40
+ mode: ToolPresentationMode;
41
+ }
42
+ /** Runtime schema. */
43
+ export declare const Config: z<Config>;
44
+ /**
45
+ * Declare the tool presentation for every agent this composition covers.
46
+ * @param ctx - the mounting composition's scope context (a preset's standing scope).
47
+ * @param config - the selected presentation.
48
+ */
49
+ export declare function apply(ctx: Context, config: Config): void;
50
+ //# sourceMappingURL=index.d.ts.map
@@ -0,0 +1,16 @@
1
+ /**
2
+ * Package-owned invariant companion for `@hydraharness/harness-agent-tool-presentation`.
3
+ * @module @hydraharness/harness-agent-tool-presentation/invariant
4
+ */
5
+ import type { Context } from '@hydraharness/cordis';
6
+ /** Cordis companion plugin name. */
7
+ export declare const name = "tool-presentation-invariant";
8
+ /** Service required before the companion can reserve package ownership. */
9
+ export declare const inject: string[];
10
+ /**
11
+ * Register this package's invariant companion.
12
+ * @param ctx - Cordis context carrying the invariant service.
13
+ * @returns the installed registration's disposer after setup succeeds.
14
+ */
15
+ export declare const apply: (ctx: Context) => Promise<() => void>;
16
+ //# sourceMappingURL=invariant.d.ts.map
package/package.json ADDED
@@ -0,0 +1,57 @@
1
+ {
2
+ "name": "@hydraharness/harness-agent-tool-presentation",
3
+ "description": "Agent-plane presentation selector: composes one agent's tools as Code Mode, native, or both",
4
+ "hydra": {
5
+ "plugin": {
6
+ "application": "Expose a preset's tools as native calls, Code Mode functions, or both."
7
+ }
8
+ },
9
+ "version": "0.1.1-rc.5",
10
+ "publishConfig": {
11
+ "access": "public"
12
+ },
13
+ "repository": {
14
+ "type": "git",
15
+ "url": "git+https://github.com/MaiHongPhong1902/Hydra-Harness.git",
16
+ "directory": "packages/core/agent-tool-presentation"
17
+ },
18
+ "type": "module",
19
+ "main": "lib/index.js",
20
+ "types": "lib/types/index.d.ts",
21
+ "exports": {
22
+ ".": {
23
+ "types": "./lib/types/index.d.ts",
24
+ "default": "./lib/index.js"
25
+ },
26
+ "./invariant": {
27
+ "types": "./lib/types/invariant.d.ts",
28
+ "default": "./lib/invariant.js"
29
+ },
30
+ "./src/*": "./src/*",
31
+ "./package.json": "./package.json"
32
+ },
33
+ "files": [
34
+ "lib/index.js",
35
+ "lib/invariant.js",
36
+ "lib/types/**/*.d.ts"
37
+ ],
38
+ "license": "MIT",
39
+ "dependencies": {
40
+ "@hydraharness/schemastery": "^3.18.2"
41
+ },
42
+ "peerDependencies": {
43
+ "@hydraharness/harness-invariants": "^0.1.1-rc.5",
44
+ "@hydraharness/harness-tools": "^0.1.1-rc.5",
45
+ "@hydraharness/cordis": "^4.0.2"
46
+ },
47
+ "devDependencies": {
48
+ "@hydraharness/harness-scope": "^0.1.1-rc.5",
49
+ "@hydraharness/harness-code-runtime": "^0.1.1-rc.5",
50
+ "@hydraharness/harness-session": "^0.1.1-rc.5",
51
+ "@hydraharness/harness-invariants": "^0.1.1-rc.5",
52
+ "@hydraharness/harness-agent": "^0.1.1-rc.5",
53
+ "@hydraharness/harness-system-prompt": "^0.1.1-rc.5",
54
+ "@hydraharness/harness-tools": "^0.1.1-rc.5",
55
+ "@hydraharness/cordis": "^4.0.2"
56
+ }
57
+ }