Skip to content
Development
Skill

/litestar-testing

Use when working with test_*.py, conftest.py, litestar.testing, TestClient, AsyncTestClient, create_test_client, create_async_test_client, anyio, Guard mocks, or DI overrides. Not for generic pytest.

From plugin
litestar
1720 skills1 agent2 hooks

Claude Code

$ npx -y skills add litestar-org/litestar-skills --skill litestar-testing --agent claude-code

SKILL.md

litestar-testing.SKILL.md
name: litestar-testing
description: "Use when working with test_*.py, conftest.py, litestar.testing, TestClient, AsyncTestClient, create_test_client, create_async_test_client, anyio, Guard mocks, or DI overrides. Not for generic pytest."

litestar-testing

Litestar-specific testing patterns built on pytest + anyio. Covers:

  • `TestClient` vs `AsyncTestClient` — constructor options, lifespan, and when to use each
  • `create_test_client` and `create_async_test_client` — inline app factories for isolated handler/controller tests
  • `@pytest.mark.anyio` setup and `pytest-asyncio` coexistence rules
  • App + lifespan fixtures (`on_startup` / `on_shutdown` / `lifespan`)
  • Mocking Guards and overriding DI dependencies (native `Provide` and Dishka `Provider`)
  • Session testing with `set_session_data` and `get_session_data`
  • WebSocket testing with `websocket_connect` and `WebSocketTestSession`
  • Unit-testing Guards and dependencies with `RequestFactory`
  • Live server subprocess testing with `subprocess_async_client` and `subprocess_sync_client`
  • Integration with `pytest-databases` (see `../pytest-databases/SKILL.md`) and `polyfactory` (see `../polyfactory/SKILL.md`)
  • Autowire discovery and cache isolation (see `../litestar-autowire/references/testing.md`)

For JS-side testing (Vitest, Testing Library, Playwright), use the upstream Vitest docs and Litestar's own JS examples. Out of scope here.

Code Style Rules

  • PEP 604 unions: `T | None`, never `Optional[T]`
  • Test modules MAY use `from __future__ import annotations` — they are pure consumer code.
  • Function-based tests (not class-based)
  • One assertion concern per test
  • Async Litestar tests use `@pytest.mark.anyio` by default; do not mix AnyIO and `pytest-asyncio` auto modes.
  • Prefer `AsyncTestClient` for new code; `TestClient` only for legacy / sync-only flows.
  • Always enter test clients as context managers (`async with AsyncTestClient(...)` / `with TestClient(...)`) — implicit lifespan startup without a context manager emits `DeprecationWarning` and is removed in Litestar 3.0.

Quick Reference

TestClient vs AsyncTestClient

| Client | Base Class | Context Manager | Session Helpers | WebSocket Connect | | --- | --- | --- | --- | --- | | `AsyncTestClient` | `httpx.AsyncClient`, `BaseTestClient` | `async with AsyncTestClient(app=app) as client:` | `await client.set_session_data(...)` / `await client.get_session_data()` | `with await client.websocket_connect("/ws") as ws:` | | `TestClient` | `httpx.Client`, `BaseTestClient` | `with TestClient(app=app) as client:` | `client.set_session_data(...)` / `client.get_session_data()` | `with client.websocket_connect("/ws") as ws:` |

Both clients accept the same constructor parameters:

from litestar.testing import AsyncTestClient, TestClient

AsyncTestClient(
    app=app,
    base_url="http://testserver.local",  # Must contain a dot ('.') or UserWarning is emitted
    raise_server_exceptions=True,  # False wraps unhandled server exceptions as HTTP 500 responses
    root_path="",
    backend="asyncio",  # "asyncio" | "trio"
    backend_options=None,
    session_config=None,  # Required for get_session_data() / set_session_data()
    timeout=None,
    cookies=None,
)

Both set `follow_redirects=True` and `headers={"user-agent": "testclient"}` by default. When testing template responses, `TestClientTransport` populates `response.template` and `response.context` on the returned `httpx.Response`.

from litestar.testing import AsyncTestClient


async def test_index(async_client: AsyncTestClient) -> None:
    resp = await async_client.get("/")
    assert resp.status_code == 200
from litestar.testing import TestClient


def test_index(client: TestClient) -> None:
    resp = client.get("/")
    assert resp.status_code == 200

`create_test_client` and `create_async_test_client`

