Skip to content

Releases

v0.14.5: super on budget checks

Choose a tag to compare

@eadwinCode eadwinCode released this 03 Nov 21:02
f7e8a6d

A replaced budget check can now call the default as super, and a run always stops at its cap even when its budget event fails to send. Go module github.com/eadwinCode/agentic-kit/packages/go-agentenkit@v0.14.5, npm agentenkit@0.14.5 and use-agentenkit@0.14.5.

No breaking changes for checks the loop builds. A check object you build by hand to pass to your own hook must now set super (Go: Super).

New: super on budget checks (#46)

TS: c.super(c). Go: c.Super(ctx, c).

  • It is the default check: the token cap or the money cap. Call it to keep the cap and add your own rule on top.
  • When it returns true it has already sent TOKEN_BUDGET_EXHAUSTED or COST_BUDGET_EXHAUSTED. Don't send it again.
  • The TS defaults (defaultCheckTokenBudgetExhausted, defaultCheckCostBudgetExhausted) still take a check without super, so calling them directly still compiles.

Fixed (#47)

  • A budget event that fails to send no longer lets a run go past its cap. In TS, a failed send inside the default check threw, and the loop read that as "don't stop". Go ignored the error and stopped. The publish a check gets now logs a failure and never throws (Go: returns nil), so both runtimes stop.

Docs

  • The package READMEs and Multi-tenancy point to the budget check hooks. Multi-tenancy says to refuse an empty balance in billingPreCheck, since the first step of a segment runs before any check.

See Your own budget checks.

v0.14.0: budget checks you can replace

Choose a tag to compare

@eadwinCode eadwinCode released this 03 Nov 20:25
d576679

The two budget checks the loop runs after every step can now be replaced, in both runtimes. A host can stop a run on its own rule, such as a live balance that other runs spend at the same time. Go module github.com/eadwinCode/agentic-kit/packages/go-agentenkit@v0.14.0, npm agentenkit@0.14.0 and use-agentenkit@0.14.0.

No breaking changes.

New: your own budget checks (#44)

Go: RuntimeOptions.CheckTokenBudgetExhausted and CheckCostBudgetExhausted. TS: checkTokenBudgetExhausted and checkCostBudgetExhausted on setupAgentCore.

  • The defaults are the old token cap and money cap, exported as DefaultCheckTokenBudgetExhausted / DefaultCheckCostBudgetExhausted (TS: defaultCheck…Exhausted), so a hook can call them and keep the cap.
  • A check is told the run (runId, threadId, agentId, state), the step that just finished (step, the stored step record), whether another step would follow (willContinue), what the run has spent with its cap, and publish.
  • True ends the run before the next step, with stopReason token_budget or cost_budget. The check says why with publish; the defaults still send TOKEN_BUDGET_EXHAUSTED and COST_BUDGET_EXHAUSTED.
  • A check that fails (TS: throws; Go: returns an error or panics) is logged and read as false. To fail closed, handle your own errors and return true.
  • Nested runs are checked against their parent's run id, and may call the check at the same time as their parent.
  • The first step of a segment runs without a check. Refuse a run on an empty balance in billingPreCheck at pickup.

Changed

  • stopReason: 'token_budget' now comes from the token check's answer, not from a sum at finalize. With the default check, nothing changes.

See Your own budget checks.

v0.13.0: per-tool time limit

Choose a tag to compare

@eadwinCode eadwinCode released this 03 Nov 15:45
eab15e1

A time limit per tool, in both runtimes: one slow tool can get more time while StepTimeout stays short for every other step. Go module github.com/eadwinCode/agentic-kit/packages/go-agentenkit@v0.13.0, npm agentenkit@0.13.0 and use-agentenkit@0.13.0.

No breaking changes.

New: a tool's own time limit (#42)

Go: Tool.Timeout, or agentenkit.WithToolTimeout(t, 30*time.Minute). TS: withToolTimeout(tool, ms), which returns a copy of the tool.

  • While a call runs, its step has at least that long, even when StepTimeout (TS: stepTimeoutMs) is shorter. Once the call returns, the step is back to StepTimeout, counted from then.
  • A call past its own limit ends the step like a step past StepTimeout: the same step N ran longer than … error, naming the limit that ran out, and the same retry.
  • Other tools keep the step limit. A tool in the same step as a slow one shares its longer time.
  • The tool must stop when its ctx is done (TS: when its abortSignal fires), as with the step limit.
  • It does not lift SegmentTimeout, or a queue's own job limit, such as Flow's step time. Keep those longer than your slowest tool.

New: a subagent's own time limit (#42)

Go: SubagentsConfig.Timeout. TS: subagents.timeoutMs. A child's whole run happens inside one spawnSubagent call, so inside one step of the parent. This gives that call its own limit, so a child, and a slow tool inside it, can outlast the parent's StepTimeout.

Changed

  • Go: a step whose tools include a timed tool now has a context with no Deadline(), because a deadline cannot be moved later. When time runs out, ctx.Err() is Canceled and context.Cause says DeadlineExceeded. The timed call itself gets a real deadline. Steps with no timed tool are as before.
  • Go: a timed-out step keeps the provider's own error text, for example context deadline exceeded (stream read: context canceled). TS keeps it as the error's cause.
  • TS: a step whose time runs out just as the model finishes now fails and retries, as in Go.

See Tools that need more time and Subagents: Limits.

v0.12.0

Choose a tag to compare

@eadwinCode eadwinCode released this 30 Oct 07:48
b9b61d3

Operator tools and limits for queues, in both runtimes: a shared QueueAdmin port, and FlowQueue gets it plus new options. Go module github.com/eadwinCode/agentic-kit/packages/go-agentenkit@v0.12.0, npm agentenkit@0.12.0 and use-agentenkit@0.12.0.

No breaking changes.

New: QueueAdmin port (#40)

pause, resume, purge, listDead, redrive and purgeDead (Go: Pause, Resume, Purge, ListDead, Redrive, PurgeDead). The Go Postgres queue and FlowQueue both have it, so admin code works with either. The Go Postgres PurgeFilter and DeadJob now point to the shared ports types, so existing code still compiles.

On FlowQueue:

  • pause pauses the Flow function. Jobs enqueued meanwhile wait and start on resume.
  • A dead job is a failed run.
    • redrive retries it, but never a run that purge cancelled.
    • purge cancels waiting runs that match. Running ones are left alone, and an empty filter is refused.
    • purgeDead deletes failed runs, except ones kept in the dashboard.

New: FlowQueue options (#40)

  • maxDepth (Go: MaxDepth) refuses a fresh dispatch with QueueFullError. The count lags a few seconds.
  • namespace (Go: Namespace) goes in front of the function ID, so two environments can share one Flow app.
  • stats asks Flow for the oldest queued job, so oldestReadyMs no longer reads low.

New: agentRunFunction options (#40)

Go: clevixflow.Functions.

  • globalConcurrency limits all jobs at once, beside the per-partitionKey limit.
  • retryBackoffMs and retryBackoffMaxMs (Go: RetryBackoff, RetryBackoffMax) set the wait between tries, as on the Postgres queue.
  • segmentTimeoutMs (Go: SegmentTimeout) throws if a segment is not shorter than the step time.

Needs: Flow SDK v0.8.0 (TS: @clevix/flow, from the flow-sdk release), and Flow engine v2.2.0 or newer.

See Setup: On Clevix Flow, with a new note on rollouts, and QueueAdmin.

v0.11.0: Clevix Flow adapters

Choose a tag to compare

@eadwinCode eadwinCode released this 29 Oct 10:50
bfbd16e

agentic-kit can now run on Clevix Flow: the queue, the bus and the run streams. Go module github.com/eadwinCode/agentic-kit/packages/go-agentenkit@v0.11.0, npm agentenkit@0.11.0 and use-agentenkit@0.11.0.

Breaking (Go only)

  • Go 1.27 or newer. flow-sdk needs it, so go-agentenkit does too.

The TS packages have no breaking changes.

New: Clevix Flow adapters (#38, both runtimes)

TS: agentenkit/adapters/flow. Go: adapters/clevixflow.

  • FlowQueue (Go: clevixflow.New), the Queue port. Each job is a Flow run that you can watch in the Flow dashboard.
    • A job key is the run's singleton key, so a key that a live run holds throws DuplicateJobError.
    • A delay is a sleep inside the run. Priority becomes Flow's run priority.
    • cancel, find and stats use Flow's runs API. find and stats lag by a few seconds.
  • agentRunFunction (Go: clevixflow.Functions) makes the Flow function that runs the jobs. Serve it with Flow's serve. When Flow gives up on a run, the job goes to handleDeadJob.
  • FlowBus (Go: clevixflow.NewBus), the EventBus port. One Flow realtime channel per thread, and one socket per thread per process. Big events go through the kv.
  • FlowStreams (Go: clevixflow.NewStreams), the RunStreams port, on Flow streams. Appends go in batches, and big items go through the kv. Time to live and grace are capped at Flow's 7 days.

The bus and the streams need a Kv. You can use any mix: for example FlowQueue with the Redis bus.

Needs: Flow SDK v0.7.0 (TS: @clevix/flow, an optional peer dependency, installed from the flow-sdk release), and Flow engine v2.1.1 or newer.

Limit: a Flow stream holds at most 20,000 items, and an append past that fails. Keep segments short.

See Setup: On Clevix Flow and the examples flow-queue-ts and flow-queue-go.

Other

  • A Go web_fetch test that failed about 1 run in 3 is fixed.

v0.10.0: AI SDK 7 and run sandboxes

Choose a tag to compare

@eadwinCode eadwinCode released this 08 Oct 06:02
8932af9

AI SDK 7, sandboxes per run, and the TypeScript package catching up with Go. Go module github.com/eadwinCode/agentic-kit/packages/go-agentenkit@v0.10.0, npm agentenkit@0.10.0 and use-agentenkit@0.10.0.

Why 0.10.0: the Go module had its own releases after 0.7.0 (v0.8.0–v0.9.0). From now on the Go module and the npm packages share one version number. npm skips 0.8 and 0.9.

Breaking (TS only)

  • AI SDK 7 (#34). ai is now a peer dependency (^7.0.0): install it next to agentenkit, bun add agentenkit ai zod. Node 22 or newer is needed.
  • agentTool({ parameters }) is now agentTool({ inputSchema }), like the SDK's own tool().
  • The examples use @ai-sdk/openai 4 and call openai.chat(...) to stay on Chat Completions.

The stored messages and the streamed chunks do not change shape, so existing threads keep loading and clients need no change.

New: run sandboxes (#35, both runtimes)

  • sandboxScope: 'run' (Go: SandboxScope: agentenkit.SandboxScopeRun): each run gets its own sandbox. It is ended when the run finishes, fails, is stopped or parks; sandboxKeepOnPark keeps it through a park. The default stays one sandbox per thread.
  • A provider can restore the work folder (TS: restoresWorkdir: true; Go: the WorkdirRestorer interface). The tools then tell the model the project files are back, not gone.
  • sandboxDefaults: network, envs, template, image, resources and extra for every sandbox the runtime makes.
  • sandboxStateDir: where the sandbox tools keep their own files. An absolute path keeps .agentenkit out of the work folder, with a folder per sandbox.
  • afterSandboxCall (Go: Tools.AfterSandboxCall): called once after each tool call that used the sandbox, for example to save the work. Its error reaches the model as the call's error.

See Sandboxes.

New in TS, as Go already had (#36)

  • A prompt refused as too long no longer fails the run. The thread is compacted at once and the run goes on from its saved steps. runtime.compactThread(threadId, state) compacts on request, for a /compact command.
  • A history larger than the summary model is summarized in parts, then merged.
  • The settle hook gets the run's state as info.runState, also when the sweep retries it later.

Fixed

  • A rate limit worded "too many tokens" (AWS Bedrock) is no longer mistaken for a too-long prompt (both runtimes).
  • After a too-long retry, a run's token count includes the steps before the refusal (both runtimes).

Other

  • web_fetch can be limited to links from searches or from the user (OnlyKnownURLs, #32).

v0.7.0: prune per tenant

Choose a tag to compare

@eadwinCode eadwinCode released this 30 Sep 10:16
da3fed9

PruneEvents can now prune one tenant's events, so a storage that keeps a database per tenant can clear the old stream-only rows. Go module github.com/eadwinCode/agentic-kit/packages/go-agentenkit@v0.7.0, npm agentenkit@0.7.0 and use-agentenkit@0.7.0.

Changed (#26)

  • New option: PruneOptions.State (TS: runtime.pruneEvents({ state })) reaches the storage the same way a run's state does. Run it once per tenant. With no state, it works as before.
  • Where it applies: runtime.pruneEvents and AgentCore.PruneEvents apply it. The low-level pruneEvents(deps) and core.PruneEvents prune with the state deps is bound with.

Breaking (Go only)

  • EventPruner.Prune takes a trailing sc ports.StorageContext, like every other storage method. A custom adapter that prunes has to add it. The kit's memory, SQLite and Postgres adapters are updated.
  • BoundEvents.Pruner() returns a *ports.BoundPruner, with the context already attached, instead of an EventPruner.

TS has no breaking changes. The optional events.prune port now declares the ctx argument the bound storage was already passing.

v0.6.1: stopped runs are billed in full

Choose a tag to compare

@eadwinCode eadwinCode released this 30 Sep 06:43
63ecc67

A fix for the Go runtime. Go module github.com/eadwinCode/agentic-kit/packages/go-agentenkit@v0.6.1, npm agentenkit@0.6.1 and use-agentenkit@0.6.1.

No breaking changes.

Fixed (#24)

  • Before: a stop that landed after the provider answered, but before the call was priced, could make a pricer that reads a price list fail with context canceled. The paid call was then stored unpriced, so it was never billed.
  • Now: Go prices a usage row on a context a stop cannot cancel, as it already did for the write.
  • Covered: every call: steps of the main run and nested runs, compaction passes and tool calls.
  • TS: already behaved this way. Its pricer is never given a signal.

v0.6.0: MCP tools

Choose a tag to compare

@eadwinCode eadwinCode released this 30 Sep 00:47

Agents can use tools from MCP servers, plus fixes found while moving Clevix to the latest kit. Go module github.com/eadwinCode/agentic-kit/packages/go-agentenkit@v0.6.0, npm agentenkit@0.6.0 and use-agentenkit@0.6.0.

No breaking changes.

MCP tools (#21)

  • A small MCP client in both runtimes: agentenkit/adapters/mcp and go-agentenkit/adapters/mcp. It needs no new dependencies.
  • It connects over stdio or streamable HTTP and turns each of the server's tools into an ordinary tool.
  • Options: a name prefix, a list of tools to keep, approval per tool, and a time limit.
  • Tool errors, time limits and a lost server go back to the model as {"error": ...}.
  • See the new MCP docs page.

Fixes (#22)

  • Refused sends no longer grow the thread. A send refused at dispatch (billing, a full queue) is now sent live only, so a user who keeps pressing Send no longer adds a row to the thread each time. A refusal at pickup belongs to a run and is still stored.
  • Admin reads can carry the tenant. rt.Admin.WithState(state) (TS: runtime.admin.withState(state)) lets the reads that go to storage carry the tenant. These are a run's and a thread's spend, and a run's events.
  • use-agentenkit:
    • A refused run() returns reason and retryAfterSeconds, from the body or a Retry-After header.
    • It reads { error: { code, message } } bodies.
    • After a reload, a tool call carries its stored result.
    • isToolError reads JSON text and lists of results.
    • isToolParked and toolCallResults are exported.
  • isToolUse / IsToolUse tell a paid tool service's usage line from a model call.

v0.5.0: built-in tools

Choose a tag to compare

@eadwinCode eadwinCode released this 27 Sep 09:42

Built-in tools that any model can use, in both runtimes: web search and web fetch, and bash, code_execution and text_editor in one sandbox per thread. Go module github.com/eadwinCode/agentic-kit/packages/go-agentenkit@v0.5.0, npm agentenkit@0.5.0 and use-agentenkit@0.5.0.

No breaking changes: everything new is opt-in.

Built-in tools

  • runtime.builtinTools([...]) (Go: rt.BuiltinTools) gives an agent tools with one name and one input shape in every runtime. The shared definitions live in packages/parity/tools/.
  • The adapters behind them are passed in at setup, with their keys: setupAgentCore({ tools: { search, fetcher, sandbox } }) (Go: RuntimeOptions.Tools). Nothing reads the environment later.
  • Each tool call writes a usage row (kind: 'tool'), so tool spend counts against a run's money cap. pricing.tools prices it per use, and now per second too.

Web tools

  • web_search: short result ids (s1r2), a limit on uses per run, and domain lists and recency set by the app, not the model. Adapters: BraveWebSearch, JinaWebSearch.
  • web_fetch: reads a page by URL or result id. With a prompt, a small model answers from the page, so a long page never fills the context. Adapters: our own PageReader (free, refuses private addresses) and JinaReader.
  • A URL sent with an unknown id is read, rather than failing.

Sandboxes

  • A new sandbox port, shaped like ComputeSDK's. Adapters: DockerSandbox, E2BSandbox, LocalSandbox (development only) in both runtimes; ComputeSdkSandbox in TS; a memory one for tests.
  • One sandbox per thread, kept between messages. It ends when the thread is deleted, after sandboxIdleTtlMs idle (30 min), or after sandboxMaxLifetimeMs (24 h). An idle sandbox shuts itself down, even with no app running.
  • withSandbox(opts, fn) (Go: WithSandbox) gives your own tools the thread's sandbox.

Sandbox tools

  • bash: each command starts in the folder the last one ended in. Asks for approval by default.
  • code_execution: runs Python or JavaScript, lists the files it made, and streams its output as it prints. Does not ask.
  • text_editor: view, create, str_replace, insert and undo. Asks for changes, not for view.
  • approval takes true, false or a check per call. There's a time limit and a limit on uses per run. Long output keeps its start and end. Output streams live as tool.output events.

Also

  • SqliteKv (agentenkit/adapters/sqlite), the TS twin of Go's sqlite.NewKv, with a shared kv test suite in both runtimes.
  • Examples: four small apps with nothing to stand up (web-tools-ts, web-tools-go, sandbox-tools-ts, sandbox-tools-go) sharing one page. The Next.js and Go examples use the tools, and the admin view shows a thread's spend, tool calls included.
  • Docs: new Web tools and Sandboxes pages.

Full details in #14 to #19.