labthings_fastapi.deps

FastAPI dependencies for LabThings.

The symbols in this module are type annotations that can be used in the arguments of Action methods (or FastAPI endpoints) to automatically supply the required dependencies.

See the documentation on Dependencies for more details of how to use these.

Attributes

BlockingPortal

A ready-made dependency type for a blocking portal. If you use an argument with

InvocationID

A FastAPI dependency that supplies the invocation ID.

InvocationLogger

A FastAPI dependency supplying a logger for the action invocation.

CancelHook

FastAPI dependency for an event that allows invocations to be cancelled.

GetThingStates

A ready-made FastAPI dependency, returning a function to collect metadata.

Classes

DirectThingClient

A wrapper for Thing that is a work-a-like for ThingClient.

Functions

raw_thing_dependency(→ type[ThingInstance])

Generate a dependency that will supply a particular Thing at runtime.

direct_thing_client_dependency(...)

Make an annotated type to allow Things to depend on each other.

direct_thing_client_class(→ type[DirectThingClient])

Create a DirectThingClient from a Thing class and a path.

Module Contents

labthings_fastapi.deps.BlockingPortal

A ready-made dependency type for a blocking portal. If you use an argument with type BlockingPortal, FastAPI will automatically inject the blocking portal. This is simply shorthand for anyio.from_thread.BlockingPortal annotated with Depends(blocking_portal_from_thing_server).

labthings_fastapi.deps.InvocationID

A FastAPI dependency that supplies the invocation ID.

This calls invocation_id() to generate a new UUID. It is used to supply the invocation ID when an action is invoked.

Any dependency of an action may access the invocation ID by using this dependency.

labthings_fastapi.deps.InvocationLogger

A FastAPI dependency supplying a logger for the action invocation.

This calls invocation_logger to generate a logger for the current invocation. For details of how to use dependencies, see Dependencies.

labthings_fastapi.deps.CancelHook

FastAPI dependency for an event that allows invocations to be cancelled.

This is an annotated type that returns a CancelEvent, which can be used to raise InvocationCancelledError exceptions if the invocation is cancelled, usually by a DELETE request to the invocation’s URL.

labthings_fastapi.deps.GetThingStates

A ready-made FastAPI dependency, returning a function to collect metadata.

Warning

This dependency is deprecated in favour of the ThingServerInterface.

This calls thing_states_getter to provide a function that supplies a dictionary of metadata. It describes the state of all Thing instances on the current ThingServer as reported by their thing_state property.

Use this wherever you need to collect summary metadata to embed in data files.

labthings_fastapi.deps.raw_thing_dependency(cls: type[ThingInstance]) type[ThingInstance]

Generate a dependency that will supply a particular Thing at runtime.

Warning

If it is possible to use a direct_thing_client_dependency instead, that is preferable. The current function supplies a Thing directly and does not supply dependency parameters or enforce the public API.

This function should make it possible for an action to obtain a Thing object directly. If you declare a type alias using this function, it will include an annotation that prompts FastAPI to supply the instance of the class.

Warning

Most linters and type checkers will not accept the result of a function call as a valid type. It may be preferable to use find_raw_thing_by_class directly, even though it is slightly more verbose.

Usage:

from my_other_thing import MyOtherThing as MyOtherThingClass

MyOtherThing = raw_thing_dependency(MyOtherThingClass)


class MyThing(Thing):
    @action
    def do_something(self, other_thing: MyOtherThing) -> None:
        "This action needs no arguments"
        other_thing.function_only_available_in_python()
Parameters:

cls – The class of the Thing that will be supplied

Returns:

An annotated type that works as a dependency to supply an instance of cls at runtime.

labthings_fastapi.deps.direct_thing_client_dependency(thing_class: type[labthings_fastapi.thing.Thing], thing_path: str, actions: list[str] | None = None) type[labthings_fastapi.thing.Thing]

Make an annotated type to allow Things to depend on each other.

This function returns an annotated type that may be used as a FastAPI dependency. The dependency will return a DirectThingClient that wraps the specified Thing. This should be a drop-in replacement for ThingClient so that code is consistent whether run in an action, or in a script or notebook on a remote computer.

See Using Things from other Things and Dependencies.

Note

direct_thing_client_dependency may confuse linters and type checkers, as types should not be the result of a function call. You may wish to manually create an annotated type using direct_thing_client_class.

Parameters:
  • thing_class – The class of the thing to connect to

  • thing_path – The path to the thing on the server

  • actions

    The actions that the client should be able to perform. If this is specified, only those actions will be available. If it is None (default), all actions will be available.

    Note that the dependencies of all available actions will be added to your endpoint - so it is best to only specify the actions you need, in order to avoid spurious extra dependencies.

Returns:

A type annotation that will cause FastAPI to supply a direct thing client

labthings_fastapi.deps.direct_thing_client_class(thing_class: type[labthings_fastapi.thing.Thing], thing_name: str, actions: list[str] | None = None) type[DirectThingClient]

Create a DirectThingClient from a Thing class and a path.

This is a class, not an instance: it’s designed to be a FastAPI dependency.

Parameters:
  • thing_class – The Thing subclass that will be wrapped.

  • thing_name – The name of the Thing on the server.

  • actions – An optional list giving a subset of actions that will be accessed. If this is specified, it may reduce the number of FastAPI dependencies we need.

Returns:

a subclass of DirectThingClient with attributes that match the properties and actions of thing_class. The __init__ method will have annotations that instruct FastAPI to supply all the dependencies needed by its actions.

This class may be used as a FastAPI dependency: see Using Things from other Things.

class labthings_fastapi.deps.DirectThingClient(request: fastapi.Request, **dependencies: Mapping[str, Any])

A wrapper for Thing that is a work-a-like for ThingClient.

This class is used to create a class that works like ThingClient but does not communicate over HTTP. Instead, it wraps a Thing object and calls its methods directly.

It is not yet 100% identical to ThingClient, in particular ThingClient returns a lot of data directly as deserialised from JSON, while this class generally returns pydantic.BaseModel instances, without serialisation.

DirectThingClient is generally not used on its own, but is subclassed (often dynamically) to add the actions and properties of a particular Thing.

Wrap a Thing so it works like a ThingClient.

This class is designed to be used as a FastAPI dependency, and will retrieve a Thing based on its thing_path attribute. Finding the Thing by class may also be an option in the future.

Parameters:
  • request – This is a FastAPI dependency to access the fastapi.Request object, allowing access to various resources.

  • **dependencies – Further arguments will be added dynamically by subclasses, by duplicating this method and manipulating its signature. Adding arguments with annotated type hints instructs FastAPI to inject dependency arguments, such as access to other Things.

__globals__
thing_class: type[labthings_fastapi.thing.Thing]

The class of the underlying Thing we are wrapping.

thing_name: str

The name of the Thing on the server.

_wrapped_thing
_request
_dependencies