For isolated route handler, controller, or router tests without bootstrapping the full application factory, use `create_async_test_client(route_handlers=..., **litestar_and_client_kwargs)` (or `create_test_client` for sync tests). Both build a `Litestar` instance and return a configured test client.

import pytest
from litestar import get
from litestar.testing import create_async_test_client


@get("/health")
async def health_check() -> dict[str, str]:
    return {"status": "ok"}


@pytest.mark.anyio
async def test_health_check() -> None:
    async with create_async_test_client(route_handlers=health_check) as client:
        resp = await client.get("/health")
        assert resp.status_code == 200
        assert resp.json() == {"status": "ok"}

anyio vs pytest-asyncio Setup

# conftest.py
import pytest


@pytest.fixture(scope="session")
def anyio_backend() -> str:
    return "asyncio"

Prefer `@pytest.mark.anyio` because Litestar's internal concurrency model is built on AnyIO. Do not mix `@pytest.mark.anyio` and `@pytest.mark.asyncio` in the same test module.

App + Lifespan Fixture

# conftest.py
from collections.abc import AsyncGenerator
import pytest
from litestar import Litestar
from litestar.testing import AsyncTestClient

from app import create_app


@pytest.fixture
async def app() -> Litestar:
    return create_app()


@pytest.fixture
async def async_client(app: Litestar) -> AsyncGenerator[AsyncTestClient[Litestar], None]:
    async with AsyncTestClient(app=app) as client:
        yield client

`async with AsyncTestClient(...)` enters `LifeSpanHandler`, firing `on_startup` / `on_shutdown` hooks and plugin `lifespan` context managers (Vite, SAQ, SQLAlchemy, Channels, etc.). Without the context manager, implicit startup emits a `DeprecationWarning` and shutdown hooks never run.

Mocking Guards & Overriding DI Dependencies (Match Your Stack)

Guards are functions of `(connection: ASGIConnection, route_handler: BaseRouteHandler) -> None | Awaitable[None]`. Test the real guard with fake identity or authorization pr

Read more
@litestar-org
Ships withlitestar

Opinionated, first-party agent skills, plugins, subagents, hooks, and rules for the Litestar framework and its ecosystem — published from a single-root repository across Google Antigravity, Claude Code, Codex CLI, Cursor, OpenCode, and VS Code / Copilot.

1720 skills1 agent
Get the whole plugin

Stars on GitHub

Momentum

stars in total
17
Star history of litestar-org/litestar-skills on GitHub, a chart by star-history.com

Other skills on litestar.

advanced-alchemy

advanced-alchemy

Use when working with advanced_alchemy, alembic/, SQLAlchemyAsyncRepositoryService, SQLAlchemyAsyncConfig, repository_type,…

litestar-autowire

litestar-autowire

Use when working with litestar_autowire, AutowirePlugin, AutowireConfig, domain_packages, AutowireIntegration, AutowireLoader, or…

litestar-build

litestar-build

Use when working with uv build, hatch build, PyApp, PYAPP_*, wheel assets, GitHub release matrices, cargo-zigbuild, or…

litestar-docs

litestar-docs

Use when working with zensical.toml, docs/conf.py, sphinx, shibuya, litestar-sphinx-theme, mkdocstrings, Griffe, objects.inv, or…

litestar-email

litestar-email

Use when working with litestar_email, EmailPlugin, EmailConfig, EmailService, EmailMessage, SMTPConfig, ResendConfig,…

More skills from other plugins.

brainstorming
Auto-invoked

brainstorming

You MUST use this before any creative work - creating features, building components, adding functionality, modifying behavior, or…

@obra@obraInstall Skill
ask-matt

ask-matt

Ask which skill or flow fits your situation. A router over the skills in this repo.

skills11d309k
@mattpocock@mattpocockInstall Skill
accessibility
Auto-invoked

accessibility

Design, implement, and audit accessible UI to WCAG 2.2 Level AA across Web, iOS, and Android — semantic ARIA roles and labels,…

ecc13d293k
@affaan-m@affaan-mInstall Skill
compiler-commit

compiler-commit

Use when you want to verify compiler changes and commit with the correct convention. Runs tests, lint, and format, then commits…

react2d252k
@facebook@facebookInstall Skill

Questions about litestar-testing.

Which coding agents can use litestar-testing?
litestar-testing installs in Claude Code, Codex, Cursor, Gemini CLI, GitHub Copilot, OpenCode and Windsurf with the skills CLI, using each agent's flag shown on this page. Flowy's auto-invocation, which fires a skill when your prompt matches, runs in Claude Code only.