Commit Graph

1296 Commits

Author SHA1 Message Date
Alberto Schiabel 705591451c chore(deps): upgrade CI actions and every outdated dependency (#4381)
This PR:

- upgrades every CI action to its latest release (only
`changesets/action` had one: v2.1.1 -> v2.1.2, SHA-pinned) and every
outdated dependency across the pnpm workspace, the docs bun workspace,
and all three `uv.lock` files
- moves zod to 4.5.4 everywhere first-party — catalog, docs,
`@composio/json-schema-to-zod`, `@composio/claude-agent-sdk` and the
zod-v4 e2e fixtures; the `*-zod-v3` fixtures stay on 3.25.76 because
that is what they exercise
- moves `@mastra/core` 1.52.1 -> 1.53.0, which is the ceiling rather
than a preference: bisecting `ts/examples/mastra`'s `cf:dry-run` shows
1.54.0 moved the workspace/sandbox subsystem behind
`@mastra/core/agent`, which drags execa (-> `npm-run-path` ->
`unicorn-magic`) into the Workers bundle where esbuild cannot link it.
`@mastra/mcp` is capped at 1.17.2 for the same reason — 1.17.3 wants
`@mastra/core` >=1.64. The docs bun workspace mirrors that cap as an
explicit devDependency plus `overrides` entry, because bun does not
apply overrides to auto-installed peers
- clears every production advisory that has a published fix, so the
audit gate can run without `--ignore`, which does not filter a single
run: it writes the advisory into `auditConfig` and exits 0 whatever else
is outstanding, so the gate was passing over nine advisories
- `qs` -> >=6.16.0, `fast-uri` -> >=3.1.6, `toml` -> the 4.x line, all
via overrides in the existing `# temporary: … drop when` style
- `extract-zip` (GHSA-jmr9-qjv8-65gv) has no fixed version to move to —
2.0.1 is the newest release and GitHub records `first_patched_version`
as null — so it moves to `auditConfig.ignoreGhsas` pointing at the
`extractZipSafely` mitigation that already covers it
- GHSA-866g-f22w-33x8 (`@ai-sdk/provider-utils` 3.x, low) also has
nothing to move to: the advisory names 3.0.98 as patched but the 3.x
line stopped at 3.0.30 and GitHub records no fixed version. It only
enters the tree through `@mastra/core`, which is a peer or dev
dependency of every published package, so all flagged paths are private
examples and e2e fixtures. It goes in `ignoreGhsas` with that rationale
so the un-levelled `pnpm audit --prod` step stops posting a warning
comment on every PR
- widens `@composio/anthropic`'s `@anthropic-ai/sdk` peer range to
include `^0.124.0`, the line its devDependency now tests against (for a
`0.x` caret, `^0.120.0` excluded it); the package is in the changeset
for that reason
- adapts three call sites that upstream broke: `eve` 0.52 moved
`ApprovalContext` to `eve/tools/approval`, `@pierre/diffs` 1.4 gave
`FileDiffProps` a second type parameter, and `fumadocs-openapi` 11.4
fixed the undeclared-tag drop that a docs guard test asserted (the guard
now also asserts the page positively, so it cannot pass vacuously)
- drops the stale `hono` `minimumReleaseAgeExclude` entry (its comment
said to after 2026-08-06) and adds an `undici` `peerDependencyRules`
allowance for openai 7.10's new optional peer

## Context

Some upgrades were deliberately declined, each for a reason recorded
next to the pin:

- `vitest`/`@vitest/ui` stay on 4.1.11 —
`@cloudflare/vitest-pool-workers@0.22.0` (latest) peers on `vitest
^4.1.0`
- `undici` stays on `^7` in core — `pinnedDispatcher.node.ts` documents
that Node's `fetch` rejects undici 8 dispatchers
- the `pnpm` catalog entry stays on `^11` to match the mise-owned
toolchain
- `eve` stays on 0.27.6 in docs — 0.52 changes the `defineAgent` model
definition and the `useEveAgent` helpers, so `agent/agent.ts` and
`components/eve-chat.tsx` fail `types:check`; migrating the docs agent
is its own PR
- `@earendil-works/pi-coding-agent` stays on 0.84.4 — 0.85.x imports
`@earendil-works/pi-server` without declaring it, so `test/pi.test.ts`
fails to load

`declareOperationTags` is kept as a safety net rather than retired, even
though `fumadocs-openapi` 11.4 makes it redundant: removing it changes
how specs are normalised at sync time and is worth its own PR.

Verified locally: `pnpm build:packages`, `pnpm typecheck`, `pnpm test`,
`pnpm typecheck:examples`, `pnpm lint:examples`, `turbo cf:dry-run
--filter='./ts/examples/*'`, `pnpm peers check`, `pnpm audit --prod
--audit-level=high` (exit 0), frozen-lockfile installs for pnpm and bun,
docs `types:check` + 542 static tests, and Python `make chk` + `make
tst` (1790 passed).

https://claude.ai/code/session_018evFic47PFPXuB95uRE1aw
EOF -R ComposioHQ/composio
2026-09-08 16:15:34 +02:00
Alberto Schiabel 0fb479b8f1 Merge commit from fork
* fix(cli): escape generated source metadata

* test(cli): execute generated Python regression

* fix(cli): order Python fallback assignments

---------

Co-authored-by: jkomyno <12381818+jkomyno@users.noreply.github.com>
2026-09-08 14:59:48 +02:00
Alberto Schiabel 230f81a737 refactor(cli): import @effect/platform modules by subpath (#4360)
This PR:

- rebases onto `next` now that
https://github.com/ComposioHQ/composio/pull/4358 and
https://github.com/ComposioHQ/composio/pull/4359 are merged
- rewrites every `@effect/platform` and `@effect/platform-bun` barrel
import under `ts/packages/cli` (155 statements in 112 files) as a
per-module namespace import, e.g. `import * as FileSystem from
'@effect/platform/FileSystem'`
- adds both barrels to the `no-restricted-imports` lists for
`ts/packages/cli/src`, with messages pointing at the subpath form
- updates the boundary guidance in `ts/packages/cli/AGENTS.md` and the
`cli-command` skill to the subpath form

## Context

Both barrels are pure namespace re-exports (60 and 19 modules), so this
is import-only with no runtime change. Effect v4 spreads these modules
across `effect` (`FileSystem`, `Path`, `PlatformError`),
`effect/unstable/http`, and `effect/unstable/process`; with per-module
imports the port becomes a scripted path rewrite instead of
hand-splitting each barrel line. Third of three preparation PRs.

## Validation

- `pnpm --filter @composio/cli typecheck` and oxlint clean; a probe
barrel import in `src/` is rejected by the new rule
- `pnpm --filter @composio/cli test`: 127 files, 1318 tests pass, 1
skipped
2026-09-07 15:14:15 +02:00
Alberto Schiabel f5ff810f2e refactor(cli): define services with Context.Tag and thread argv explicitly (#4359)
This PR:

- builds on top of https://github.com/ComposioHQ/composio/pull/4358
- replaces the eleven `Effect.Service` files (fourteen services) with
`Context.Tag` classes that export a `<Name>Shape` type and an explicit
`static readonly Default` layer built from a `make<Name>` constructor
- removes the three `accessors: true` declarations; nothing in `src/`
used a generated accessor, and the one test that did now yields the
service
- builds test doubles with `Service.of({ ... })` instead of `new
Service({ ... })`, and types helper parameters with the `Shape` types
where the class had been used as a type
- passes the normalized argv from `bin.ts` into `runCli` and through
`cli-main.ts` instead of mutating `process.argv` and reading it back in
five places
- documents the service pattern in `ts/packages/cli/AGENTS.md`

## Context

Effect v4 replaces `Effect.Service` with `Context.Service`, which
generates neither a `.Default` layer nor accessors; with the
explicit-layer shape already on v3, the port turns each service into a
one-line rename. `Command.runWith` in `effect/unstable/cli` takes user
arguments explicitly, so `cli-main.ts` now receives argv rather than
re-reading process state. Second of three preparation PRs.

## Validation

- `pnpm --filter @composio/cli typecheck`, `validate:boundaries`, and
oxlint clean
- `pnpm --filter @composio/cli test`: 127 files, 1319 tests pass, 1
skipped
2026-09-07 12:34:13 +02:00
Alberto Schiabel 20aaa95c96 ci(ts): verify packed provider compatibility (#4355)
This PR:

- adds a clean consumer harness that packs core, its internal JSON
Schema dependency, and all ten TypeScript providers
- verifies tarball contents, npm installation, named public exports,
consumer typechecking, provider construction, and a credential-free
`wrapTool` conversion
- covers the current workspace core, one verified minimum-core lane per
provider, and the packed workspace core presented as `1.0.0-beta.0`
- preserves existing 0.x minimum peer ranges while recording the
verified floors separately for the future breaking release
- additively accepts core 1.0 prereleases without claiming stable 1.x
support yet
- widens the Anthropic and OpenAI Agents peer ranges to include the
upstream versions already used by this repository
- runs the gate in TypeScript CI and immediately before Changesets
publishing

The release guard fails before publication and its regression test
verifies build -> compatibility -> publish ordering plus failure
propagation.

## Non-breaking scope

No public API is removed or renamed, and the existing 0.x core peer
floors remain unchanged. All peer-range changes are additive. The gate
reports the nine floor corrections that should be made with the planned
breaking release.

## Validation

- `pnpm run check:provider-compatibility` (12 packed consumer lanes)
- `pnpm run test:provider-compatibility`
- `pnpm run test:release-workflow`
- `pnpm run build:packages` (19 packages)
- focused TypeScript compile and Oxlint checks
- Prettier, Changesets validation, and `git diff --check`
2026-09-07 12:33:53 +02:00
sdkrelease[bot] 61c3cb6481 chore(cli): refresh baked toolkit slugs (#4372)
## Summary
Automated refresh of the toolkit slugs the CLI knows without asking
the API, generated by
`ts/packages/cli/scripts/generate-toolkit-slugs.ts`.

Toolkits added since the last refresh currently cost users one
toolkit-list fetch (~2 s) the first time they run one of that
toolkit's tools. Merging this makes them free.

The generator refuses to write a list that is short, malformed, or
missing staple toolkits, so a bad fetch opens no PR at all.

Co-authored-by: jkomyno <12381818+jkomyno@users.noreply.github.com>
2026-09-07 12:33:27 +02:00
Alberto Schiabel d4077ba415 chore(cli): trim unused Effect packages and unify version output (#4358)
This PR:

- drops the eight `@effect/*` satellite devDependencies and
`@effect/platform-node-shared` from `@composio/cli`; none is imported by
the CLI, its tests, or its scripts, and the
`@effect/platform-node-shared` catalog entry goes with them
- makes `--log-level` fall back to `COMPOSIO_LOG_LEVEL` when the flag is
absent (`Option.orElse` instead of `Option.zipLeft`, which discarded the
env value) and adds a precedence test
- rewrites `composio --version` and `composio -v` to the `version`
command before parsing, so the three spellings share one handler and
print identical output (the framework built-in used to add a trailing
blank line); CI and the installer keep using `composio --version`

## Context

First of three preparation PRs for the Effect v4 port;
https://github.com/ComposioHQ/composio/pull/3901 is the reference port.
Each lands v3-compatible groundwork that the port otherwise has to redo
on top of a large diff: the manifest, catalog, and lockfile were three
of the conflicting files in that PR, and its review had accepted Effect
v4's default `composio v<semver>` banner for `--version`. Owning the
flag in argv normalization keeps `--version` output stable across the
framework change instead.

## Validation

- `pnpm --filter @composio/cli typecheck` and oxlint clean
- `pnpm --filter @composio/cli test`: 127 files, 1318 tests pass, 1
skipped; `version`, `--version`, and `-v` are asserted byte-identical
- The Docker install e2e suite was not run locally;
`cli.install-e2e.yml` runs it on this PR
2026-09-05 00:22:11 +02:00
sdkrelease[bot] 2573c64d97 Release: update version (#4285)
This PR was opened by the [Changesets
release](https://github.com/changesets/action) GitHub action. When
you're ready to do a release, you can merge this and the packages will
be published to npm automatically. If you're not ready to do a release
yet, that's fine, whenever you add more changesets to next, this PR will
be updated.


# Releases
## @composio/claude-agent-sdk@0.12.0

### Minor Changes

- 9447932: Dereference internal $ref/$defs in tool input schemas before
provider translation, so properties reachable only through a reference
keep their types and validation instead of degrading to untyped (z.any)
or being emitted as a dangling reference.

This changes the JSON Schema these providers emit for $ref-using tools.
Downstream snapshot tests on tool definitions will see diffs. Schemas
the Composio API ships with a $ref but no $defs block (e.g.
GMAIL_FETCH_EMAILS) degrade to a permissive object schema rather than
throwing. The strict-structured-outputs path of @composio/openai-agents
is unchanged — OpenAI supports $defs/$ref natively, including recursion.
## @composio/google@0.11.0

### Minor Changes

- 9447932: Dereference internal $ref/$defs in tool input schemas before
provider translation, so properties reachable only through a reference
keep their types and validation instead of degrading to untyped (z.any)
or being emitted as a dangling reference.

This changes the JSON Schema these providers emit for $ref-using tools.
Downstream snapshot tests on tool definitions will see diffs. Schemas
the Composio API ships with a $ref but no $defs block (e.g.
GMAIL_FETCH_EMAILS) degrade to a permissive object schema rather than
throwing. The strict-structured-outputs path of @composio/openai-agents
is unchanged — OpenAI supports $defs/$ref natively, including recursion.
## @composio/langchain@0.11.0

### Minor Changes

- 9447932: Dereference internal $ref/$defs in tool input schemas before
provider translation, so properties reachable only through a reference
keep their types and validation instead of degrading to untyped (z.any)
or being emitted as a dangling reference.

This changes the JSON Schema these providers emit for $ref-using tools.
Downstream snapshot tests on tool definitions will see diffs. Schemas
the Composio API ships with a $ref but no $defs block (e.g.
GMAIL_FETCH_EMAILS) degrade to a permissive object schema rather than
throwing. The strict-structured-outputs path of @composio/openai-agents
is unchanged — OpenAI supports $defs/$ref natively, including recursion.
## @composio/llamaindex@0.11.0

### Minor Changes

- 9447932: Dereference internal $ref/$defs in tool input schemas before
provider translation, so properties reachable only through a reference
keep their types and validation instead of degrading to untyped (z.any)
or being emitted as a dangling reference.

This changes the JSON Schema these providers emit for $ref-using tools.
Downstream snapshot tests on tool definitions will see diffs. Schemas
the Composio API ships with a $ref but no $defs block (e.g.
GMAIL_FETCH_EMAILS) degrade to a permissive object schema rather than
throwing. The strict-structured-outputs path of @composio/openai-agents
is unchanged — OpenAI supports $defs/$ref natively, including recursion.
## @composio/openai-agents@0.11.0

### Minor Changes

- 9447932: Dereference internal $ref/$defs in tool input schemas before
provider translation, so properties reachable only through a reference
keep their types and validation instead of degrading to untyped (z.any)
or being emitted as a dangling reference.

This changes the JSON Schema these providers emit for $ref-using tools.
Downstream snapshot tests on tool definitions will see diffs. Schemas
the Composio API ships with a $ref but no $defs block (e.g.
GMAIL_FETCH_EMAILS) degrade to a permissive object schema rather than
throwing. The strict-structured-outputs path of @composio/openai-agents
is unchanged — OpenAI supports $defs/$ref natively, including recursion.
## @composio/vercel@0.12.0

### Minor Changes

- 9447932: Dereference internal $ref/$defs in tool input schemas before
provider translation, so properties reachable only through a reference
keep their types and validation instead of degrading to untyped (z.any)
or being emitted as a dangling reference.

This changes the JSON Schema these providers emit for $ref-using tools.
Downstream snapshot tests on tool definitions will see diffs. Schemas
the Composio API ships with a $ref but no $defs block (e.g.
GMAIL_FETCH_EMAILS) degrade to a permissive object schema rather than
throwing. The strict-structured-outputs path of @composio/openai-agents
is unchanged — OpenAI supports $defs/$ref natively, including recursion.
## @composio/core@0.18.1

### Patch Changes

- 8a56383: Fix: automatic S3 file downloads are now capped at 100 MiB
(configurable per call) to prevent memory exhaustion from oversized or
streaming responses.
- 7420927: Fix custom toolkit child slug mapping: reject response tools
that have local handles but no exact toolkit match instead of silently
dropping them or binding another toolkit's handler, derive bare-slug
ambiguity from local definitions, and only reuse a same-toolkit bare
alias in customToolkits().
- 1d31c80: Redact credential-shaped values at the SDK log boundary.
- 95f9d32: Expose the runtime-conditional SSRF-safe fetch helper for
protected URL upload consumers.
- 0d28bef: Map file-download transport failures to the SDK error
contract and bound streamed response bodies.
- 52efb5b: Fix trigger subscriptions ignoring the `authConfigId` filter.
- Updated dependencies [ab289d6]
  - @composio/json-schema-to-zod@0.3.2
## @composio/experimental@0.2.4

### Patch Changes

- 4e633d1: Update TypeBox to 1.3.18.
## @composio/json-schema-to-zod@0.3.2

### Patch Changes

- ab289d6: Preserve Draft 7 acceptance across primitive, composed,
referenced, conditional, and typeless schemas. Enforce sibling and
object/array assertions, retain positional tuple and `additionalItems`
behavior, and prevent native Zod materialization from rejecting values
already accepted by the source schema.
## @composio/openai@0.12.2

### Patch Changes

- 620075a: Fix: stop printing MCP server URLs (credential-bearing) to
stdout via console.log in the OpenAI Responses provider; log server
names via logger.debug instead.
## @composio/slim@0.18.1

### Patch Changes

- Updated dependencies [ab289d6]
  - @composio/json-schema-to-zod@0.3.2
## @e2e-tests/cf-workers-basic@0.0.2

### Patch Changes

- Updated dependencies [8a56383]
- Updated dependencies [7420927]
- Updated dependencies [1d31c80]
- Updated dependencies [95f9d32]
- Updated dependencies [0d28bef]
- Updated dependencies [52efb5b]
  - @composio/core@0.18.1
## @e2e-tests/cf-workers-files@0.0.2

### Patch Changes

- Updated dependencies [8a56383]
- Updated dependencies [7420927]
- Updated dependencies [1d31c80]
- Updated dependencies [95f9d32]
- Updated dependencies [0d28bef]
- Updated dependencies [52efb5b]
  - @composio/core@0.18.1
## @e2e-tests/cf-workers-tool-router-ai@0.0.2

### Patch Changes

- Updated dependencies [8a56383]
- Updated dependencies [7420927]
- Updated dependencies [9447932]
- Updated dependencies [1d31c80]
- Updated dependencies [95f9d32]
- Updated dependencies [0d28bef]
- Updated dependencies [52efb5b]
  - @composio/core@0.18.1
  - @composio/vercel@0.12.0
## @e2e-tests/node-claude-agent-sdk@0.0.2

### Patch Changes

- Updated dependencies [8a56383]
- Updated dependencies [7420927]
- Updated dependencies [9447932]
- Updated dependencies [1d31c80]
- Updated dependencies [95f9d32]
- Updated dependencies [0d28bef]
- Updated dependencies [52efb5b]
  - @composio/core@0.18.1
  - @composio/claude-agent-sdk@0.12.0
## @e2e-tests/node-custom-tools@0.0.2

### Patch Changes

- Updated dependencies [8a56383]
- Updated dependencies [7420927]
- Updated dependencies [1d31c80]
- Updated dependencies [95f9d32]
- Updated dependencies [0d28bef]
- Updated dependencies [52efb5b]
  - @composio/core@0.18.1
## @e2e-tests/node-json-schema-to-zod-v3@0.0.2

### Patch Changes

- Updated dependencies [ab289d6]
  - @composio/json-schema-to-zod@0.3.2
## @e2e-tests/node-json-schema-to-zod-v4@0.0.2

### Patch Changes

- Updated dependencies [ab289d6]
  - @composio/json-schema-to-zod@0.3.2
## @e2e-tests/node-mastra-tool-router-zod-v3@0.0.2

### Patch Changes

- Updated dependencies [8a56383]
- Updated dependencies [7420927]
- Updated dependencies [1d31c80]
- Updated dependencies [95f9d32]
- Updated dependencies [0d28bef]
- Updated dependencies [52efb5b]
  - @composio/core@0.18.1
  - @composio/mastra@0.10.4
## @e2e-tests/node-mastra-tool-router-zod-v4@0.0.2

### Patch Changes

- Updated dependencies [8a56383]
- Updated dependencies [7420927]
- Updated dependencies [1d31c80]
- Updated dependencies [95f9d32]
- Updated dependencies [0d28bef]
- Updated dependencies [52efb5b]
  - @composio/core@0.18.1
  - @composio/mastra@0.10.4
## @e2e-tests/node-tool-router-files@0.0.2

### Patch Changes

- Updated dependencies [8a56383]
- Updated dependencies [7420927]
- Updated dependencies [1d31c80]
- Updated dependencies [95f9d32]
- Updated dependencies [0d28bef]
- Updated dependencies [52efb5b]
  - @composio/core@0.18.1
## @e2e-tests/node-tool-router-pagination@0.0.2

### Patch Changes

- Updated dependencies [8a56383]
- Updated dependencies [7420927]
- Updated dependencies [1d31c80]
- Updated dependencies [95f9d32]
- Updated dependencies [0d28bef]
- Updated dependencies [52efb5b]
  - @composio/core@0.18.1
## anthropic-example@0.1.2

### Patch Changes

- Updated dependencies [8a56383]
- Updated dependencies [7420927]
- Updated dependencies [9447932]
- Updated dependencies [1d31c80]
- Updated dependencies [95f9d32]
- Updated dependencies [0d28bef]
- Updated dependencies [52efb5b]
  - @composio/core@0.18.1
  - @composio/claude-agent-sdk@0.12.0
  - @composio/anthropic@0.11.1
## connected-accounts-example@0.1.11

### Patch Changes

- Updated dependencies [8a56383]
- Updated dependencies [7420927]
- Updated dependencies [1d31c80]
- Updated dependencies [95f9d32]
- Updated dependencies [0d28bef]
- Updated dependencies [52efb5b]
  - @composio/core@0.18.1
## error-handling-example@0.1.11

### Patch Changes

- Updated dependencies [8a56383]
- Updated dependencies [7420927]
- Updated dependencies [1d31c80]
- Updated dependencies [95f9d32]
- Updated dependencies [0d28bef]
- Updated dependencies [52efb5b]
  - @composio/core@0.18.1
## file-handling-example@0.1.2

### Patch Changes

- Updated dependencies [8a56383]
- Updated dependencies [7420927]
- Updated dependencies [1d31c80]
- Updated dependencies [95f9d32]
- Updated dependencies [0d28bef]
- Updated dependencies [52efb5b]
  - @composio/core@0.18.1
## google-example@0.1.2

### Patch Changes

- Updated dependencies [8a56383]
- Updated dependencies [7420927]
- Updated dependencies [9447932]
- Updated dependencies [1d31c80]
- Updated dependencies [95f9d32]
- Updated dependencies [0d28bef]
- Updated dependencies [52efb5b]
  - @composio/core@0.18.1
  - @composio/google@0.11.0
## json-schema-to-zod-example@0.1.2

### Patch Changes

- Updated dependencies [8a56383]
- Updated dependencies [7420927]
- Updated dependencies [9447932]
- Updated dependencies [1d31c80]
- Updated dependencies [95f9d32]
- Updated dependencies [0d28bef]
- Updated dependencies [52efb5b]
  - @composio/core@0.18.1
  - @composio/vercel@0.12.0
## langchain-example@0.1.11

### Patch Changes

- Updated dependencies [8a56383]
- Updated dependencies [7420927]
- Updated dependencies [9447932]
- Updated dependencies [1d31c80]
- Updated dependencies [95f9d32]
- Updated dependencies [0d28bef]
- Updated dependencies [52efb5b]
  - @composio/core@0.18.1
  - @composio/langchain@0.11.0
## llamaindex-example@0.1.2

### Patch Changes

- Updated dependencies [8a56383]
- Updated dependencies [7420927]
- Updated dependencies [9447932]
- Updated dependencies [1d31c80]
- Updated dependencies [95f9d32]
- Updated dependencies [0d28bef]
- Updated dependencies [52efb5b]
  - @composio/core@0.18.1
  - @composio/llamaindex@0.11.0
## mastra-example@0.1.2

### Patch Changes

- Updated dependencies [8a56383]
- Updated dependencies [7420927]
- Updated dependencies [1d31c80]
- Updated dependencies [95f9d32]
- Updated dependencies [0d28bef]
- Updated dependencies [52efb5b]
  - @composio/core@0.18.1
  - @composio/mastra@0.10.4
## mcp-example@0.1.2

### Patch Changes

- Updated dependencies [8a56383]
- Updated dependencies [7420927]
- Updated dependencies [9447932]
- Updated dependencies [1d31c80]
- Updated dependencies [95f9d32]
- Updated dependencies [0d28bef]
- Updated dependencies [52efb5b]
  - @composio/core@0.18.1
  - @composio/vercel@0.12.0
## modifiers-example@0.1.11

### Patch Changes

- Updated dependencies [8a56383]
- Updated dependencies [7420927]
- Updated dependencies [9447932]
- Updated dependencies [1d31c80]
- Updated dependencies [95f9d32]
- Updated dependencies [0d28bef]
- Updated dependencies [52efb5b]
  - @composio/core@0.18.1
  - @composio/vercel@0.12.0
## openai-example@0.1.11

### Patch Changes

- Updated dependencies [8a56383]
- Updated dependencies [7420927]
- Updated dependencies [9447932]
- Updated dependencies [620075a]
- Updated dependencies [1d31c80]
- Updated dependencies [95f9d32]
- Updated dependencies [0d28bef]
- Updated dependencies [52efb5b]
  - @composio/core@0.18.1
  - @composio/openai-agents@0.11.0
  - @composio/openai@0.12.2
## session-management-example@0.1.2

### Patch Changes

- Updated dependencies [8a56383]
- Updated dependencies [7420927]
- Updated dependencies [1d31c80]
- Updated dependencies [95f9d32]
- Updated dependencies [0d28bef]
- Updated dependencies [52efb5b]
  - @composio/core@0.18.1
## tool-router-example@1.0.12

### Patch Changes

- Updated dependencies [8a56383]
- Updated dependencies [7420927]
- Updated dependencies [9447932]
- Updated dependencies [1d31c80]
- Updated dependencies [95f9d32]
- Updated dependencies [0d28bef]
- Updated dependencies [52efb5b]
  - @composio/core@0.18.1
  - @composio/claude-agent-sdk@0.12.0
  - @composio/vercel@0.12.0
  - @composio/openai-agents@0.11.0
## toolkits-example@0.1.11

### Patch Changes

- Updated dependencies [8a56383]
- Updated dependencies [7420927]
- Updated dependencies [9447932]
- Updated dependencies [1d31c80]
- Updated dependencies [95f9d32]
- Updated dependencies [0d28bef]
- Updated dependencies [52efb5b]
  - @composio/core@0.18.1
  - @composio/vercel@0.12.0
## tools-example@0.1.2

### Patch Changes

- Updated dependencies [8a56383]
- Updated dependencies [7420927]
- Updated dependencies [9447932]
- Updated dependencies [1d31c80]
- Updated dependencies [95f9d32]
- Updated dependencies [0d28bef]
- Updated dependencies [52efb5b]
  - @composio/core@0.18.1
  - @composio/vercel@0.12.0
## triggers-example@0.1.2

### Patch Changes

- Updated dependencies [8a56383]
- Updated dependencies [7420927]
- Updated dependencies [1d31c80]
- Updated dependencies [95f9d32]
- Updated dependencies [0d28bef]
- Updated dependencies [52efb5b]
  - @composio/core@0.18.1
## vercel-example@0.1.11

### Patch Changes

- Updated dependencies [8a56383]
- Updated dependencies [7420927]
- Updated dependencies [9447932]
- Updated dependencies [1d31c80]
- Updated dependencies [95f9d32]
- Updated dependencies [0d28bef]
- Updated dependencies [52efb5b]
  - @composio/core@0.18.1
  - @composio/vercel@0.12.0
## versioning-example@0.1.2

### Patch Changes

- Updated dependencies [8a56383]
- Updated dependencies [7420927]
- Updated dependencies [1d31c80]
- Updated dependencies [95f9d32]
- Updated dependencies [0d28bef]
- Updated dependencies [52efb5b]
  - @composio/core@0.18.1
## @composio/json-schema-to-effect-schema@0.1.1

### Patch Changes

- ab289d6: Translate draft-4 boolean
`exclusiveMinimum`/`exclusiveMaximum` flags (as emitted by OpenAPI 3.0
exporters) into their Draft 7 numeric spelling so exclusive bounds are
enforced instead of silently ignored.

Co-authored-by: sdkrelease[bot] <294075132+sdkrelease[bot]@users.noreply.github.com>
2026-09-04 21:01:00 +02:00
Alberto Schiabel ab289d6224 fix(sdk): preserve primitive JSON Schema semantics (#4316)
## Summary

- preserve boolean, empty, null, type-array, enum, const, and
scalar-constraint semantics across every Python conversion entry point
- intersect Zod enum and const values with declared types and
constraints, including compound JSON values
- default unversioned exact validation to Draft 7 and apply inclusive
and numeric exclusive bounds independently
- run one byte-identical corpus through Python, Zod, and Effect so
accepted and rejected inputs stay aligned
- keep exact JSON Schema acceptance separate from Pydantic default
materialization

## Review follow-up (second push)

- Python: exact Draft 7 acceptance now wraps all three entry points
(`json_schema_to_pydantic_type`, `json_schema_to_model`,
`pydantic_model_from_param_schema`), so they can no longer disagree
- Python: draft-4 boolean `exclusiveMinimum`/`exclusiveMaximum` (OpenAPI
3.0 style) no longer crash conversion — exact validation falls back to
Draft 4, and the library input is translated to the numeric spelling
- Python: ECMA-only regex patterns (look-around) no longer crash
pydantic model builds — Rust-incompatible patterns fall back to Python
`re`
- Python: type arrays with sibling constraints no longer raise
`TypeError` on valid input — constraints are scoped per member before
the library sees them
- Python: integral floats satisfy `integer`, `const` intersects `enum`,
annotation-only schemas accept anything, and an optional property with
an empty `enum` tolerates absence
- Zod: typeless scalar constraints apply per instance type, and string
lengths count Unicode code points instead of UTF-16 code units
- Effect: draft-4 boolean exclusive bounds are enforced instead of
silently ignored
- `multipleOf` uses decimal scaling in all three converters (declared
`divergesFromJsonSchema` on the corpus case)
- shared corpus grows by 13 primitive cases; new property-based tests
check acceptance against real Draft 7 oracles (hypothesis + `jsonschema`
in Python, fast-check + Ajv in TypeScript)

## Verification

- Python `make chk` (ruff + mypy)
- Python pytest: 1,572 passed (5 langchain-extra tests need an env this
sandbox lacks; unchanged from base)
- `@composio/json-schema-to-zod`: 187 passed incl. 300-run fast-check
property test; typecheck + build
- `@composio/json-schema-to-effect-schema`: 133 passed; typecheck
- `@composio/core` corpus ingress tests: 61 passed
- shared Python/TypeScript corpus files are byte-identical
(shasum-verified)
- `git diff --check`

## Contributor context

This replaces four narrow proposals after independent local
reproduction:

- [#4301](https://github.com/ComposioHQ/composio/pull/4301) ·
[Glen](https://app.tryglen.com/ComposioHQ/composio/pull/4301)
- [#4302](https://github.com/ComposioHQ/composio/pull/4302) ·
[Glen](https://app.tryglen.com/ComposioHQ/composio/pull/4302)
- [#4303](https://github.com/ComposioHQ/composio/pull/4303) ·
[Glen](https://app.tryglen.com/ComposioHQ/composio/pull/4303)
- [#4307](https://github.com/ComposioHQ/composio/pull/4307) ·
[Glen](https://app.tryglen.com/ComposioHQ/composio/pull/4307)

---------

Co-authored-by: simpleqt <89645338+simpleqt@users.noreply.github.com>
2026-09-04 14:19:02 +02:00
CoralGarden52 7420927183 fix(sdk): qualify custom toolkit child slug mapping across Python and TypeScript (#4311)
## Summary
The Python SDK treated a custom tool's `original_slug` as globally
unique, rejecting valid custom toolkits that reuse common child names
such as `SEARCH`, `VERSION`, or `GREP` even though the backend-assigned
final slugs are toolkit-qualified (`LOCAL_ALPHA_GREP`,
`LOCAL_BETA_GREP`).

This ports the toolkit-qualified lookup from #3360 to Python, then fixes
three response-mapping bugs found in review and applies the same fixes
to the TypeScript SDK so both stay in parity.

## Changes

### Python (`composio`)
- Scope custom-tool collision detection and response matching by toolkit
plus original slug.
- Keep bare original-slug aliases only when unambiguous;
`session.execute("GREP")` raises with the final slugs to use when the
slug is shared.
- Preserve toolkit-qualified final slugs in `custom_toolkits()`.
- `build_custom_tools_map_from_response`: raise when a response tool has
local handles but no exact toolkit match instead of silently dropping it
or binding another toolkit's handler; only fall back to a bare match
when the response carries no toolkit identity; reject duplicate
qualified response entries; derive bare-slug ambiguity from local
definitions so omitting a sibling in the response never makes the
survivor callable by bare name.
- `custom_toolkits()` only reuses a bare alias that belongs to the same
toolkit.
- Docstring and Python session reference page state that bare-slug
execution requires a unique original slug.

### TypeScript (`@composio/core`)
- Same four fixes in `buildCustomToolsMapFromResponse` and the same
guard in `customToolkits()`.
- JSDoc and TypeScript session reference page updated.
- Changeset: patch for `@composio/core`.

### Not changed
- `COMPOSIO_MULTI_EXECUTE_TOOL` still aborts the whole batch when one
item uses an ambiguous bare slug, matching current TS behavior.
Switching to per-item errors is a cross-SDK design change left for a
follow-up.

## Type of change
- [x] Bug fix
- [ ] New feature
- [ ] Refactor/Chore
- [ ] Documentation
- [ ] Breaking change

## How Has This Been Tested?
Python:
- `pytest tests/test_custom_tools.py tests/test_tool_router.py`: 181
passed.
- ruff (project config) clean; mypy reports no errors in the touched
files.
- New tests: sibling routing, multi-execute, preload rejection, listing
guard, and five response-mapping cases (no exact match, cross-toolkit
binding, standalone bare fallback, unknown response tools skipped,
ambiguity from local definitions, duplicate qualified entries).

TypeScript:
- `vitest run` in `ts/packages/core`: 53 files, 1251 passed, 2 expected
failures.
- `tsc --noEmit` clean; prettier and oxlint via pre-commit hook.
- New tests: cross-toolkit reuse in `buildCustomToolsMap` and a new
`buildCustomToolsMapFromResponse` block mirroring the Python cases.

Python and TypeScript CI do not run automatically on this fork PR; a
maintainer needs to approve the workflow run.

## Checklist
- [x] I have read the Code of Conduct and this PR adheres to it
- [x] I ran linters/tests locally and they passed
- [x] I updated documentation as needed
- [x] I added tests or explain why not applicable
- [x] I added a changeset if this change affects published packages

## Additional context
Reviewed with a second opinion from Codex (gpt-5.6-sol), which flagged
the wrong-handler binding and response-derived ambiguity bugs fixed in
the follow-up commits.

https://claude.ai/code/session_01Y7Ni3QEBDGShSrEtwQS5bA
EOF -R ComposioHQ/composio

---------

Signed-off-by: CoralGarden52 <2193436736@qq.com>
Co-authored-by: jkomyno <alberto@composio.dev>
Co-authored-by: Alberto Schiabel <jkomyno@users.noreply.github.com>
2026-09-03 14:08:48 +02:00
CoralGarden52 52efb5b833 fix(core): respect authConfigId in trigger subscriptions (#4298)
## Summary

- Apply the existing authConfigId subscription filter to incoming
trigger events.
- Add a V3 regression test for mismatched auth configurations.
- Add a patch changeset for @composio/core.

Previously, a subscription filtered by authConfigId still invoked its
callback for events belonging to a different auth configuration.

## Verification

- Vitest targeted tests: 76 passed
- Vitest core suite: 1244 passed, 2 expected failures
- TypeScript typecheck and Prettier passed

Fixes the missing authConfigId filtering in trigger subscriptions.

---------

Co-authored-by: jkomyno <alberto@composio.dev>
2026-09-03 12:15:46 +02:00
Alberto Schiabel 0d28befb14 fix(sdk): map streamed file transport failures (#4321)
## Summary

- map Python file-fetch failures that occur after response headers into
the documented upload and download errors
- map TypeScript RemoteFile connection and streamed-body failures into
RemoteFileDownloadError while preserving blocked-URL errors
- close or cancel response bodies on every exit and apply the shared 100
MiB response limit to TypeScript RemoteFile downloads

This supersedes the Python-only proposal in #4305 and carries the same
failure category across both SDKs.

## Independent reproduction

A response double returned one chunk and then raised a connection-reset
error. On current next:

- Python _fetch_file_from_url leaked ConnectionError, although it did
close the response
- Python Tool Router URL fetch leaked ConnectionError and left the
response open
- TypeScript RemoteFile leaked the native fetch/body TypeError instead
of RemoteFileDownloadError

## Verification

- Python make chk
- Python make tst: 1,490 passed
- TypeScript core typecheck
- TypeScript core tests: 1,245 passed, 2 expected failures
- TypeScript package build: 19 packages
- focused Python regression tests: 3 passed
- focused TypeScript RemoteFile tests: 17 passed
2026-09-03 12:06:37 +02:00
Alberto Schiabel 95f9d3295f fix(cli): guard URL file uploads against SSRF (#4319)
## Summary

- route attacker-controlled URL sources and API-provided presigned
upload destinations through the runtime-conditional core SSRF guard
- expose that guard through a Node/workerd-aware core subpath
- validate and revalidate DNS on redirects, pin Node and Bun connections
to validated addresses, and preserve configured proxy routes
- fail closed for user-chosen URL uploads in edge runtimes
- cancel ignored response bodies and cover both upload boundaries at the
public CLI pipeline
- avoid adding `Content-Length: 0` to bodyless Bun GET requests

## Local reproduction

On `next`, the CLI pipeline used bare `fetch` for both targets. A local
loopback source and an internal presigned destination reached the
network path. With this branch, the real `uploadToolInputFiles` pipeline
blocks a `127.0.0.1` source before presigning and a `169.254.169.254`
destination before sending bytes.

A direct Bun proof also confirmed the pinned transport reaches a
validated address without calling native `fetch`, while retaining the
original Host header. Focused tests preserve native Bun fetch when an
environment proxy is configured.

## Cross-SDK parity

Python already applies public-address validation, redirect checks, DNS
pinning, and response limits to URL uploads. Its focused URL-safety and
upload suite remains green: 62 passed. No Python behavior change was
needed.

## Verification

- `pnpm build:packages`: 19 packages built
- root `pnpm typecheck`: 14 package checks passed
- TypeScript core: 53 files, 1,246 passed and 2 expected failures
- focused core SSRF and pinned-transport tests: 31 passed
- Python URL-safety/upload tests: 62 passed
- real Bun execution of both CLI upload boundaries: blocked before
presign/send
- `git diff --check`

The CLI Effect test file contains source and presigned-destination
regressions and typechecks. Its local runner is blocked on current
`next` by the repository-wide `@effect/vitest` config failure; hosted
CLI checks exercise that boundary.

## Contributor context

Supersedes [#4299](https://github.com/ComposioHQ/composio/pull/4299) ·
[Glen](https://app.tryglen.com/ComposioHQ/composio/pull/4299) after
independently reproducing the attack path. The report is valid and
useful, but the proposed root export hard-coded a Node module into an
edge-capable package, its happy-path test did not execute the returned
Effect, and it omitted destination protection, response cleanup, and Bun
address pinning.
2026-09-03 11:51:30 +02:00
Alberto Schiabel be8e978c3a fix(toolchain): pin Bun canary for valid macOS signatures (#4315)
This PR:
- closes #4284
- makes `mise.toml` the editable source of truth for Bun and pins
`1.4.1-canary.1+d9b769812`, the first Bun build whose compiled macOS
binaries carry strictly valid signatures
- maps that revision to the immutable per-platform `@oven/bun-*` npm
tarballs via mise's `http` backend, so mise extracts the exact
checksum-verified binary with no npm lifecycle, Node dependency, or
postinstall script
- installs Bun through mise in CI and Docker E2E images, removing the
independent `bun-version` input and the `oven-sh/setup-bun` channel
- updates the checksum-verified mise installer to `2026.8.15`, reuses it
in the Docker E2E images, and regenerates `mise.lock` with that release
- teaches the preinstall toolchain check to compare the full Bun
revision (via `Bun.version_with_sha`, in-process) when the pinned
version carries build metadata
- verifies the exact `bun --revision`, a strictly valid Bun-compiled
macOS signature, a Linux container install, the release-workflow
contract, and formatting/linting
EOF -R ComposioHQ/composio
2026-09-03 11:51:22 +02:00
Alberto Schiabel 1d31c80eff fix(sdk): keep credentials private in storage and logs (#4318)
## Summary

- write CLI user data, pending login sessions, and agent identities
through one atomic `0600` helper
- repair `0644` credential files created by older CLI versions before
reading them
- redact credential-shaped structured values from CLI user-context
diagnostics
- redact secret-shaped text at both TypeScript and Python SDK log-output
boundaries, including Pusher `auth` responses and exception tracebacks
- preserve Python logger compatibility: errors remain untruncated,
disabled levels remain lazy, and malformed placeholders cannot expose
arguments

## Local reproduction

Under the normal `022` umask, `next` created a plaintext credential file
with mode `0644`. The pre-fix CLI user-context and TypeScript SDK debug
paths also emitted sentinel credentials. The private atomic writer
changes an existing `0644` target to `0600`, and the upgrade tests now
prove all three legacy credential files are tightened without changing
their contents.

## Verification

- CLI permission upgrade tests: 31 passed across user data, pending
login, and agent identity paths
- CLI source and test typechecks passed
- TypeScript core logging, redaction, and Pusher tests: 17 passed
- TypeScript core source and type-test typechecks passed
- Python logging regression tests: 5 passed
- focused Ruff, Prettier, Oxlint, and `git diff --check` passed

The focused CLI runner needed a temporary local alias for the
pre-existing missing `#ssrf_guard` mapping in the CLI Vitest config. The
alias was removed after verification and is not part of this PR.

## Contributor context

Credit to **Syed Anas Mohiuddin**, independent security researcher, for
reporting the legacy CLI credential-file permission issue.

Supersedes [#4300](https://github.com/ComposioHQ/composio/pull/4300) ·
[Glen review](https://app.tryglen.com/ComposioHQ/composio/pull/4300).
The implementation also covers agent credentials, retains atomic writes,
and applies redaction at the shared SDK logging boundary.
2026-09-03 01:45:11 +02:00
Saransh Rana 961b0a0418 security: fix Parameter finding #91 (CWE-94) - identifier guard in ts-builders codegen (#4324)
## What the vulnerability was

The CLI's TypeScript generator wrote API-supplied tool and trigger slugs
straight into generated `.ts` files at two places where the slug becomes
**code**, not data:

- **object-literal property keys** (`PropertyValue.write`), and
- **type-declaration names** (`TypeDeclaration.write`).

Slugs are unconstrained strings (`ToolAsEnum = Schema.String`, no
character allowlist) and the threat model treats API responses as
untrusted. So a crafted slug could close the key and inject arbitrary
top-level TypeScript, which then executes when the generated SDK is
imported or built. That is remote code execution on the developer or CI
host running `composio ts generate`.

The sibling `Property` builder already got this right: it tests
`isValidJsIdentifier` and falls back to a JSON-encoded computed key.
`PropertyValue` and `TypeDeclaration` simply lacked the same guard.

## Why this change addresses it

- `PropertyValue` now applies the exact guard `Property` uses. A name
that is not a valid identifier becomes a quoted computed key
(`["..."]`), so everything it contains is parsed as a string, never as
an expression.
- `TypeDeclaration` refuses a non-identifier name with a `TypeError`. A
type name has no quoted or computed form, so quoting is not available
and failing loudly is the only safe option. The guard sits after the
existing early return for a string type body, which never writes the
name.

Output is byte-identical for every name that is already a valid
identifier, so no existing generation changes. The CLI codegen snapshots
contain only identifier-shaped slugs
(`GITHUB_ACCEPT_A_REPOSITORY_INVITATION_INPUT`) and no computed keys,
and they are unchanged.

Worth noting on the throw: the two sinks differ in exposure.
`typeDeclaration` receives the full `tool.slug` (for example
`GITHUB_FOO`), which is identifier-shaped in practice. `propertyValue`
receives `stripPrefix(tool.slug)`, which can plausibly start with a
digit for real data and now gets safely quoted rather than throwing. Any
name that would now throw was already producing syntactically invalid
TypeScript, so this converts a confusing downstream compile error into a
clear codegen error.

## Tests

**Exploit tests**, not behaviour-pinning. Nine new tests across the two
files.

The key one builds the generated object literal from a malicious slug,
evaluates it, and asserts the injected IIFE did not run:

```ts
const evaluated = new Function(`return { ${out} };`)() as Record<string, unknown>;
expect(Object.keys(evaluated)).toEqual([malicious]);
expect((globalThis as Record<string, unknown>).__PWNED__).toBeUndefined();
```

Each test was confirmed to fail against the unpatched builders and pass
after the change. On the vulnerable code the generator emits `["k"]: (()
=> { globalThis.__PWNED__ = 1; })(), ["SEND"]: "SLACK_SEND"`, which is
the payload as live code.

Existing behaviour is also pinned: valid identifier keys, well-known
symbols, optional properties, generic parameters, doc comments, and the
string-type-body short circuit.

## What was not verified

- **No end-to-end run of `composio ts generate` against a real or
malicious API response.** The fix and its tests are at the builder
layer. The call sites in
`ts/packages/cli/src/generation/typescript/generate-toolkit-sources.ts`
were read to confirm they pass attacker-controlled slugs into these
builders, but were not exercised.
- **No model-layer slug validation was added.** The finding also
suggests validating slugs against `^[A-Za-z0-9_]+$` at the model layer.
That is deliberately out of scope here: it would change what the CLI
accepts from the API and belongs in a separate, human-reviewed change.
This PR closes the two injection sinks only.
- **The `TypeDeclaration` throw is a new failure mode.** If any live
toolkit ships a slug that is not a valid identifier, codegen will now
fail loudly for it instead of emitting broken TypeScript. No such slug
appears in the repo's fixtures, but the full set of production slugs was
not enumerated.
- Python codegen was not reviewed. This finding and fix are
TypeScript-only.

## Testing performed

Clean-HEAD baseline captured before any edit: full monorepo `pnpm run
test` green, 26/26 turbo tasks, exit 0.

After the change, the same full suite is green, 26/26 tasks, exit 0.
`@composio/ts-builders` goes from 131 to 140 tests, all passing.
`@composio/cli` unchanged at 1304 passed. 20 example packages validated.
No new failures and no snapshot churn.

## Finding

Parameter finding #91 (CWE-94), validated live at
`abc8e038218305cab7f3373b82a37144fa15e630`.
Linear: https://linear.app/composio/issue/SEC-579

parameter-finding: kcy19unq784bp2z34b3299w0

Co-authored-by: Saransh <saranshrana@Saranshs-MacBook-Pro.local>
Co-authored-by: Claude Opus 5 (1M context) <noreply@anthropic.com>
2026-09-01 10:50:42 +02:00
Alberto Schiabel 28378595a1 fix(providers/anthropic): re-export AnthropicTool, InputSchema, and CacheControlEphemeral types (#4286) (#4295)
## Summary
- Re-exports `AnthropicTool`, `InputSchema`, and `CacheControlEphemeral`
types from `@composio/anthropic` entry point
(`ts/packages/providers/anthropic/src/index.ts`).
- Allows TypeScript users to import schema types directly without
reaching into internal paths.

## Test Plan
- Verified index exports in `@composio/anthropic`.
2026-08-31 13:07:19 +02:00
Alberto Schiabel 7da1397017 Merge branch 'next' into fix/cli-spinner-narrow-terminal-scroll 2026-08-31 13:02:18 +02:00
jkomyno 41019972e1 fix(cli): harden spinner message clamping
Keep live spinner updates within both Clack's construction-time width and the current terminal width, so resizing wider cannot reintroduce wrapped frames while narrower terminals remain clamped.

Segment messages by grapheme cluster before measuring display width so keycap and joined emoji cannot be under-counted or split.
2026-08-31 13:00:11 +02:00
jkomyno 26eedbf5c8 chore(cli): refresh baked toolkit slugs 2026-08-31 06:35:42 +00:00
jkomyno 6b135d1606 refactor(cli): start clamped spinners in one place
Both spinner entry points constructed a clack spinner on stderr and
started it with a clamped message, and useMakeSpinner built a throwaway
lambda purely to relay that same clamp into createClackSpinnerHandle.

Give makeTerminalUI a startSpinner helper that both entry points call,
and let createClackSpinnerHandle take the output stream it clamps
against instead of a pre-bound closure. Behaviour is unchanged.

Claude-Session: https://claude.ai/code/session_0191yFPnWgJnzPPnCYrVm6X7
2026-08-29 12:30:09 +02:00
teddiesloco f438422df0 fix(providers/anthropic): re-export AnthropicTool, InputSchema, and CacheControlEphemeral types (#4286) 2026-08-29 12:34:04 +07:00
jkomyno 4e45d7fabe fix(cli): clamp spinner messages by display width
Follow-ups from review of the narrow-terminal spinner fix.

- Budget and truncate by display columns instead of UTF-16 code units.
  Clack wraps the rendered frame by width, so a CJK message sat under a
  `.length` budget and wrapped anyway, reinstating the leak. Walking whole
  code points also keeps the cut off a surrogate pair.
- Drop MIN_SPINNER_MESSAGE_COLUMNS. The 8-column floor exceeded the row
  below ~15 columns and restored the scroll it was meant to prevent. The
  budget now degrades to the ellipsis, so the one-row invariant holds
  wherever it can hold at all.
- Cover the paths production actually drives: live `message()` updates and
  `withSpinner`'s start message. Reverting either clamp previously left the
  whole suite green.
- Advance fake timers past clack's dot animation so the three dot columns
  SPINNER_RENDER_OVERHEAD reserves are exercised, and run these cases
  through `it.live` per the package's Effect test convention.
- Add the CHANGELOG entry this user-facing fix needs; `@composio/cli` is
  changeset-ignored, so release notes go there directly.

Claude-Session: https://claude.ai/code/session_0191yFPnWgJnzPPnCYrVm6X7
2026-08-28 18:39:48 +02:00
jkomyno 071bca0feb test(experimental): type Eve approval contexts 2026-08-28 15:35:52 +02:00
jkomyno fb77efc4ba chore(experimental): update agent dependencies 2026-08-28 14:54:38 +02:00
jkomyno 9758571072 chore(deps-dev): update TypeScript tooling 2026-08-28 14:52:53 +02:00
jkomyno 02bee3b2d9 chore(deps): refresh production dependencies 2026-08-28 14:51:36 +02:00
Alberto Schiabel 1157faf0a1 fix(providers): dereference $ref/$defs before schema translation (#4288)
This PR:
- resolves internal `$ref`/`$defs` in tool input schemas before
translation in `langchain`, `llamaindex`, `claude-agent-sdk`, `vercel`,
`google`, and `openai-agents` (`onUnresolved: 'sentinel'`)
- previously `$ref`-typed properties degraded to `z.any()` — the Zod
converter has no `$ref` branch — or were emitted as dangling references
after the root rebuild (google, openai-agents fallback)
- keeps `openai-agents`' strict-structured-outputs path untouched:
OpenAI resolves `$defs`/`$ref` natively including recursion, pinned by a
guard test
- adds per-provider `$ref` regression suites for all six providers,
including dangling-`$defs` (`GMAIL_FETCH_EMAILS`) and recursive-schema
cases
- adds a cross-provider contract test that fails when a new provider
ships without a `$ref` classification, plus property tests for
`dereferenceJsonSchema` (Python counterparts land with the Python-side
fix)
- changes the vendor-visible schema shape for `$ref`-using tools;
changeset is `minor`

## Context

The same bug was fixed locally twice before (mastra, anthropic) without
surfacing the other six providers — nothing enumerated providers and
asked the `$ref` question. The new contract test does exactly that, so
provider #11 cannot ship unclassified. Python mirrors exist already; the
Python-side provider fix follows separately.
2026-08-28 14:42:35 +02:00
jkomyno 2777545a4c test(core): make $ref contract holdout exclusive, flag polluting-key refs unresolvable 2026-08-28 14:20:23 +02:00
jkomyno 98f16febcd test(core,providers): restore $ref contract and property suites
Regenerate the cross-provider $ref contract test, the
dereferenceJsonSchema property tests, and the openai-agents
$ref contract lost in a session handoff, ported from their
surviving Python counterparts. The openai-agents non-strict
ratchet flips to a plain it now that the fallback dereferences;
the superseded openai-agents-ref.test.ts is removed in favor of
the richer contract file.
2026-08-28 13:34:14 +02:00
jkomyno 9447932d98 fix(providers): dereference $ref/$defs schemas before translation
jsonSchemaToZodSchema has no $ref branch, so a $ref node degrades to
z.any() for langchain, llamaindex, claude-agent-sdk, and vercel's
default path. google and openai-agents' non-strict fallback rebuild
the root from properties/required, discarding $defs while dangling
$ref pointers survive.

Dereference internal $ref/$defs before translation in all six, using
onUnresolved: 'sentinel' so a $ref into an undeclared $defs block
(e.g. GMAIL_FETCH_EMAILS) degrades to a permissive schema instead of
throwing. The mastra and anthropic providers already had this fix;
openai-agents' strict branch is untouched since OpenAI's structured
outputs support $defs/$ref natively, including recursion, and
google's rebuild still drops additionalProperties/title/root
oneOf-anyOf-allOf beyond the dangling-$ref class this fixes.
2026-08-28 11:40:49 +02:00
jkomyno 620075a5de fix(openai): stop logging MCP server URLs to stdout 2026-08-28 11:38:12 +02:00
jkomyno 9f77e643a5 test(core): use the node: prefix for the fs import
Every other test in the package imports node builtins with the `node:`
prefix — this was the only bare `'fs'` specifier, and inconsistent with
`node:path` on the line above it.

Claude-Session: https://claude.ai/code/session_01K1hH9PMmd6KPKdkACX553z
2026-08-28 10:00:25 +02:00
jkomyno 8a56383b24 fix(core): cap automatic S3 download size at 100 MiB
`downloadFileFromS3` buffered the whole response with `arrayBuffer()`. The
`s3Url` it fetches is a tool-execution response field — the same untrusted
input the SSRF guard already defends against — so an oversized or endlessly
streaming body could exhaust the host process's heap.

Route the body through the existing `readResponseBodyWithLimit` guard, which
pre-checks `Content-Length` and counts streamed bytes (the header can be
absent or dishonest). The 100 MiB default matches the upload-from-URL sibling
in the same module; `maxDownloadBytes` overrides it per call.

Claude-Session: https://claude.ai/code/session_01K1hH9PMmd6KPKdkACX553z
2026-08-28 09:50:57 +02:00
sdkrelease[bot] dbe5a63965 Release: update version 2026-08-27 18:07:50 +00:00
Alberto Schiabel 08306f8bc1 Merge branch 'next' into fix/error-subclass-names 2026-08-27 18:51:36 +02:00
Alberto Schiabel 3c7b938bd1 Merge branch 'next' into fix/telemetry-request-timeout 2026-08-27 18:27:32 +02:00
jkomyno cf42328040 fix(telemetry): clear timeout on serialization errors 2026-08-27 18:23:38 +02:00
jkomyno f37c6fbec3 docs(strict-mode): correct provider support details 2026-08-27 15:51:18 +02:00
jkomyno a93e8df547 docs(providers): clarify strict schema behavior 2026-08-27 15:41:46 +02:00
jkomyno 9feca8f95d fix(json-schema): accept document-root references in strict mode 2026-08-27 15:39:38 +02:00
Alberto Schiabel 81631f83f4 Merge branch 'next' into fix/strict-mode-keep-optional-parameters 2026-08-27 15:14:24 +02:00
sjd9021 7ad88415c7 fix(cli): stop spinner from scrolling endlessly in narrow terminals
Clack's spinner erases the previous frame by re-wrapping the raw message,
but each frame actually renders three extra prefix columns plus up to three
animated dots. Once those extras push the rendered frame across a wrap
boundary — e.g. the ~90-column upgrade message in a narrower terminal — the
erase under-counts lines and every 80ms tick leaks one, scrolling
'New version available: …' forever.

Clamp live spinner messages (start and message updates) to a single
terminal row so the redraw arithmetic cannot diverge. Stop/error messages
are single writes and stay untouched.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
2026-08-27 01:30:26 +05:30
jkomyno c0880764cf fix(docs): escape pipes in generated text 2026-08-26 19:55:59 +02:00
jkomyno 8fe03eff47 test(json-schema): add strict-mode edge cases enumerated with a second model
Extends strict-cases.json to 68 cases with shapes enumerated independently
(single-element and three-member type arrays, null-only and null-carrying
enum/const properties, nested compositions, nullable objects in arrays,
tuple and boolean items, conditional and dependency keywords, oneOf beside
anyOf, boolean and malformed properties, $ref siblings and chains, legacy
definitions next to $defs, non-string required entries, ten-level
nesting) plus null-omission pairs for nullable, composed and $ref-typed
arguments. Checks in the generator that derives the pinned JSON.

Co-authored-by: AseemPrasad <aseemprasad0520@gmail.com>

Claude-Session: https://claude.ai/code/session_01TDrxCHn2hg51HmxVstSUgs
2026-08-26 17:59:21 +02:00
jkomyno b47d5137c2 fix(core): report every construct strict mode cannot rewrite
Tuple-form items, boolean subschemas, malformed properties, oneOf left
beside anyOf, and the conditional and dependency keywords (not, if, then,
else, dependencies, dependentSchemas, propertyNames, contains,
additionalItems, unevaluatedItems, unevaluatedProperties) are now reported
as unsupported so the tool is sent without strict mode instead of with a
schema the API rejects. A root typed ["object"] is accepted, and an enum
or const that already includes null is not wrapped again.

omitNullToolArguments now follows the anyOf/oneOf branch that matches an
argument's shape, so nulls inside an object sent for a composed property
are reconciled against that branch.

Co-authored-by: AseemPrasad <aseemprasad0520@gmail.com>

Claude-Session: https://claude.ai/code/session_01TDrxCHn2hg51HmxVstSUgs
2026-08-26 17:59:18 +02:00
jkomyno 678ac7260a fix(docs): complete generated string escaping 2026-08-26 17:41:41 +02:00
jkomyno 3ca07210d3 test(json-schema): drive strict-mode cases from a shared corpus
strict-cases.json (one byte-identical copy per language, next to
object-cases.json) pins the exact strict schema or the reported
incompatibilities for 44 shapes: optional widening at every depth,
nullable type arrays, compositions, enum/const wrapping, annotation
stripping, keyword-named and prototype-named properties, dynamic-key and
free-form objects, allOf/prefixItems, $defs recursion, dangling and
external refs, malformed required, non-object roots, plus null-omission
argument pairs. The TypeScript suite pins the implementation and the
Python suite checks parity against the same file.

Co-authored-by: AseemPrasad <aseemprasad0520@gmail.com>

Claude-Session: https://claude.ai/code/session_01TDrxCHn2hg51HmxVstSUgs
2026-08-26 17:37:53 +02:00
jkomyno 991c57af80 fix(core): keep properties named like prototype keys under strict mode
toStrictJsonSchema assigned rewritten property schemas by name, so a
property called __proto__ set the prototype of the properties map instead
of being stored and disappeared from the strict schema. Own properties are
now defined explicitly, matching the other schema walkers in this module.

Co-authored-by: AseemPrasad <aseemprasad0520@gmail.com>

Claude-Session: https://claude.ai/code/session_01TDrxCHn2hg51HmxVstSUgs
2026-08-26 17:37:25 +02:00
jkomyno 9692db5c0a fix(openai-agents): honor the strict option
OpenAIAgentsProvider accepted { strict } but always registered tools with
strict: false and additionalProperties: true. Strict mode now registers
tools with strict: true and a schema normalized by toStrictJsonSchema
(optional parameters required-nullable), drops null arguments the tool
schema rejects before execution, and registers tools strict mode cannot
express without strict mode with a warning.

Co-authored-by: AseemPrasad <aseemprasad0520@gmail.com>

Claude-Session: https://claude.ai/code/session_01TDrxCHn2hg51HmxVstSUgs
2026-08-26 17:34:08 +02:00