Python API¶
airflow.providers.lamindb.operators.flow
¶
Operators that open and close the LaminDB flow run of a DAG run.
Both run lamindb inside a virtualenv, so the worker needs no lamindb.
LaminDBFlowInitOperator
¶
LaminDBFlowInitOperator(
*,
task_id: str = "lamindb_flow_init",
is_setup: bool = True,
lamindb_conn_id: str | None = default_conn_name,
lamindb_instance: str | None = None,
lamindb_version: str | None = None,
lamindb_cache_dir: str | None = None,
**kwargs: Any,
)
Bases: _LaminDBFlowOperator
Start the LaminDB flow run for this DAG run, in a virtualenv.
Creates (or restarts, on retry) a Run of the DAG file's Transform and tags
it with the DAG run so downstream LaminDB steps can find it. Wrap the steps in
with init >> finish: to wire them, or let steps with auto_flow=True add
and wire one. Returns the flow run uid.
Marked as an Airflow setup task by default, pairing with the teardown
LaminDBFlowFinishOperator; pass is_setup=False to opt out. Accepts
every PythonVirtualenvOperator argument except python_callable,
op_args and op_kwargs.
Source code in src/airflow/providers/lamindb/operators/flow.py
LaminDBFlowFinishOperator
¶
LaminDBFlowFinishOperator(
*,
task_id: str = "lamindb_flow_finish",
is_teardown: bool = True,
lamindb_conn_id: str | None = default_conn_name,
lamindb_instance: str | None = None,
lamindb_version: str | None = None,
lamindb_cache_dir: str | None = None,
**kwargs: Any,
)
Bases: _LaminDBFlowOperator
Close the LaminDB flow run with the DAG run's outcome, in a virtualenv.
Marked as an Airflow teardown task by default: it runs after every other task
(trigger_rule=all_done_setup_success) and is ignored when Airflow decides the
DAG run state, so a failed step still fails the DAG run. Marks the flow run
errored if any other task in the DAG run failed. Pass is_teardown=False
together with your own trigger_rule to opt out. Accepts every
PythonVirtualenvOperator argument except python_callable, op_args and
op_kwargs.
Source code in src/airflow/providers/lamindb/operators/flow.py
airflow.providers.lamindb.decorators.python_virtualenv
¶
@task.lamindb_venv: run the function as a LaminDB step inside a virtualenv.
lamindb_venv_task
¶
lamindb_venv_task(
python_callable: Callable[..., Any] | None = None,
multiple_outputs: bool | None = None,
**kwargs: Any,
)
@task.lamindb_venv: run the function as a LaminDB step inside a virtualenv.
Accepts every @task.virtualenv argument, plus:
lamindb_conn_id: Airflow connection of typelamindbwith the Lamin API key and the instance; defaultlamindb_default. The virtualenv gets them instead of the worker's~/.lamin.Noneuses lamindb's own configuration instead. Templated, e.g. from an upstream task's XCom.lamindb_instance: instance slug to connect to; overrides the connection's. Templated.lamindb_version: version oflamindb-coreadded torequirementsunless you list lamindb yourself, 2.8.1 or newer; defaults to the instance's version on LaminHub (with a connection), else the latest.lamindb_cache_dir: absolute path of a lamindb cache shared between tasks, set asLAMIN_CACHE_DIR; overrides the connection'scache_dirextra. Templated.auto_flow: wireinit >> step >> finishwith the DAG's flow operators, adding ones with the same Python, index and LaminDB settings if the DAG has none yet. DefaultFalse; mapped steps are never auto-wired.track: record the call in LaminDB. DefaultTrue; withFalsethe function runs exactly as under@task.virtualenv, and lamindb is not added torequirements.
The worker needs no lamindb.
Source code in src/airflow/providers/lamindb/decorators/python_virtualenv.py
airflow.providers.lamindb.decorators.kubernetes
¶
@task.lamindb_k8s: run the function as a LaminDB step in a Kubernetes pod.
lamindb_k8s_task
¶
lamindb_k8s_task(
python_callable: Callable[..., Any] | None = None,
multiple_outputs: bool | None = None,
**kwargs: Any,
)
@task.lamindb_k8s: run the function as a LaminDB step in a Kubernetes pod.
Accepts every @task.kubernetes argument, plus lamindb_conn_id (Airflow
connection of type lamindb; the pod only gets its instance, not its API key),
lamindb_instance (instance slug; overrides the connection's; both templated),
auto_flow (wire flow operators, which run in a virtualenv on the worker, if the
DAG has none yet; default False) and track (record the call in LaminDB; with
False it runs exactly as under @task.kubernetes). The image must have lamindb 2.8.1
or newer installed (the step fails on older versions) and credentials for the instance,
e.g. LAMIN_API_KEY from a Kubernetes secret. The worker needs no lamindb. Requires
pip install "apache-airflow-providers-lamindb[cncf.kubernetes]".
The step needs the lamindb_default connection (or the one named by
lamindb_conn_id) and fails if it is missing. Pass lamindb_conn_id=None to
use only the pod's own lamindb configuration, together with lamindb_instance to
pin the instance. The auto-wired flow operators get the same lamindb_conn_id, so
with None they use the worker's lamindb configuration (LAMIN_API_KEY,
LAMIN_CURRENT_INSTANCE, ~/.lamin) in their virtualenv.
Source code in src/airflow/providers/lamindb/decorators/kubernetes.py
airflow.providers.lamindb.triggers.records
¶
LaminDBRecordEventTrigger
¶
LaminDBRecordEventTrigger(
registry: str,
*,
events: str | Sequence[str] = ("created",),
branch: str | int | None = "main",
filter: FilterLike | None = None,
changed_fields: Sequence[str] | None = None,
**kwargs: Any,
)
Bases: LaminDBDbWriteEventTrigger
Fire an event for every record of a LaminDB registry that is created, updated or deleted.
Use it in an AssetWatcher to schedule DAGs on LaminDB changes. Each event
payload contains the event (created/updated/deleted), the current record
(None for hard deletes), the previous values logged with the write, the changed_fields
of updates, changed_by and the underlying dbwrite log entry.
With branch set (main by default), events are relative to that branch: created also
covers records that arrive on the branch by merging a contribution branch or by restoring them
from the trash or archive, and deleted also covers records moved off the branch, for example
to the trash via record.delete(). For registries without branches, branch is ignored.
Parameters:
-
registry(str) –Registry to watch, e.g.
LaminDBRegistry.COLLECTION,"core.run","core.record"or"bionty.celltype". -
events(str | Sequence[str], default:('created',)) –Events to report, any of
created,updatedanddeleted. -
branch(str | int | None, default:'main') –Name or id of the branch to watch;
Nonereports raw inserts, updates and deletes on all branches. -
filter(FilterLike | None, default:None) –Filter the record must match, built with
F, e.g.F(ArtifactField.KEY).startswith("raw/"), or a LaminHub REST filter such as{"key": {"startswith": "raw/"}}. It's evaluated against the current record; for hard deletes against the deleted row, which only supports direct fields. -
changed_fields(Sequence[str] | None, default:None) –Only report updates that change at least one of these fields, e.g.
[ArtifactField.KEY].Records that hold trigger cursors (see
cursor_store) are never reported. They are recognized by theregistryandreference_typeof this trigger's ownRecordCursorStore(by defaultcore.recordandairflow_trigger_cursor), so give triggers that store cursors in the registry they watch the same settings.
Source code in src/airflow/providers/lamindb/triggers/records.py
LaminDBArtifactEventTrigger
¶
LaminDBArtifactEventTrigger(
*,
key: str | None = None,
key_prefix: str | None = None,
suffix: str | Sequence[str] | None = None,
kind: str | Sequence[str] | None = None,
include_internal: bool = False,
wait_for_upload: bool = True,
**kwargs: Any,
)
Bases: LaminDBRecordEventTrigger
Fire an event for every LaminDB artifact that is created, updated or deleted.
A specialization of LaminDBRecordEventTrigger for core.artifact. By default,
the created event fires only once the artifact's upload to storage has completed
(wait_for_upload), so that downstream tasks can load it right away. Artifacts that LaminDB
creates internally (run logs, environments) are ignored unless include_internal is set.
Parameters:
-
key(str | None, default:None) –Only artifacts with this exact key.
-
key_prefix(str | None, default:None) –Only artifacts whose key starts with this prefix, e.g.
"raw/". -
suffix(str | Sequence[str] | None, default:None) –Only artifacts with this suffix (or any of these suffixes), e.g.
".parquet". -
kind(str | Sequence[str] | None, default:None) –Only artifacts of this kind (or any of these kinds), e.g.
ArtifactKind.DATASET. -
include_internal(bool, default:False) –Also report artifacts LaminDB creates internally.
-
wait_for_upload(bool, default:True) –Report
createdonly once the upload to storage has completed and skip updates of artifacts that are being uploaded. -
events– -
branch– -
filter–Additional filter, see
LaminDBRecordEventTrigger. -
changed_fields–
Source code in src/airflow/providers/lamindb/triggers/records.py
airflow.providers.lamindb.triggers.branches
¶
LaminDBBranchStatusEventTrigger
¶
LaminDBBranchStatusEventTrigger(
*,
to_status: str | Sequence[str] | None = None,
from_status: str | Sequence[str] | None = None,
branch_name: str | Sequence[str] | None = None,
**kwargs: Any,
)
Bases: LaminDBDbWriteEventTrigger
Fire an event whenever the status of a LaminDB branch changes.
Branch statuses are standalone, draft and review (a Change Request is open), and
merged and closed. The event payload contains from_status, to_status, the
branch (with its current status), changed_by and the underlying dbwrite entry.
Parameters:
-
to_status(str | Sequence[str] | None, default:None) –Only report transitions to this status (or any of these statuses).
-
from_status(str | Sequence[str] | None, default:None) –Only report transitions from this status (or any of these statuses).
-
branch_name(str | Sequence[str] | None, default:None) –Only report branches whose name matches this glob pattern (or any of these patterns), e.g.
"release-*".
Source code in src/airflow/providers/lamindb/triggers/branches.py
LaminDBBranchBlockEventTrigger
¶
LaminDBBranchBlockEventTrigger(
*,
kinds: str | Sequence[str] = BLOCK_KINDS,
branch_name: str | Sequence[str] | None = None,
**kwargs: Any,
)
Bases: LaminDBDbWriteEventTrigger
Fire an event whenever a comment or readme is added to a LaminDB branch.
Comments and readmes are core.branchblock records; a new readme version is a new block. The
event payload contains the kind, the block (including its Markdown content), the
branch, changed_by and the underlying dbwrite entry.
Parameters:
-
kinds(str | Sequence[str], default:BLOCK_KINDS) –Block kinds to report,
commentand/orreadme. -
branch_name(str | Sequence[str] | None, default:None) –Only report blocks on branches whose name matches this glob pattern (or any of these patterns).
Source code in src/airflow/providers/lamindb/triggers/branches.py
airflow.providers.lamindb.triggers.base
¶
LaminDBDbWriteEventTrigger
¶
LaminDBDbWriteEventTrigger(
*,
lamindb_conn_id: str | None = default_conn_name,
instance: str | None = None,
poll_interval: float = 30.0,
batch_size: int = MAX_PAGE_SIZE,
max_batches_per_poll: int = 10,
cursor_store: CursorStore | Mapping[str, Any] | None = None,
)
Bases: BaseEventTrigger
Base class for event-driven scheduling triggers that watch the LaminHub database write log.
LaminHub logs every INSERT, UPDATE and DELETE on a LaminDB instance's database in the
hubmodule.dbwrite registry ("Changes → Database writes" in the LaminHub UI). Subclasses define
which writes to poll and how to turn them into trigger events.
The trigger polls writes with an id greater than its cursor, and stores the cursor under
state_key so that a restarted triggerer resumes where it left off. The cursor is committed
at least commit_delay seconds after the events were yielded, which gives Airflow time to persist
them: events are delivered at least once. It is only committed when the trigger processed new
writes. On the first start the trigger only reports writes that happen from then on.
Parameters:
-
lamindb_conn_id(str | None, default:default_conn_name) –Airflow connection of type
lamindb. -
instance(str | None, default:None) –LaminDB instance
owner/name; overrides the connection's instance. -
poll_interval(float, default:30.0) –Seconds between polls of the write log.
-
batch_size(int, default:MAX_PAGE_SIZE) –Number of writes fetched per request (at most 200).
-
max_batches_per_poll(int, default:10) –Maximum number of batches processed per poll cycle.
-
cursor_store(CursorStore | Mapping[str, Any] | None, default:None) –Where and how to store the cursor:
AssetCursorStore(default) in the asset state store of theAssetWatcher's assets, orRecordCursorStorein a record of the watched instance. Both also set thecommit_delay.
Source code in src/airflow/providers/lamindb/triggers/base.py
airflow.providers.lamindb.triggers.cursors
¶
Where the event triggers keep the id of the last processed database write.
Pass a trigger cursor_store=AssetCursorStore() (the default) to keep it in the watched asset's
Airflow asset state store, or cursor_store=RecordCursorStore() to keep it in a record of the
watched instance itself.
DEFAULT_COMMIT_DELAY
module-attribute
¶
Default minimum seconds between yielding events and committing the cursor past them.
CursorStore
dataclass
¶
CursorStore(*, commit_delay: float = DEFAULT_COMMIT_DELAY)
Where and how an event trigger keeps its cursor; use a subclass.
Parameters:
-
commit_delay(float, default:DEFAULT_COMMIT_DELAY) –Minimum seconds between yielding events and committing the cursor past them, which gives Airflow time to persist the events. Longer delays save less often, but redeliver more events after a crash.
coerce
classmethod
¶
coerce(value: CursorStore | Mapping[str, Any] | None) -> CursorStore
Accept a store, its serialize form (as in serialized trigger kwargs) or None.
Source code in src/airflow/providers/lamindb/triggers/cursors.py
open
¶
open(
*, hook: LaminDBHook, asset_state_store: Any, key: str, description: str
) -> CursorBackend
The backend that loads and saves the cursor under key while the trigger runs.
AssetCursorStore
dataclass
¶
AssetCursorStore(*, commit_delay: float = DEFAULT_COMMIT_DELAY)
Bases: CursorStore
Keep the cursor in the asset state store of the AssetWatcher's assets.
The cursor lives in Airflow's metadata database next to the asset events. A trigger outside an
AssetWatcher has no asset state store and keeps its cursor in memory only.
RecordCursorStore
dataclass
¶
RecordCursorStore(
*,
commit_delay: float = DEFAULT_COMMIT_DELAY,
registry: str = "core.record",
field: str = "extra_data",
record_type: str | None = CURSOR_RECORD_TYPE_NAME,
reference_type: str | None = CURSOR_REFERENCE_TYPE,
branch: str | int = "main",
space: str | int | None = None,
name: str | None = None,
description: str | None = None,
)
Bases: CursorStore
Keep the cursor in a record of the watched instance; needs write access to the instance.
The defaults keep each trigger's cursor in its own core.record on main, grouped under the
record type Airflow trigger cursors. The record and its type are created on the first save.
Deleting the record resets the cursor when the trigger restarts; a running trigger creates the
record again on its next save.
Parameters:
-
registry(str, default:'core.record') –Registry of the cursor records. It needs the fields
name,branch,spaceandfield, plusreference_typeandtype/is_typeunless those are disabled below. -
field(str, default:'extra_data') –JSON field that holds the cursor,
{"dbwrite_id": ..., "instance_id": ...}. -
record_type(str | None, default:CURSOR_RECORD_TYPE_NAME) –Name of the record type (
is_type=True) that groups the cursor records;Nonefor no type, for registries without types. -
reference_type(str | None, default:CURSOR_REFERENCE_TYPE) –Marker in
reference_typethat identifies cursor records, so that record triggers onregistrycan skip them;Nonefor no marker. Then such triggers report the cursor records like any other record. A record trigger watchingregistryitself needs a marker, so it rejectsNone. -
branch(str | int, default:'main') –Branch (name or id) of the cursor records and their type.
-
space(str | int | None, default:None) –Space (name or id) of the cursor records and their type, e.g. a restricted space that only the Airflow API key can write to;
Nonefor LaminHub's default space. -
name(str | None, default:None) –Name of the cursor record;
Nonefor the trigger'sstate_key. A fixed name must be unique per trigger, or triggers overwrite each other's cursors. -
description(str | None, default:None) –Description of the cursor record;
Noneto describe the trigger. -
commit_delay(float, default:DEFAULT_COMMIT_DELAY) –See
CursorStore.
airflow.providers.lamindb.sensors.branches
¶
LaminDBBranchStatusSensor
¶
LaminDBBranchStatusSensor(
*,
branch: str | int,
target_status: str | Sequence[str] = "merged",
failure_status: str | Sequence[str] = ("closed",),
lamindb_conn_id: str | None = default_conn_name,
instance: str | None = None,
deferrable: bool = getboolean("operators", "default_deferrable", fallback=False),
**kwargs: Any,
)
Bases: BaseSensorOperator
Wait until a LaminDB branch reaches a status, e.g. until its Change Request is merged.
Returns the branch (with its status), which is pushed to XCom. Fails without retries if the
branch reaches one of the failure_status statuses (by default, when the Change Request is
closed without merging). Network errors, rate limiting and LaminHub server errors don't end the
wait; the sensor checks again later.
For more information on how to use this sensor, take a look at the guide.
Parameters:
-
branch(str | int) –Branch name or id.
-
target_status(str | Sequence[str], default:'merged') –Status (or statuses) to wait for, any of
standalone,draft,review,mergedandclosed. -
failure_status(str | Sequence[str], default:('closed',)) –Status (or statuses) that fail the sensor.
-
lamindb_conn_id(str | None, default:default_conn_name) –Airflow connection of type
lamindb. -
instance(str | None, default:None) –LaminDB instance
owner/name; overrides the connection's instance. -
deferrable(bool, default:getboolean('operators', 'default_deferrable', fallback=False)) –Wait in the triggerer instead of occupying a worker slot.
Source code in src/airflow/providers/lamindb/sensors/branches.py
airflow.providers.lamindb.sensors.records
¶
LaminDBRecordSensor
¶
LaminDBRecordSensor(
*,
registry: str,
filter: FilterLike | None = None,
branch: str | int | None = "main",
min_count: int = 1,
limit: int = 100,
wait_for_upload: bool | None = None,
lamindb_conn_id: str | None = default_conn_name,
instance: str | None = None,
deferrable: bool = getboolean("operators", "default_deferrable", fallback=False),
**kwargs: Any,
)
Bases: BaseSensorOperator
Wait until records matching a filter exist in a LaminDB registry.
Returns the matching records (newest first, at most limit), which are pushed to XCom. Network
errors, rate limiting and LaminHub server errors don't end the wait; the sensor checks again later.
For more information on how to use this sensor, take a look at the guide.
Parameters:
-
registry(str) –Registry to query, e.g.
LaminDBRegistry.RUN,"core.artifact"or"bionty.celltype". -
filter(FilterLike | None, default:None) –Filter built with
F, e.g.F(ArtifactField.KEY) == "raw/sample1.fastq.gz", or a LaminHub REST filter such as{"key": {"eq": "raw/sample1.fastq.gz"}}. It's validated when the DAG is parsed. -
branch(str | int | None, default:'main') –Only records on this branch (name or id);
Nonefor all branches and for registries without branches. -
min_count(int, default:1) –Number of matching records to wait for.
-
limit(int, default:100) –Maximum number of records returned.
-
wait_for_upload(bool | None, default:None) –Ignore artifacts whose upload to storage is still in progress.
-
lamindb_conn_id(str | None, default:default_conn_name) –Airflow connection of type
lamindb. -
instance(str | None, default:None) –LaminDB instance
owner/name; overrides the connection's instance. -
deferrable(bool, default:getboolean('operators', 'default_deferrable', fallback=False)) –Wait in the triggerer instead of occupying a worker slot.
Source code in src/airflow/providers/lamindb/sensors/records.py
LaminDBArtifactSensor
¶
LaminDBArtifactSensor(
*,
key: str | None = None,
key_prefix: str | None = None,
suffix: str | Sequence[str] | None = None,
kind: str | Sequence[str] | None = None,
include_internal: bool = False,
wait_for_upload: bool = True,
**kwargs: Any,
)
Bases: LaminDBRecordSensor
Wait until LaminDB artifacts matching some criteria exist and their upload has completed.
Returns the matching artifacts (newest first, at most limit), which are pushed to XCom.
For more information on how to use this sensor, take a look at the guide.
Parameters:
-
key(str | None, default:None) –Artifact key, e.g.
"raw/sample1.fastq.gz". -
key_prefix(str | None, default:None) –Key prefix, e.g.
"raw/". -
suffix(str | Sequence[str] | None, default:None) –Suffix (or suffixes), e.g.
".parquet". -
kind(str | Sequence[str] | None, default:None) –Artifact kind (or kinds), e.g.
ArtifactKind.DATASET. -
include_internal(bool, default:False) –Also consider artifacts LaminDB creates internally (run logs, ...).
-
filter–Additional filter, see
LaminDBRecordSensor. -
wait_for_upload(bool, default:True) –Ignore artifacts whose upload is still in progress (default).
Source code in src/airflow/providers/lamindb/sensors/records.py
airflow.providers.lamindb.hooks.lamindb
¶
LaminDBHook
¶
LaminDBHook(
lamindb_conn_id: str | None = default_conn_name,
instance: str | None = None,
*,
timeout: float = 30.0,
retries: int = 3,
retry_backoff: float = 1.0,
**kwargs: Any,
)
Bases: BaseHook
Interact with LaminDB instances hosted on LaminHub via the LaminHub REST API.
The connection's password is a Lamin API key; it is exchanged for a short-lived access token that
is refreshed automatically. Without an API key, requests are anonymous, which works for public
instances. The instance (owner/name) is read from the connection's instance extra and can
be overridden per hook. Instances on lamindb older than 2.8.1 are rejected with
LaminDBVersionError.
Parameters:
-
lamindb_conn_id(str | None, default:default_conn_name) –Airflow connection of type
lamindb.Nonemeans anonymous access with default settings, which requiresinstanceto be passed. -
instance(str | None, default:None) –LaminDB instance slug
owner/name. Overrides the connection's instance. -
timeout(float, default:30.0) –Timeout for HTTP requests in seconds.
-
retries(int, default:3) –Number of retries for connection errors and retryable HTTP status codes (429 and 5xx).
-
retry_backoff(float, default:1.0) –Base delay in seconds for the exponential retry backoff.
Source code in src/airflow/providers/lamindb/hooks/lamindb.py
get_conn
¶
Return the (lazily created) synchronous HTTP client.
Source code in src/airflow/providers/lamindb/hooks/lamindb.py
get_async_conn
¶
Return the (lazily created) asynchronous HTTP client.
Source code in src/airflow/providers/lamindb/hooks/lamindb.py
get_instance_slug
¶
get_instance_slug() -> str
Return the configured instance owner/name without contacting LaminHub.
get_cache_dir
¶
get_cache_dir() -> str | None
Return the connection's cache_dir extra: the lamindb cache shared by virtualenv tasks.
get_instance
¶
get_instance() -> LaminDBInstance
Return the configured instance (resolves its id and regional API URL on first use).
Raises LaminDBVersionError if the
instance runs lamindb older than 2.8.1.
Source code in src/airflow/providers/lamindb/hooks/lamindb.py
get_schema
¶
Return the instance schema: {module: {model: {"table_name": ..., "fields": ...}}}.
Source code in src/airflow/providers/lamindb/hooks/lamindb.py
get_registry
¶
Resolve a registry name such as core.artifact or bionty.gene.
Source code in src/airflow/providers/lamindb/hooks/lamindb.py
query_records
¶
query_records(
registry: str | Registry,
filter: FilterLike | None = None,
*,
select: Sequence[str] | None = None,
order_by: Sequence[str | Mapping[str, Any]] | None = None,
limit: int = 50,
offset: int = 0,
include_foreign_keys: bool = True,
search: str | None = None,
branch_ids: Sequence[int] | None = None,
) -> list[dict[str, Any]]
Query records of a registry.
Parameters:
-
registry(str | Registry) –Registry name such as
core.artifact,core.runorbionty.gene, or aLaminDBRegistrymember. -
filter(FilterLike | None, default:None) –Filter built with
F, e.g.F(ArtifactField.SUFFIX) == ".csv", or a LaminHub REST filter such as{"suffix": {"eq": ".csv"}}, see https://docs.lamin.ai/rest -
select(Sequence[str] | None, default:None) –Fields (and relations such as
created_by(handle)) to return. -
order_by(Sequence[str | Mapping[str, Any]] | None, default:None) –Sort order, for example
["-created_at"]. Defaults to ascendingid. -
limit(int, default:50) –Maximum number of records; requests are paginated in pages of 200.
-
offset(int, default:0) –Number of records to skip.
-
include_foreign_keys(bool, default:True) –Include foreign key columns (
run_id,branch_id, ...). -
search(str | None, default:None) –Full-text search string.
-
branch_ids(Sequence[int] | None, default:None) –Restrict the query scope to these branch ids.
Source code in src/airflow/providers/lamindb/hooks/lamindb.py
get_records_by_ids
¶
get_records_by_ids(
registry: str | Registry, ids: Iterable[int], filter: FilterLike | None = None
) -> dict[int, dict[str, Any]]
Fetch records by id, optionally restricted by an additional filter. Returns {id: record}.
Source code in src/airflow/providers/lamindb/hooks/lamindb.py
query_dbwrites
¶
query_dbwrites(
filter: FilterLike | None = None,
*,
after_id: int | None = None,
limit: int = MAX_PAGE_SIZE,
descending: bool = False,
) -> list[dict[str, Any]]
Query the LaminHub database write log, ordered by id.
Every INSERT, UPDATE and DELETE on the instance database is logged with
table_name, sqlrecord_id, event_type, branch_id and data. For updates,
data holds the previous values of the changed fields; for deletes the full previous
row; for inserts it is null.
Source code in src/airflow/providers/lamindb/hooks/lamindb.py
get_latest_dbwrite_id
¶
get_latest_dbwrite_id() -> int
Return the id of the most recent database write (0 if there is none).
get_branch
¶
Return a branch record by name or id, or None if it doesn't exist.
Source code in src/airflow/providers/lamindb/hooks/lamindb.py
get_users
¶
insert_records
¶
insert_records(
registry: str | Registry, records: Sequence[Mapping[str, Any]]
) -> list[dict[str, Any]]
Insert records into a registry and return the created rows.
Needs write access to the instance. Fields are column names, e.g. {"name": "treated"} or
{"type_id": 3}. Inserts are not retried after errors that may have reached LaminHub, so a
failed request never creates a record twice.
Source code in src/airflow/providers/lamindb/hooks/lamindb.py
update_record
¶
update_record(
registry: str | Registry, uid: str, values: Mapping[str, Any]
) -> dict[str, Any] | None
Update fields of the record with uid and return the updated row (if LaminHub returns it).
Source code in src/airflow/providers/lamindb/hooks/lamindb.py
test_connection
¶
Test the connection by resolving the instance and reading its database write log.
Source code in src/airflow/providers/lamindb/hooks/lamindb.py
aget_instance
async
¶
aget_instance() -> LaminDBInstance
Async version of get_instance.
Source code in src/airflow/providers/lamindb/hooks/lamindb.py
aget_schema
async
¶
Async version of get_schema.
Source code in src/airflow/providers/lamindb/hooks/lamindb.py
aget_registry
async
¶
Async version of get_registry.
Source code in src/airflow/providers/lamindb/hooks/lamindb.py
aquery_records
async
¶
aquery_records(
registry: str | Registry,
filter: FilterLike | None = None,
*,
select: Sequence[str] | None = None,
order_by: Sequence[str | Mapping[str, Any]] | None = None,
limit: int = 50,
offset: int = 0,
include_foreign_keys: bool = True,
search: str | None = None,
branch_ids: Sequence[int] | None = None,
) -> list[dict[str, Any]]
Async version of query_records.
Source code in src/airflow/providers/lamindb/hooks/lamindb.py
aget_records_by_ids
async
¶
aget_records_by_ids(
registry: str | Registry, ids: Iterable[int], filter: FilterLike | None = None
) -> dict[int, dict[str, Any]]
Async version of get_records_by_ids.
Source code in src/airflow/providers/lamindb/hooks/lamindb.py
aquery_dbwrites
async
¶
aquery_dbwrites(
filter: FilterLike | None = None,
*,
after_id: int | None = None,
limit: int = MAX_PAGE_SIZE,
descending: bool = False,
) -> list[dict[str, Any]]
Async version of query_dbwrites.
Source code in src/airflow/providers/lamindb/hooks/lamindb.py
aget_latest_dbwrite_id
async
¶
aget_latest_dbwrite_id() -> int
Async version of get_latest_dbwrite_id.
aget_branch
async
¶
Async version of get_branch.
Source code in src/airflow/providers/lamindb/hooks/lamindb.py
aget_users
async
¶
ainsert_records
async
¶
ainsert_records(
registry: str | Registry, records: Sequence[Mapping[str, Any]]
) -> list[dict[str, Any]]
Async version of insert_records.
Source code in src/airflow/providers/lamindb/hooks/lamindb.py
aupdate_record
async
¶
aupdate_record(
registry: str | Registry, uid: str, values: Mapping[str, Any]
) -> dict[str, Any] | None
Async version of update_record.
Source code in src/airflow/providers/lamindb/hooks/lamindb.py
airflow.providers.lamindb.utils.filters
¶
Build, validate and evaluate LaminHub REST filters.
Filters select records by their fields. Build them with F and the field enums, or write the
JSON form of the LaminHub REST API directly. These are equivalent:
F(ArtifactField.KEY).startswith("raw/") & (F(ArtifactField.SIZE) > 1_000_000)
{"and": [{"key": {"startswith": "raw/"}}, {"size": {"gt": 1000000}}]}
F
¶
F(*path: str)
A field to filter on, e.g. F(ArtifactField.KEY), F("key") or F("created_by.handle").
Compare it with a value to get a Condition, using Python's comparison operators (==,
!=, >, >=, <, <=) or the methods of this class. Combine conditions with &
(and) and | (or); as & and | bind more tightly than comparisons, wrap comparisons in
parentheses:
(F(ArtifactField.SUFFIX) == ".parquet") & (F(ArtifactField.SIZE) > 1_000_000)
F(ArtifactField.KEY).startswith("raw/") | F(ArtifactField.KIND).is_in([ArtifactKind.DATASET])
Pass several fields to follow relations: F(ArtifactField.CREATED_BY, UserField.HANDLE) is the
path created_by.handle. Index JSON fields with keys: F(RunField.PARAMS)["learning_rate"].
Parameters:
-
path(str, default:()) –Field enum members or field names, e.g.
ArtifactField.KEYor"key".
Source code in src/airflow/providers/lamindb/utils/filters.py
op
¶
op(operator: FilterOperator | str, value: Any) -> Condition
Compare with any FilterOperator, e.g. F("key").op(FilterOperator.EQ, "a.csv").
eq
¶
Equal to value (==); None selects null values.
ne
¶
Distinct from value, including null values (!=); None selects non-null values.
Source code in src/airflow/providers/lamindb/utils/filters.py
gt
¶
gte
¶
lt
¶
lte
¶
is_in
¶
Equal to any of values; an empty list matches nothing.
not_in
¶
startswith
¶
endswith
¶
contains
¶
The string contains value (case-sensitive), or the JSON array has the element value.
Count
¶
Count(field: F)
FilterExpression
¶
Base class of filters built in Python: Condition, And and Or.
Combine filters with & (and) and | (or); the other operand may also be a LaminHub REST
filter dict. to_dict returns the JSON form that the LaminHub REST API expects.
to_dict
¶
from_dict
staticmethod
¶
from_dict(node: Mapping[str, Any]) -> FilterExpression
Parse and validate a LaminHub REST filter, e.g. {"key": {"eq": "raw/a.csv"}}.
Source code in src/airflow/providers/lamindb/utils/filters.py
Condition
¶
Condition(field: F | str, operator: FilterOperator | str, value: Any)
Bases: FilterExpression
A condition on a field, e.g. Condition(ArtifactField.KEY, FilterOperator.STARTSWITH, "raw/").
Comparing an F creates conditions too, e.g. F(ArtifactField.KEY).startswith("raw/").
Parameters:
-
field(F | str) –The field, as an
F, a field enum member or a field name. -
operator(FilterOperator | str) –A
FilterOperatoror its name, e.g."startswith". -
value(Any) –The value to compare with; enum members, dates, tuples and sets are converted to their JSON form.
Source code in src/airflow/providers/lamindb/utils/filters.py
And
¶
Bases: _Group
All filters match, e.g. And(F("suffix") == ".csv", F("size") > 0); like &.
Source code in src/airflow/providers/lamindb/utils/filters.py
Or
¶
Bases: _Group
At least one filter matches, e.g. Or(F("suffix") == ".csv", F("suffix") == ".tsv"); like |.
Source code in src/airflow/providers/lamindb/utils/filters.py
airflow.providers.lamindb.utils.enums
¶
Enums for building LaminHub REST filters: registries, filter operators, registry fields and values.
The field enums reflect the core registries of LaminDB 2.11. Use them with
F, for example F(ArtifactField.KEY) == "raw/a.csv".
Plain strings work for every field, including fields of other schema modules such as bionty.
LaminDBRegistry
¶
FilterOperator
¶
Bases: _StrEnum
Operators of LaminHub REST filters, see https://docs.lamin.ai/rest.
NE
class-attribute
instance-attribute
¶
Distinct from the value, including null on SQL columns.
GTE
class-attribute
instance-attribute
¶
Greater than or equal to the value (a string or number).
LTE
class-attribute
instance-attribute
¶
Less than or equal to the value (a string or number).
IN
class-attribute
instance-attribute
¶
Equal to any of the listed values; an empty list matches nothing.
IS_NULL
class-attribute
instance-attribute
¶
True selects null values, False selects non-null values.
CONTAINS
class-attribute
instance-attribute
¶
Case-sensitive substring of strings, or element of JSON arrays.
COUNT_EQ
class-attribute
instance-attribute
¶
Number of related records equals the value.
COUNT_NE
class-attribute
instance-attribute
¶
Number of related records differs from the value.
COUNT_GT
class-attribute
instance-attribute
¶
Number of related records is greater than the value.
COUNT_GTE
class-attribute
instance-attribute
¶
Number of related records is at least the value.
COUNT_LT
class-attribute
instance-attribute
¶
Number of related records is less than the value.
COUNT_LTE
class-attribute
instance-attribute
¶
Number of related records is at most the value.
ArtifactKind
¶
Bases: _StrEnum
Values of ArtifactField.KIND.
TransformKind
¶
Bases: _StrEnum
Values of TransformField.KIND.
RunStatus
¶
RegistryField
¶
Bases: _StrEnum
Base class of the registry field enums.
Members that are relations know the registry they point to (related), so that
F can follow them, for example
F(ArtifactField.CREATED_BY, UserField.HANDLE). Foreign keys (..._ID members) hold the id of
the related record and can be compared directly.
ArtifactField
¶
Bases: RegistryField
Fields of core.artifact (LaminDBRegistry.ARTIFACT).
COLLECTIONS
class-attribute
instance-attribute
¶
COLLECTIONS = ('collections', LaminDBRegistry.COLLECTION)
INPUT_OF_RUNS
class-attribute
instance-attribute
¶
INPUT_OF_RUNS = ('input_of_runs', LaminDBRegistry.RUN)
LINKED_BY_ARTIFACTS
class-attribute
instance-attribute
¶
LINKED_BY_ARTIFACTS = ('linked_by_artifacts', LaminDBRegistry.ARTIFACT)
LINKED_BY_RUNS
class-attribute
instance-attribute
¶
LINKED_BY_RUNS = ('linked_by_runs', LaminDBRegistry.RUN)
LINKED_IN_RECORDS
class-attribute
instance-attribute
¶
LINKED_IN_RECORDS = ('linked_in_records', LaminDBRegistry.RECORD)
RECREATING_RUNS
class-attribute
instance-attribute
¶
RECREATING_RUNS = ('recreating_runs', LaminDBRegistry.RUN)
REFERENCES
class-attribute
instance-attribute
¶
REFERENCES = ('references', LaminDBRegistry.REFERENCE)
CollectionField
¶
Bases: RegistryField
Fields of core.collection (LaminDBRegistry.COLLECTION).
META_ARTIFACT
class-attribute
instance-attribute
¶
META_ARTIFACT = ('meta_artifact', LaminDBRegistry.ARTIFACT)
INPUT_OF_RUNS
class-attribute
instance-attribute
¶
INPUT_OF_RUNS = ('input_of_runs', LaminDBRegistry.RUN)
LINKED_IN_RECORDS
class-attribute
instance-attribute
¶
LINKED_IN_RECORDS = ('linked_in_records', LaminDBRegistry.RECORD)
RECREATING_RUNS
class-attribute
instance-attribute
¶
RECREATING_RUNS = ('recreating_runs', LaminDBRegistry.RUN)
REFERENCES
class-attribute
instance-attribute
¶
REFERENCES = ('references', LaminDBRegistry.REFERENCE)
RunField
¶
Bases: RegistryField
Fields of core.run (LaminDBRegistry.RUN).
STATUS_CODE
class-attribute
instance-attribute
¶
The run status as a code, compare it with RunStatus.
INITIATED_BY_RUN_ID
class-attribute
instance-attribute
¶
ENVIRONMENT
class-attribute
instance-attribute
¶
ENVIRONMENT = ('environment', LaminDBRegistry.ARTIFACT)
INITIATED_BY_RUN
class-attribute
instance-attribute
¶
INITIATED_BY_RUN = ('initiated_by_run', LaminDBRegistry.RUN)
INPUT_ARTIFACTS
class-attribute
instance-attribute
¶
INPUT_ARTIFACTS = ('input_artifacts', LaminDBRegistry.ARTIFACT)
INPUT_COLLECTIONS
class-attribute
instance-attribute
¶
INPUT_COLLECTIONS = ('input_collections', LaminDBRegistry.COLLECTION)
INPUT_RECORDS
class-attribute
instance-attribute
¶
INPUT_RECORDS = ('input_records', LaminDBRegistry.RECORD)
LINKED_ARTIFACTS
class-attribute
instance-attribute
¶
LINKED_ARTIFACTS = ('linked_artifacts', LaminDBRegistry.ARTIFACT)
LINKED_IN_RECORDS
class-attribute
instance-attribute
¶
LINKED_IN_RECORDS = ('linked_in_records', LaminDBRegistry.RECORD)
OUTPUT_ARTIFACTS
class-attribute
instance-attribute
¶
OUTPUT_ARTIFACTS = ('output_artifacts', LaminDBRegistry.ARTIFACT)
OUTPUT_COLLECTIONS
class-attribute
instance-attribute
¶
OUTPUT_COLLECTIONS = ('output_collections', LaminDBRegistry.COLLECTION)
OUTPUT_RECORDS
class-attribute
instance-attribute
¶
OUTPUT_RECORDS = ('output_records', LaminDBRegistry.RECORD)
OUTPUT_TRANSFORMS
class-attribute
instance-attribute
¶
OUTPUT_TRANSFORMS = ('output_transforms', LaminDBRegistry.TRANSFORM)
RECREATED_ARTIFACTS
class-attribute
instance-attribute
¶
RECREATED_ARTIFACTS = ('recreated_artifacts', LaminDBRegistry.ARTIFACT)
RECREATED_COLLECTIONS
class-attribute
instance-attribute
¶
RECREATED_COLLECTIONS = ('recreated_collections', LaminDBRegistry.COLLECTION)
TransformField
¶
Bases: RegistryField
Fields of core.transform (LaminDBRegistry.TRANSFORM).
ENVIRONMENT
class-attribute
instance-attribute
¶
ENVIRONMENT = ('environment', LaminDBRegistry.ARTIFACT)
LINKED_IN_RECORDS
class-attribute
instance-attribute
¶
LINKED_IN_RECORDS = ('linked_in_records', LaminDBRegistry.RECORD)
PREDECESSORS
class-attribute
instance-attribute
¶
PREDECESSORS = ('predecessors', LaminDBRegistry.TRANSFORM)
REFERENCES
class-attribute
instance-attribute
¶
REFERENCES = ('references', LaminDBRegistry.REFERENCE)
SUCCESSORS
class-attribute
instance-attribute
¶
SUCCESSORS = ('successors', LaminDBRegistry.TRANSFORM)
RecordField
¶
Bases: RegistryField
Fields of core.record (LaminDBRegistry.RECORD).
COLLECTIONS
class-attribute
instance-attribute
¶
COLLECTIONS = ('collections', LaminDBRegistry.COLLECTION)
INPUT_OF_RUNS
class-attribute
instance-attribute
¶
INPUT_OF_RUNS = ('input_of_runs', LaminDBRegistry.RUN)
LINKED_ARTIFACTS
class-attribute
instance-attribute
¶
LINKED_ARTIFACTS = ('linked_artifacts', LaminDBRegistry.ARTIFACT)
LINKED_COLLECTIONS
class-attribute
instance-attribute
¶
LINKED_COLLECTIONS = ('linked_collections', LaminDBRegistry.COLLECTION)
LINKED_IN_RECORDS
class-attribute
instance-attribute
¶
LINKED_IN_RECORDS = ('linked_in_records', LaminDBRegistry.RECORD)
LINKED_PROJECTS
class-attribute
instance-attribute
¶
LINKED_PROJECTS = ('linked_projects', LaminDBRegistry.PROJECT)
LINKED_RECORDS
class-attribute
instance-attribute
¶
LINKED_RECORDS = ('linked_records', LaminDBRegistry.RECORD)
LINKED_REFERENCES
class-attribute
instance-attribute
¶
LINKED_REFERENCES = ('linked_references', LaminDBRegistry.REFERENCE)
LINKED_TRANSFORMS
class-attribute
instance-attribute
¶
LINKED_TRANSFORMS = ('linked_transforms', LaminDBRegistry.TRANSFORM)
LINKED_ULABELS
class-attribute
instance-attribute
¶
LINKED_ULABELS = ('linked_ulabels', LaminDBRegistry.ULABEL)
LINKED_USERS
class-attribute
instance-attribute
¶
LINKED_USERS = ('linked_users', LaminDBRegistry.USER)
REFERENCES
class-attribute
instance-attribute
¶
REFERENCES = ('references', LaminDBRegistry.REFERENCE)
TRANSFORMS
class-attribute
instance-attribute
¶
TRANSFORMS = ('transforms', LaminDBRegistry.TRANSFORM)
ULabelField
¶
Bases: RegistryField
Fields of core.ulabel (LaminDBRegistry.ULABEL).
COLLECTIONS
class-attribute
instance-attribute
¶
COLLECTIONS = ('collections', LaminDBRegistry.COLLECTION)
LINKED_IN_RECORDS
class-attribute
instance-attribute
¶
LINKED_IN_RECORDS = ('linked_in_records', LaminDBRegistry.RECORD)
TRANSFORMS
class-attribute
instance-attribute
¶
TRANSFORMS = ('transforms', LaminDBRegistry.TRANSFORM)
FeatureField
¶
SchemaField
¶
Bases: RegistryField
Fields of core.schema (LaminDBRegistry.SCHEMA).
VALIDATED_ARTIFACTS
class-attribute
instance-attribute
¶
VALIDATED_ARTIFACTS = ('validated_artifacts', LaminDBRegistry.ARTIFACT)
VALIDATED_COLLECTIONS
class-attribute
instance-attribute
¶
VALIDATED_COLLECTIONS = ('validated_collections', LaminDBRegistry.COLLECTION)
ProjectField
¶
Bases: RegistryField
Fields of core.project (LaminDBRegistry.PROJECT).
COLLECTIONS
class-attribute
instance-attribute
¶
COLLECTIONS = ('collections', LaminDBRegistry.COLLECTION)
LINKED_IN_RECORDS
class-attribute
instance-attribute
¶
LINKED_IN_RECORDS = ('linked_in_records', LaminDBRegistry.RECORD)
PREDECESSORS
class-attribute
instance-attribute
¶
PREDECESSORS = ('predecessors', LaminDBRegistry.PROJECT)
REFERENCES
class-attribute
instance-attribute
¶
REFERENCES = ('references', LaminDBRegistry.REFERENCE)
SUCCESSORS
class-attribute
instance-attribute
¶
SUCCESSORS = ('successors', LaminDBRegistry.PROJECT)
TRANSFORMS
class-attribute
instance-attribute
¶
TRANSFORMS = ('transforms', LaminDBRegistry.TRANSFORM)
ReferenceField
¶
Bases: RegistryField
Fields of core.reference (LaminDBRegistry.REFERENCE).
COLLECTIONS
class-attribute
instance-attribute
¶
COLLECTIONS = ('collections', LaminDBRegistry.COLLECTION)
LINKED_IN_RECORDS
class-attribute
instance-attribute
¶
LINKED_IN_RECORDS = ('linked_in_records', LaminDBRegistry.RECORD)
TRANSFORMS
class-attribute
instance-attribute
¶
TRANSFORMS = ('transforms', LaminDBRegistry.TRANSFORM)
StorageField
¶
BranchField
¶
SpaceField
¶
UserField
¶
Bases: RegistryField
Fields of core.user (LaminDBRegistry.USER).
CREATED_ARTIFACTS
class-attribute
instance-attribute
¶
CREATED_ARTIFACTS = ('created_artifacts', LaminDBRegistry.ARTIFACT)
CREATED_RUNS
class-attribute
instance-attribute
¶
CREATED_RUNS = ('created_runs', LaminDBRegistry.RUN)
CREATED_TRANSFORMS
class-attribute
instance-attribute
¶
CREATED_TRANSFORMS = ('created_transforms', LaminDBRegistry.TRANSFORM)
LINKED_IN_RECORDS
class-attribute
instance-attribute
¶
LINKED_IN_RECORDS = ('linked_in_records', LaminDBRegistry.RECORD)
airflow.providers.lamindb.exceptions
¶
LaminDBApiError
¶
LaminDBApiError(
message: str,
*,
http_status_code: int | None = None,
detail: Any = None,
transient: bool = False,
)
Bases: AirflowException
Raised when the LaminHub REST API returns an error response.
transient is true when the request may succeed if repeated later: network errors, rate
limiting (429) and server errors (5xx).
Source code in src/airflow/providers/lamindb/exceptions.py
LaminDBVersionError
¶
Bases: AirflowFailException, ValueError
Raised for lamindb older than the provider supports; tasks fail without retries.