> ## Documentation Index
> Fetch the complete documentation index at: https://docs.speckle.systems/llms.txt
> Use this file to discover all available pages before exploring further.

# Data Validation in 2026.9

> What changes for Data Validation after models move to the 2026.9 data format, including related objects, value mapping, and the removal of project standards.

<Note>
  This is 2026.9 preview documentation. Coverage here is incremental: a page exists only where
  2026.9 differs or is newly documented.
</Note>

Use this page when your project is on the 2026.9 data format. Authoring, saving, and result review
still work as in the current product. **Project standards** are not in 2026.9. For check and result
flows that did not change, see [Data Validation](/analytics/data-validation/overview).

This page covers only the differences that change how a check scopes objects, reads properties,
binds a related object (direction, all versus any, multi-hop), and maps labels before a
comparison, plus the Project standards change.

## What stays the same

Checks, thresholds, plan caps, BCF export, and result history follow the current guides:

* [Checks](/analytics/data-validation/checks)
* [Viewing Results](/analytics/data-validation/viewing-results)

Authoring still uses a scope and a check. In 2026.9 the editor shows those as short sentences.
A rule can also include a related object.

## Project standards

2026.9 does not include **Project standards**. The Data Validation sidebar shows **Run check** and
**Checks** only. You cannot create, import, or spawn checks from a project standard.

Reuse across the workspace is planned later as a rollup from Checks into workspace standards. That
flow is not available yet. Until it is, author and save checks.

<Warning>
  If your team spent time developing Project standards in the previous Data Validation flow, email
  [hello@speckle.systems](mailto:hello@speckle.systems).
</Warning>

## Default object scope

In the current product, a new check starts with a global filter that keeps connector BIM objects
and drops proxy and geometry noise. In 2026.9, a new check starts with an **empty** global
scope. The version already contains user-facing objects only, so that starting filter is not
needed.

