Skip to content

feat(proxy): harden authorized tool discovery - #5

Merged
lennney merged 1 commit into
mainfrom
feature/find-tool-readiness
Aug 14, 2026
Merged

feat(proxy): harden authorized tool discovery#5
lennney merged 1 commit into
mainfrom
feature/find-tool-readiness

Conversation

@lennney

@lennney lennney commented Aug 10, 2026

Copy link
Copy Markdown
Owner

Outcome

Harden portable find_tool discovery without changing the three-tool Interface or the Native, Compact, and Extreme mode contract.

  • snapshot the authorized catalog before indexing or invocation;
  • use canonical catalog identity and locale-independent ordering;
  • index bounded nested schema metadata while returning the complete original input schema;
  • reject extra fields and raw queries longer than 256 Unicode code points locally;
  • strengthen Runner-owned authorization, schema-integrity, determinism, no-match, and zero-upstream evidence;
  • exercise both Compact and Extreme through the installed-package smoke;
  • keep 0.1.1-alpha.2 documented as an unpublished source candidate.

Related issue

N/A.

Change type

  • Feature
  • Bug fix
  • Breaking change
  • Documentation
  • Performance
  • Refactor
  • Build or CI

Verification

npm run ci
# 43 test files passed; 506 tests passed
# 1 POSIX-only test skipped on Windows
# package boundary: 75 allowed files, 409,030 unpacked bytes, zero source maps

npm run smoke:package
# Compact install/start/find/call/read/uninstall passed
# one business upstream call; exact recovery verified

npm run smoke:package:extreme
# Extreme install/start/find/call/read/uninstall passed
# one business upstream call; exact recovery verified

Compatibility and recovery

  • No new public Tool or configuration field.
  • Compact and Extreme remain find_tool, call_tool, and read_result.
  • Native remains authorized upstream Tools plus read_result.
  • Original-schema validation, at-most-once upstream execution, exact local recovery, and fail-open exact delivery remain unchanged.
  • Overlong or extra-field find_tool requests fail locally without an upstream business call.
  • Alpha2 remains unpublished; the README and Host setup use reviewed source installation instructions.

Checklist

  • This pull request covers one focused behavior.
  • The branch is based on the latest main.
  • No credentials, private paths, result bodies, local artifacts, internal plans, research notes, or launch drafts are included.
  • Relevant focused tests pass.
  • npm run typecheck, npm run lint, and npm run format:check pass.
  • Routing and stdio changes include installed-package smokes.
  • No new public compression, token, latency, billing, or accuracy claim is introduced.
  • CHANGELOG.md and the English/Chinese setup documentation are updated.

@lennney
lennney marked this pull request as ready for review August 11, 2026 07:22
Copilot AI lite review requested due to automatic review settings August 11, 2026 07:22

Copilot AI left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Copilot was unable to review this pull request because the user who requested the review has reached their quota limit.

@chatgpt-codex-connector chatgpt-codex-connector Bot left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

💡 Codex Review

Here are some automated review suggestions for this pull request.

Reviewed commit: 4f1ab7805e

ℹ️ About Codex in GitHub

Your team has set up Codex to review pull requests in this repo. Reviews are triggered when you

  • Open a pull request for review
  • Mark a draft as ready
  • Comment "@codex review".

If Codex has suggestions, it will comment; otherwise it will react with 👍.

Codex can also answer questions or update the PR. Try commenting "@codex address that feedback".

Comment on lines +1799 to +1801
const upstreamCallCount = observations.reduce(
(sum, entry) => sum + (typeof entry.upstream_call_count === "number" ? entry.upstream_call_count : 0),
0,

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

P1 Badge Check zero-upstream evidence in the repeat run

When the adapter's repeat run invokes an upstream business Tool or omits upstream_events, this sum still reads only the primary observations; repeat_observations contributes only its ranking signature. The repeat can therefore have side effects while zero_upstream_calls passes, producing false security evidence, so upstream evidence must be required and aggregated for both matrices.

Useful? React with 👍 / 👎.

Comment thread src/deterministic-json.ts
Comment on lines +27 to +30
const output: Record<string, unknown> = {};
for (const key of Object.keys(value).sort(compareStableText)) {
const normalized = canonicalize((value as Record<string, unknown>)[key], ancestors);
if (normalized !== undefined) output[key] = normalized;

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

P2 Badge Preserve __proto__ keys in canonical catalogs

When an upstream JSON Schema defines a valid property named __proto__, assigning that key into {} invokes the legacy prototype setter instead of creating an own property. Canonical serialization consequently drops the definition, so catalogs that differ only in this property's schema receive the same digest and tool references; the proxy signature also misses the schema change and may suppress its tool-list notification. Construct the canonical object with a null prototype or an own-property-safe API such as Object.fromEntries.

Useful? React with 👍 / 👎.

@lennney
lennney merged commit a5596a0 into main Aug 14, 2026
4 checks passed
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants