Restate is a system for easily building resilient applications using distributed durable async/await. This repository contains the Restate SDK for writing services in Python.
- 🤗️ Join our online community for help, sharing feedback and talking to the community.
- 📖 Check out our documentation to get quickly started!
- 📣 Follow us on Twitter for staying up to date.
- 🙋 Create a GitHub issue for requesting a new feature or reporting a problem.
- 🏠 Visit our GitHub org for exploring other repositories.
Prerequisites:
- Python >= v3.11
To use this SDK, add the dependency to your project:
pip install restate_sdkGiven an app.py:
import restate
greeter = restate.Service("greeter")
@greeter.handler()
async def greet(ctx: restate.Context, name: str) -> str:
return f"Hello {name}!"
app = restate.app(services=[greeter])restate.app takes services, virtual objects and workflows, and anything else that is a
restate.Servable: session objects, and agents, each of which brings along its own companion
(<agent>.prebuilt.restate), the object its tools wait on. Each is served once, however many
things bring it along.
Serve it with restate.serve, which needs the serve extra (pip install "restate-sdk[serve]").
It listens on $PORT, or 9080, with the HTTP/2 that Restate connects with, and
stops on SIGINT or SIGTERM:
if __name__ == "__main__":
import asyncio
asyncio.run(restate.serve(app))Or from the command line, with no __main__ block: python -m restate serve app:app (--port
to choose the port).
restate.app(...) returns an ASGI application, so any ASGI server can serve it instead, for example
Hypercorn:
pip install hypercorn
python -m hypercorn app:app --bind "0.0.0.0:9080"Once served, register the deployment with restate deployments register http://localhost:9080.
An application can connect outbound to Restate Cloud instead of exposing a port. Copy a connect key from the Cloud UI -> Development → Configure SDK, pick a name for the deployment, and run:
RESTATE_CONNECT_KEY=rstcloudv1_... python -m restate connect app:app --name greeter-v1Then register the deployment as connect://greeter-v1.
The same from code:
if __name__ == "__main__":
import asyncio
asyncio.run(restate.connect(app, name="greeter-v1"))Or using the context manager, for finer control:
async with restate.with_connection(app, name="greeter-v1") as connection:
print(connection.info.deployment_url)
await connection.wait_closed()restate.create_client() without a URL connects to Restate Cloud using the ingress key in RESTATE_INGRESS_KEY, copied from the
Cloud UI -> Development → Configure SDK.
The compatibility with Restate is described in the following table. sdk-python versions < 0.10 are deprecated and no longer supported.
| Restate Server\sdk-python | 0.10 - 0.18 | 1.0 |
|---|---|---|
| < 1.3 | ❌ | ❌ |
| 1.3 - 1.4 | ✅ (1) | ✅ (1)(2) |
| 1.5 - 1.6 | ✅ | ✅ (2) |
| 1.7 | ✅ | ✅ |
| 1.8 | ✅ | ✅ (3) |
(1) Note The new Service/Object/Workflow constructor field and the decorator field invocation_retry_policy works only from Restate 1.4 onward. Check the in-code documentation for more details.
(2) Note Scopes and limit keys work only from Restate 1.7 onward. Check the in-code documentation for more details.
(3) Note The list form of state_preload (eager state keys whitelist) works only from Restate 1.8 onward. Check the in-code documentation for more details.
We’re excited if you join the Restate community and start contributing! Whether it is feature requests, bug reports, ideas & feedback or PRs, we appreciate any and all contributions. We know that your time is precious and, therefore, deeply value any effort to contribute!
- Python 3
- PyEnv or VirtualEnv
- just
- Rust toolchain
Set up your virtual environment using the tool of your choice, e.g. VirtualEnv:
python3 -m venv .venv
source .venv/bin/activateInstall the build tools:
pip install -r requirements.txtNow build the Rust module and include opt-in additional dev dependencies:
maturin dev -E test,lintYou usually need to build the Rust module only once, but you might need to rebuild it on pulls.
For linting and testing:
just verifyPull latest main:
git checkout main && git pullUpdate module version in Cargo.toml and run a local build to update the Cargo.lock too, commit it. Then push tag, e.g.:
git tag -m "Release v0.1.0" v0.1.0
git push origin v0.1.0