Do not follow the current [Default scope](/analytics/data-validation/checks#default-scope)
guidance on a 2026.9 version. Leave the global scope empty, then narrow with category, type, or
parameter filters in `WHERE` when you need a tighter rule.

<Warning>
  An existing check can return no objects on a 2026.9 version. Preview shows empty counts and an
  empty object table. The stored rule still uses the previous-format object filter. That filter is
  not shown as a control in the 2026.9 check editor, so you cannot clear it in place. Rebuild the
  check: create a new check, run preview, then save.
</Warning>

Unsaved drafts that still carry the old default are cleared when you reopen the editor. Saved
checks keep their stored rules. After save, you can edit name and description only.

## Checks against related objects

In the current product, a rule looks at properties on one object. In 2026.9 you can also check
that object against something it is related to, because those relationships are in the published
version.

Use **Add related object** on the rule. The editor adds a binding row. The name on the left
(`@host`, `@room`, `@connected`) is how later conditions address that object. Pick a
relationship from the list the version actually carries. Friendly labels include **Host
element**, **Sub-elements**, **Room**, **Bounded room**, **Assembly**, and **Connected
element**.

Then choose a property on that related object from the path picker. Related paths show as
`@host · Fire Rating` in the sentence pills.

**Add condition** adds a scope filter above the check. It does not turn the existing check into a
filter.

Rules display as short sentences, for example **category is Doors**. Select a sentence to edit
it.

<Note>
  **Add related object** is disabled when the preview version has no relationship data. The tooltip
  reads **This model has no relationship data — re-publish with a current connector to use
  related-object rules.** Publish a new version after the project uses the 2026.9 data format.
</Note>

### Direction, all versus any, and narrowing

The arrow on the binding follows the relation **forward** (for example a door toward its host
wall) or **backward** (a wall toward the elements hosted on it). Click the arrow to reverse it.

**all** (default) means every related object must satisfy the check. **any** means one related
object is enough. That setting applies to the check only. A scope filter on a related path still
keeps a subject when at least one related object matches, regardless of **all** or **any**.

Open **where** and select **Narrow related objects** to keep only some related objects, for
example hosts whose category is Walls. Those filters run on the related object. They do not use
`@` prefixes.

### When there is no related object

A subject with no related object **fails** a check that reads that binding. If a door with no
host should be not applicable instead of a fail, add a scope condition that the related path
exists (for example `@host` is present) before the check.

Examples you can author:

* A door's fire rating must match the wall that hosts it
* If the host wall is fire-rated, the door must be rated. Unrated walls are not applicable, not a
  fail (scope on the host rating, then check the door)
* Every door must be hosted on a wall
* Every wall that bounds a room carries a rating (**all**), or at least one of them does
  (**any**)
* A door can be checked against a room reached through the host wall: add a second related
  object, set **of** to `@host` instead of **this element**, and pick **Bounded room** or
  **Room**

You cannot remove a binding while a condition still uses `@name`, or while a later binding
chains from it. Update those references first.

## Map labels before you compare

When a check compares two properties (**Equals property**), 2026.9 can map each side's raw
labels onto shared values before it compares them. This is how `60 MIN` and `1 HR` become the
same rating, and how a `2 HR` wall can require a door of at least `90 MIN`.

Select **Equals property**, pick the other path, then open the comparison control beside it. The
control shows `=` until you add a mapping or change the comparison.

Set **Compare** to **= equals**, **≥ at least**, or **≤ at most**. Under **This value maps** and
**Other value maps**, select **Add mapping**, pick a raw value from the list, and set what it
**maps to**. Unmapped values stay as they are.

Map both sides to the same numbers when the labels should count as equal. Map the other side to a
required minimum and use **≥ at least** when one side must be stricter than the other.

The same mapping works when the other path is on a related object, such as a host wall.

<Tip>
  If preview already lists known values, **Seed N known values** on that mapping list fills it so
  you do not type every label. Seed one side at a time. The control is hidden when the list is empty
  or too large to seed in one step.
</Tip>

## Match a property wherever it sits

A Fire Rating parameter is not always on the same path. Click the path-matching control next to
the path to cycle modes:

* **Exact** (`=`) — the full path from the picker
* **Suffix** (`*.x`) — every property whose path ends with that segment, for example **Fire
  Rating**. Every matching value must pass
* **Regex** (`.*`) — a regular expression over the full path

That covers instance and type placements without a separate rule for each path. Path matching is
not available on **Equals property** or **Equals template**. Those operators compare two specific
paths.

## Property paths

Always pick property paths from the path picker after a preview model loads. Paths in the current
[Checks](/analytics/data-validation/checks#property-paths) examples, such as
`parameters.Width.value` and `baseline.length`, come from the previous data format and may not
exist on a 2026.9 version.

Typical Revit parameters now sit under `properties.Parameters` (for example type Width under
`properties.Parameters.Type Parameters.Dimensions.Width`). Use the picker for the paths that
exist on your model.

## Versions you can run against

Data Validation preview and saved-check runs need a version in the 2026.9 data format. If preview
does not load, publish a new version after the project has moved to 2026.9. See
[Speckle's data model is changing](/workspaces/data-model-migration).

## FAQ

<AccordionGroup>
  <Accordion title="Where did Project standards go?">
    They are not in 2026.9. Author and save checks instead. A later step is a rollup from Checks
    into workspace standards. That is not available yet. If you already built Project standards,
    email [hello@speckle.systems](mailto:hello@speckle.systems). See [Project
    standards](#project-standards).
  </Accordion>

  <Accordion title="Why does my existing check show 0 objects after the project moves to 2026.9?">
    The saved rule still uses the previous-format object filter. That filter is not shown in the
    2026.9 check editor, and saved checks cannot change rules in place. Create a new check, run
    preview, then save. See [Default object scope](#default-object-scope).
  </Accordion>

  <Accordion title="Should I still drop DataObject to widen scope?">
    No. That step is for the current product. In 2026.9 the object set is already the user-facing
    elements. An empty global scope is the correct starting point. Narrow with category, type, or
    parameter filters in `WHERE` when you need a tighter rule.
  </Accordion>

  <Accordion title="Why is Add related object disabled?">
    The preview version has no relationship data. The tooltip asks you to re-publish with a current
    connector. Publish a new version after the project uses the 2026.9 data format. See [Checks
    against related objects](#checks-against-related-objects).
  </Accordion>

  <Accordion title="Why does a door with no host fail the related-object check?">
    A subject with no related object fails a check that reads that binding. Add a scope condition
    that the related path exists if that case should be not applicable. See [When there is no
    related object](#when-there-is-no-related-object).
  </Accordion>

  <Accordion title="What is the difference between all and any?">
    **all** requires every related object to satisfy the check. **any** requires one. Scope filters
    on related paths still keep a subject when at least one related object matches. See [Direction,
    all versus any, and narrowing](#direction-all-versus-any-and-narrowing).
  </Accordion>

  <Accordion title="How do I check a door against the wall that hosts it?">
    On the door rule, select **Add related object**, choose **Host element**, then compare the
    door's fire rating to the host's fire rating with **Equals property**. Map labels if one side
    uses minutes and the other uses hours. See [Map labels before you
    compare](#map-labels-before-you-compare).
  </Accordion>

  <Accordion title="How do I treat 60 MIN and 1 HR as the same rating?">
    On an **Equals property** comparison, open the comparison control beside the other path. Under
    **This value maps** and **Other value maps**, add a mapping so both labels map to the same
    number, such as `60`. Unmapped values stay as they are. See [Map labels before you
    compare](#map-labels-before-you-compare).
  </Accordion>

  <Accordion title="How do I match Fire Rating on every path it appears?">
    Click the path-matching control until it shows **suffix** (`*.x`), and set the path to **Fire
    Rating**. Every matching value must pass. Click again for regex over the full path. Path
    matching is not available on **Equals property**. See [Match a property wherever it
    sits](#match-a-property-wherever-it-sits).
  </Accordion>

  <Accordion title="Do I rewrite every property path in every check?">
    Only when a path no longer exists on the new version. Load preview, pick the replacement from
    the path picker, and save a new check. Saved checks cannot change rules in place.
  </Accordion>
</AccordionGroup>
