v0.3.0
Upgrading from 0.2.0
This release turns a number of silently-wrong declarations into errors. Most surface
the moment a pot is imported, so an upgrade either starts cleanly or tells you exactly
what to change.
Registration now fails for an endpoint that:
- has no docstring — the docstring is the endpoint's goal, so it cannot be empty;
- has a path without a leading slash;
- reuses a
(path, method)pair already registered; - passes
stream=True, which was never implemented; - has an annotation that cannot be resolved, such as a
TYPE_CHECKING-only import or
a model defined inside a function; - declares a capability that is an unbound method or is not callable;
- uses a bodyless method (
GET,DELETE,HEAD) with a Pydantic request model, an
unsupported HTTP verb, or a parameter with no query encoding such as a mapping.
Two changes alter behaviour rather than rejecting it:
method=is now honoured. An endpoint that declaredmethod="GET"previously
servedPOST; it now servesGET, and its parameters move to the query string.
Clients of such an endpoint need updating.- Request validation is stricter. A generic such as
list[int]now validates its
element types instead of accepting anything, so requests that were wrongly accepted
may now return 422. Optional parameters accept an explicitnull, which they
previously rejected.
One change surfaces under traffic rather than at import, and is the one worth checking
before deploying:
- Synchronous capabilities now run in a worker thread so a slow operation no longer
blocks concurrent requests. A capability that captures a thread-affine resource — a
default SQLite connection is the common case — will now fail at request time. Give
such capabilities their own connection per call.
Finally, endpoint failures now return meaningful status codes (429, 502, 504)
rather than an opaque 500, and the response body no longer carries model output or
provider text. Anything depending on the previous bodies should read the status instead.
Added
- Add
usage_limitsandtimeouttoRuntime, and re-exportUsageLimits, so a single endpoint call can be capped on requests, tokens, cost, and wall-clock time. (#23) - Add
Pot(model=...)andPot(runtime=...), and resolveSUMMONPOT_MODELat call time so setting it after import still applies. (#33) - Honour
method=on@pot.summon, registering the declared HTTP verb and taking parameters as a query string for methods that carry no body. (#38) - Added progressive, executable examples covering typed endpoints, required deterministic capabilities, bounded agentic choices, HTTP methods, runtime limits, provider selection, and multi-file services. (#41)
Changed
- Move the shared annotation helpers into a single module so endpoint and capability inspection can no longer drift apart. (#26)
- Raise the CI coverage floor from 50% to 85%, close to the project's actual 88%, so a real regression fails the build. (#34)
- Document that
serve()binds every interface by default, that endpoints carry no authentication yet, and how to bound and protect an exposed pot. (#35) - Document that the closed capability set governs which operations run, not the arguments they receive, and that each capability must validate its own inputs. (#36)
- Reuse an endpoint's agent across requests by moving required-capability tracking onto per-run state, instead of rebuilding every tool and output schema on each call. (#37)
Fixed
- Load pot files that define dataclasses by registering the module in
sys.modulesbefore executing it. (#17) - Report an unloadable pot file once, instead of following it with the exit code formatted as a second error. (#18)
- Append the pot file's directory to
sys.pathinstead of prepending it, so a neighbouring module can no longer shadow the standard library. (#19) - Run synchronous capabilities in a worker thread so a slow operation no longer blocks concurrent requests, and await callable objects whose
__call__is async. (#20) - Accept
functools.partialand callable objects as capabilities, so an operation can carry a connection or configuration, and raise a clear error for values that are not callable. (#21) - Reject an unbound method used as a capability at registration, instead of hiding
selffrom the declared parameters while still demanding it in the schema sent to the model. (#22) - Generate request schemas from the resolved annotation, so optional parameters accept null,
Anyaccepts any JSON value, and generics validate their element types. (#24) - Return meaningful status codes when an endpoint exceeds its budget, times out, or the model fails to satisfy the contract, instead of an opaque 500. (#25)
- Raise at registration when an endpoint annotation cannot be resolved, instead of silently degrading the endpoint to an untyped request body and response. (#27)
- Reject an endpoint without a docstring at registration, instead of running it with an empty agent instruction. (#28)
- Reject an endpoint path that does not start with '/' at registration, instead of building a route no request can reach. (#29)
- Reject a second endpoint registered on an existing path, instead of silently making it unreachable while documenting it in place of the first. (#30)
- Raise when an endpoint is declared with
stream=True, instead of accepting the flag and returning a fully buffered response. (#31) - Copy pot-level capabilities per endpoint so marking one
Requiredcannot make it required for every other endpoint that declares it. (#32) - Allow
SUMMONPOT_MODEL=testto use pydantic-ai's built-in keyless model, so summonpot can be tried without a provider account. (#39) - Report a missing or invalid provider configuration as a labelled error with the cause in the server log, instead of an opaque 500. (#40)