Releases: restatedev/sdk-python
v1.0.0
The Restate Python SDK reaches 1.0! 🎉
This release brings many new features to the SDK to use together with Restate 1.7: scope and limit keys for flow control, signals for direct invocation-to-invocation communication, terminal error metadata, and several other improvements.
New Features
(Preview) Scope and limit key to enable flow control
This release adds the SDK API for flow control, the new Restate 1.7 feature to cap how many invocations run concurrently within a scope, with optional hierarchical limit keys. Use it to bound cost (especially for AI agents, where every concurrent invocation is real model/API spend), shield downstream systems from bursts, and share capacity fairly across tenants.
To use scope and limit keys in service to service communication:
# Route a call into a named scope
await ctx.scope("tenant-123").service_call(MyService.process, payload)
# Add a limit key for hierarchical concurrency limits within the scope
await ctx.scope("tenant-123").workflow_call(
MyWorkflow.run, "wf-key", payload, limit_key="api-key/user42"
)The scope also becomes part of the invocation's identity and is exposed back on ctx.request().scope / ctx.request().limit_key.
Check out the Flow control documentation for more details on how concurrency limits work and how to set them up.
NOTE: This API is in preview and is not enabled by default. To use it in restate-server 1.7, enable the flow control and protocol v7 experimental features via
RESTATE_EXPERIMENTAL_ENABLE_PROTOCOL_V7=trueandRESTATE_EXPERIMENTAL_ENABLE_VQUEUES=true(new clusters only). See https://docs.restate.dev/services/flow-control for details.
Signals
Signals let invocations communicate directly with each other: one invocation waits for a named signal, and any other handler can resolve or reject it by referencing the target invocation's ID.
# Inside the invocation that wants to wait:
approved = await ctx.signal("approved", type_hint=bool)
# Inside another handler that knows the target invocation's ID:
ctx.resolve_signal(target_invocation_id, "approved", True)
# or, to wake the waiter with a terminal error:
ctx.reject_signal(target_invocation_id, "approved", "Request denied")NOTE: Signals require restate-server 1.7 with
RESTATE_EXPERIMENTAL_ENABLE_PROTOCOL_V7=trueenabled.
TerminalError metadata
TerminalError now carries an optional metadata dictionary, propagated alongside the error message and status code. Use it to attach structured, machine-readable context to terminal failures.
raise TerminalError(
"Payment declined",
status_code=402,
metadata={"reason": "insufficient_funds"},
)General improvements
- New cooperative suspensions behavior when awaiting futures (#192): the SDK now propagates the full tree of pending futures to the shared core to decide when and how to suspend, resulting in less concurrency-quota thrashing when fanning out many requests from one handler to others.
- Cheaper
ctx.runround-trips: instead of echoing the full completion message back to the SDK after storing actx.runresult, the runtime replies with an ack message. This noticeably cuts network cost for handlers with many or largectx.runentries. - zstd response compression on AWS Lambda (#206): on Python 3.13 or older, install the optional dependency with
pip install restate_sdk[zstd]to enable it. - Fixed a race condition in the LangChain turnstile (#198).
- Require tool calls to carry an ID in the LangChain extension (#199).
- Journal the tool message ID (#200).
pydantic: usecurrent_context()inRestateModelWrapper.request_stream, fixing anAttributeErroron streaming /event_stream_handler(#201).
NOTE: The cooperative suspensions and run-acks improvements above are enabled in restate-server 1.7 with
RESTATE_EXPERIMENTAL_ENABLE_PROTOCOL_V7=trueset up.
What's Changed
- Cooperative suspensions by @slinkydeveloper in #192
- Add TerminalError.metadata by @slinkydeveloper in #196
- Bump shared core by @slinkydeveloper in #197
- Fix race condition langchain turnstile by @gvdongen in #198
- Require tool calls with ID in langchain ext by @gvdongen in #199
- Bump shared core by @slinkydeveloper in #202
- Journal tool message ID by @gvdongen in #200
- Support zstd compression for py < 3.14 by @aelci in #206
- feat: Add scopes, flow-control limit keys and signals by @slinkydeveloper in #207
- fix(pydantic): use current_context() in RestateModelWrapper.request_stream (AttributeError on streaming / event_stream_handler) by @selimacerbas in #201
New Contributors
- @aelci made their first contribution in #206
- @selimacerbas made their first contribution in #201
Full Changelog: v0.18.0...v1.0.0
v0.18.1
- PR 198 Fixed race condition in LangChain integration
Full Changelog: v0.18.0...v0.18.1
v0.18.0
v0.17.1
What's Changed
Full Changelog: v0.17.0...v0.17.1
v0.17.0
What's Changed
- Use WarpBuild runners for CI workflows by @tillrohrmann in #185
- Introduce RetryableError by @hatstand in #184
- Add a RestateTracer and RestateTracerProvider for AI observability by @gvdongen in #187
New Contributors
Full Changelog: v0.16.0...v0.17.0
v0.16.0
What's Changed
- Pydantic AI integration: upgrade pydantic ai library to 1.68.0. Disable autowrapping tools in ctx.run. Default retry strategy for LLM calls is now 10 attemps with 1 second minimum interval.
- Google ADK integration: Added RestateEventsSummarizer to wrap LLM summarization calls in durable steps and added flushing compaction events in append_event to Restate.
Bug fixes
- fix: #175 BidiStream SIGTERM causes CPU hot loop and pod stuck in Terminating by @brightsparc in #176
- Bump shared core, bump max protocol version, update feature matrix by @slinkydeveloper in #183
New Contributors
- @brightsparc made their first contribution in #176
Full Changelog: v0.15.0...v0.16.0
v0.15.0
What's Changed
- Support zstd compression in python 3.14+ by @jackkleeman in #174
Full Changelog: v0.14.2...v0.15.0
v0.14.2
What's Changed
- Update shared core by @slinkydeveloper in #170
- Fix stacktrace propagation inside ctx.run by @slinkydeveloper in #171
Full Changelog: v0.14.0...v0.14.2
v0.14.0
What's Changed
- doc: fix various typos by @didier-durand in #168
- Add pydantic ai by @igalshilman in #167
- [extensions] Avoid global state in the ADK plugin by @igalshilman in #169
New Contributors
- @didier-durand made their first contribution in #168
Full Changelog: v0.13.2...v0.14.0
v0.13.2
What's Changed
- OpenAI integration: DurableRunner with LLM retry opts and lazy session flushing by @gvdongen in #164
- Add explicit tool execution synchronization by @igalshilman in #165
- Cancel subsequent tools by @igalshilman in #166
Full Changelog: v0.13.1...v0.13.2