alt-python-boot-lib
Application bootstrap for the alt-python framework. Provides the one-call
Boot.boot() entry point, the startup banner, and the MiddlewarePipeline
used by all HTTP and serverless adapters.
Inspired by Spring Boot's
SpringApplication.run() auto-configuration and application context lifecycle.
Part of the alt-python/boot monorepo.
Install
uv add alt-python-boot-lib # or: pip install alt-python-boot-lib
Requires Python 3.12+, alt-python-config, alt-python-logger, and
alt-python-cdi.
Quick Start
from boot import Boot
from cdi import Context, Singleton
class GreetingService:
def __init__(self):
self.config = None # CDI-autowired
def greet(self, name: str) -> str:
return f"Hello, {name}!"
class Application:
def __init__(self):
self.greeting_service = None # CDI-autowired
def run(self):
print(self.greeting_service.greet("world"))
Boot.boot({
'contexts': [
Context([Singleton(GreetingService), Singleton(Application)])
]
})
Boot.boot() resolves config from the current directory, prints the startup
banner, and calls application.run() on the Application bean.
API
from boot import Boot, MiddlewarePipeline, RequestLoggerMiddleware, ErrorHandlerMiddleware, NotFoundMiddleware
Boot
Boot.boot(options=None)
Bootstrap the application. Loads config, wires the CDI container, prints the
banner, and calls run() on the Application bean.
Boot.boot({
'contexts': [Context([Singleton(MyService), Singleton(Application)])]
})
Options:
| Key | Type | Description |
|---|---|---|
contexts |
list[Context] |
CDI contexts to wire |
config |
config-like | Config source (default: auto-discovered via ConfigFactory) |
Returns the ApplicationContext after start() completes.
Boot.test(options=None)
Test bootstrap. Suppresses the startup banner and captures log output
in-memory. Accepts the same options as Boot.boot().
def test_my_service():
ctx = Boot.test({
'contexts': [Context([Singleton(MyService)])]
})
svc = ctx.get('my_service')
assert svc.greet("world") == "Hello, world!"
Boot.root(name, default=None)
Read a value from the global boot context.
config = Boot.root('config')
logger_factory = Boot.root('logger_factory')
MiddlewarePipeline
The CDI middleware pipeline — the Python equivalent of Spring Security's filter chain, applied uniformly across all HTTP and serverless adapters.
MiddlewarePipeline.compose(middlewares, final_handler)
Composes an ordered list of middleware instances and a final handler into a single async callable.
pipeline = MiddlewarePipeline.compose(middlewares, dispatch)
response = await pipeline(request)
compose() is called once per request. Middleware run in order (lowest order
value first). Each middleware calls await next_fn(request) to pass control
down the chain; returning without calling next_fn short-circuits the pipeline.
MiddlewarePipeline.collect(ctx)
Collects all CDI components that declare __middleware__ = {"order": N} from
an ApplicationContext, filters out uninstantiated entries, and returns them
sorted by order.
middlewares = MiddlewarePipeline.collect(app_ctx)
Writing Middleware
A middleware component is a plain CDI class with __middleware__ = {"order": N}
as a class attribute and an async def handle(self, request, next_fn) method.
Lower order values run first (outermost).
class AuthMiddleware:
__middleware__ = {"order": 5}
def __init__(self):
self.logger = None # CDI-autowired
async def handle(self, request, next_fn):
token = request.get("headers", {}).get("authorization", "").removeprefix("Bearer ")
if not token:
return {"statusCode": 401, "body": {"error": "Unauthorized"}}
return await next_fn({**request, "user": {"token": token}})
Register it in the CDI context — no extra wiring needed:
from boot_aws_lambda import lambda_starter
from cdi import Context, Singleton
context = Context([
*lambda_starter(),
Singleton(AuthMiddleware), # auto-detected via __middleware__
Singleton(TodoController),
])
Normalised Request Shape
All adapters present the same request dict to middleware:
{
"method": "GET",
"path": "/todos/42",
"params": {"id": "42"},
"query": {"page": "1"},
"headers": {...},
"body": {...},
"ctx": application_context,
}
Middleware written against this shape works identically across Lambda, Azure Functions, GCP Cloud Functions, FastAPI, and Flask adapters.
Built-in Middleware
Every *_starter() function registers these three middleware components:
| Class | Order | Behaviour |
|---|---|---|
RequestLoggerMiddleware |
10 | Logs METHOD /path → status (Xms) at verbose level |
ErrorHandlerMiddleware |
20 | Converts unhandled exceptions to JSON error responses |
NotFoundMiddleware |
30 | Returns 404 when no route matches |
print_banner(config=None, logger=None)
Prints the startup banner to stdout. Called automatically by Boot.boot().
Pass config with boot.banner-mode: off to suppress:
from boot import print_banner
print_banner() # prints the banner
print_banner(config) # suppressed if boot.banner-mode == "off"
Testing
Use Boot.test() to suppress the banner and capture logs during tests:
from boot import Boot
from cdi import Context, Singleton
def test_greet():
ctx = Boot.test({
'contexts': [Context([Singleton(GreetingService)])]
})
assert ctx.get('greeting_service').greet("world") == "Hello, world!"
Boot.test() wraps the config in a PropertySourceChain with
boot.banner-mode: off prepended, and uses CachingLoggerFactory so log
output is captured in-memory rather than printed.
Spring Attribution
The Boot lifecycle maps to Spring Boot's SpringApplication.run():
| Spring | alt-python-boot |
|---|---|
SpringApplication.run() |
Boot.boot() |
ApplicationContext.refresh() + start() |
ApplicationContext.start() |
@SpringBootApplication banner |
print_banner() |
Spring Security FilterChain |
MiddlewarePipeline |
Filter.doFilter(req, res, chain) |
handle(request, next_fn) |
License
MIT
Metadata
Release files for alt-python-boot-lib 1.1.1
For a detailed explanation of source distributions (sdists) and built distributions (wheels), please see the package formats documentation.
Source distribution (sdist)
| File | Size | Uploaded | Provenance | |
|---|---|---|---|---|
| alt_python_boot_lib-1.1.1.tar.gz | 6.6 kB | Without provenance | Details |
Built distribution (wheel)
| File | Interpreter | ABI | Platform | Reset |
|---|---|---|---|---|
| alt_python_boot_lib-1.1.1-py3-none-any.whl | Python 3 | none | any | Details |
Total release size: 14.9 kB
Release files / alt_python_boot_lib-1.1.1.tar.gz
| Download URL | alt_python_boot_lib-1.1.1.tar.gz |
|---|---|
| Size | 6.6 kB |
| Tags | Source |
|
SHA-256 checksum How to use checksums |
d2204b43ce2dba35d0b578ee36d01a4c9cc3ab75151b8cb4e99ab991b6c325b1
|
|
BLAKE2b-256 checksum How to use checksums |
2d4af05663acdb8f93add863a0219cce2b7b955e3e7eb1f9d918220ebca9d050
|
| Upload date | |
|
Uploaded using Trusted Publishing? What is trusted publishing? |
No |
| Uploaded via |
uv/0.11.2 {"installer":{"name":"uv","version":"0.11.2","subcommand":["publish"]},"python":null,"implementation":{"name":null,"version":null},"distro":{"name":"Ubuntu","version":"24.04","id":"noble","libc":null},"system":{"name":null,"release":null},"cpu":null,"openssl_version":null,"setuptools_version":null,"rustc_version":null,"ci":true}
|
Release files / alt_python_boot_lib-1.1.1-py3-none-any.whl
| Download URL | alt_python_boot_lib-1.1.1-py3-none-any.whl |
|---|---|
| Size | 8.3 kB |
| Tags | Python 3 |
|
SHA-256 checksum How to use checksums |
5e852201c14370622e290507f75b7eb2c071258427dbca11ef4f9ee5eba5f988
|
|
BLAKE2b-256 checksum How to use checksums |
c395c99b02a9f64b06637a49868fa402c1888c67dc70a406885e6ffe3184d0b2
|
| Upload date | |
|
Uploaded using Trusted Publishing? What is trusted publishing? |
No |
| Uploaded via |
uv/0.11.2 {"installer":{"name":"uv","version":"0.11.2","subcommand":["publish"]},"python":null,"implementation":{"name":null,"version":null},"distro":{"name":"Ubuntu","version":"24.04","id":"noble","libc":null},"system":{"name":null,"release":null},"cpu":null,"openssl_version":null,"setuptools_version":null,"rustc_version":null,"ci":true}
|
Security for alt-python-boot-lib 1.1.1
Provenance
Provenance describes where a file came from. On PyPI, provenance is shared via attestations, which provide a verifiable record of the build or publishing details. View details, limitations and caveats.
No provenance found
None of the files in this release were uploaded with provenance metadata.
A note on package security
PyPI is a repository for distributing packages, not a service for auditing them. While third-party security researchers and our staff do their best to detect and remove malicious packages, PyPI cannot guarantee the quality, security or suitability of any given package.
To learn more about protecting yourself from malicious actors, visit our package security documentation.