Asset integrity checks
An asset-integrity check is a Jinja assertion template. It runs against accepted inventory for the active site and reports each requirement as passed, failed, or warned.
{% require ... %}is blocking. A failed requirement prevents a protected configuration output from being published.{% warn ... %}is advisory. It records a problem without blocking publication.
Create checks from Templates → New check, choose whether the check inspects inventory or a generated
artifact, and use a clear code and message. Test the check against a real site before linking it to a
configuration template.

Each requirement displays its result and message.
Require named devices
Use an exact name when a particular device is part of the site's contract. exists() is enough for a presence
check; the count in actual makes a failure easier to understand.
{% set router = data.devices.filter('name:eq:edge-router') %}
{% require router.exists(),
code='edge_router_present',
message='The edge router must exist in accepted inventory',
expected='one device named edge-router',
actual=router.count() %}
{% set backup = data.devices.filter('name:eq:backup-nas') %}
{% require backup.exists(),
code='backup_nas_present',
message='The backup NAS must exist in accepted inventory',
expected='one device named backup-nas',
actual=backup.count() %}
If a name is not stable, check a tag or another field exposed in Data reference instead. Do not use a loose substring match for a critical asset unless similarly named devices represent the same asset type.
Require named services
Services are logical capabilities, so they can be used as integrity anchors when the device behind them changes.
{% set grafana = data.services.filter('name:eq:Grafana') %}
{% require grafana.exists(),
code='grafana_service_present',
message='Grafana must still be represented as a service',
expected='one service named Grafana',
actual=grafana.count() %}
{% set dns = data.services.filter('name:eq:DNS') %}
{% require dns.exists(),
code='dns_service_present',
message='The DNS service must still be represented',
expected='one service named DNS',
actual=dns.count() %}
An integrity check can also require that a service has a provider application. Evaluate the provider requirement only when the service exists.
{% set grafana = data.services.filter('name:eq:Grafana').first() %}
{% require grafana is not none,
code='grafana_service_present',
message='Grafana service is missing',
expected='a Grafana service',
actual='missing' if grafana is none else grafana.name %}
{% if grafana %}
{% set providers = data.applications.of(grafana) %}
{% require providers.exists(),
code='grafana_provider_present',
message='Grafana must still have a provider application',
expected='one or more provider applications',
actual=providers.count() %}
{% endif %}
Check generated output too
Inventory checks answer “does the thing exist?” Artifact checks answer “did the generated file contain something safe enough to use?” Choose artifact scope for these assertions.
{% require artifact.content|trim|length > 0,
code='output_not_empty',
message='The generated configuration must not be empty',
expected='non-empty output',
actual=artifact.size %}
{% require 'server_name' in artifact.content,
code='nginx_server_name_present',
message='The Nginx output must contain at least one server_name',
expected='server_name' %}
Attach checks to a configuration template from its Checks tab. Automatic publication requires at least one blocking check, and any failed or non-executed blocking requirement stops publication. A check reports a problem; it does not repair inventory.
Maintain checks
Give every check a message that tells the next operator what to fix. Prefer several small named requirements over one opaque condition. Run checks manually after changing their source, review the preserved evaluations from the configuration template's Checks tab, and only then enable scheduled or inventory-change automation.
See Templates for Nginx, Traefik, and report-generation examples.