Contact
Data reference

The scene record, field by field.

Terrain360 captures corridors as georeferenced 360° panoramas. Scene Intelligence is the structured record read out of those panoramas: located objects with computed compass bearings, transcribed on-scene text, scene-level conditions, and a controlled tag vocabulary. This page documents that record for the people who have to integrate it — its schema, its coordinate semantics, its reliability tiers, its versioned lenses, and its public read endpoints.

Every figure below is queried from the running system when this page is served. Nothing on it is transcribed by hand, because the page it replaced was, and it drifted.

Coverage

Extraction is project-scoped, not corpus-wide.

A scene record exists only where a corridor has been licensed, captured, and run. The counts below are current as of this request, and they move — corridors are being read in overnight batches. Do not assume a panorama you can see in the viewer has a record behind it: ask the endpoint, and expect a 404 for most of the fleet today.

28,893
Panoramas with
a scene record
75
Corridors
covered
24
States
represented
871,620
Public panoramas
in the platform
50,658
Object observations
on record
4,914
Text transcriptions
on record
Read the covered figure against the fleet figure before you scope anything. Coverage is a live count precisely so this page cannot go stale between corridor deliveries: every number here is queried when the page is served, never typed in. The corridor and panorama totals and the tier table below are read from a single snapshot, so the tier rows always sum to the total above even while a batch is landing. Search the same corpus on /discover.

Not every covered scene carries the same record

Coverage is read at one of two depths, and the difference matters more than the totals do. Check tier before you assume a field exists.

Tier Panoramas Corridors Payload sections What it carries
lite 24,114 54 texts · tags · scalars · caption Caption, tags, transcribed text with legibility, surface and water character, people count, scene rating, capture issues. No entities array — nothing located, no bearings.
full 4,779 21 entities · texts · tags · scalars · caption Adds an entities array: located objects with a source face, an anchor, distance and condition. Whether an object is pixel-grounded depends on when its corridor was read — see the reliability tiers below for the live position.
Located objects and bearings exist at full tier only. The lite extraction schema has no entities section at all, so a lite scene can carry a caption, tags, and transcribed text but cannot carry a positioned object — and therefore cannot carry a bearing. Breadth of coverage and depth of coverage are two different numbers, and the table above is the only place they are reconciled. If your integration depends on bearings, scope it to full-tier corridors and confirm with the tier field on every payload rather than assuming.
Schema

Six additive tables in maintain_data.

The record is additive: it sits beside the existing corridor and panorama tables and never rewrites them. Column names, types, and nullability below are generated from the database catalog when this page is served — this is the live schema, not a description of it. The notes are the only hand-written part.

maintain_data.scene_intel

One row per panorama that has been read. The flat columns are the scene-level facts; the graph column holds the full structured reading.

Column Type Null Notes
scene_id integer no Primary key. The panorama this record describes; the same id the read endpoints take.
trail_id integer no Corridor the panorama belongs to. Every public read is gated on this corridor being public.
tier text no Depth of the pass that produced the record. full carries an entities array; lite does not, so a lite scene has no located objects and no bearings. Check this before assuming a field is present.
schema_v smallint no Structure version of the stored graph. Compare this before parsing, not the extraction date.
model text yes Internal provenance of the pass. Not served by the public endpoints.
batch_id text yes Internal job identity for reconciliation. Not served publicly.
graph jsonb no Full structured reading of the scene. The flat columns beside it are denormalised for query speed.
caption text yes One-sentence factual description of the scene.
scenic smallint yes Openness / composition indicator for the view.
season text yes Season as it appears in the imagery, not as inferred from the capture date.
water_kind text yes Character of the water visible in the scene, where any is.
trail_surface text yes Surface underfoot as read from the imagery.
people_count smallint yes People visible. Drives review escalation; no identification is performed or stored.
escalated boolean no True when the scene was re-read at higher resolution for one of the escalation triggers.
extracted_at timestamp with time zone no When this record was written.
Values the database enforces
scene_intel_tier_check
  CHECK ((tier = ANY (ARRAY['lite'::text, 'full'::text])))

maintain_data.scene_entities

One row per observed object. This is where the located record lives — face, anchor pixel, computed angles, and the reliability tier that decides whether it may be drawn.

Column Type Null Notes
id bigint no Surrogate key.
scene_id integer no Panorama the observation was read from.
trail_id integer no Corridor, denormalised for the public gate and for corridor-wide queries.
type text no Coarse class of the observed object. The live vocabulary is listed below.
label text yes Free-text label as read. Trigram-indexed for fuzzy matching.
face character yes Cube face the object was seen on: f, r, b, l, u, d.
bearing_deg smallint yes Legacy captured bearing. Kept for pre-v2 rows; new rows derive bearing from pano_ath_deg instead.
dist_m integer yes Estimated distance from the camera, in metres. An estimate, and labelled as one.
attributes jsonb yes Type-specific detail. Reviewer audit history is held privately inside this column and is never served.
condition text yes Condition as observed, where the type supports one.
confidence real yes Confidence in the SEMANTIC identification. Separate from grounding confidence.
source text no ai or human. Human rows survive every subsequent automated re-read.
hidden boolean no Reviewer-suppressed. Hidden rows are excluded from every public read.
elev_deg numeric yes Elevation angle above (+) or below (−) the horizon, computed from the anchor pixel.
source_image_index smallint yes One-based cube face index returned by the reading pass. Must agree with face.
anchor_x numeric yes Normalised horizontal position of the object centre within that face image. 0 is the left edge.
anchor_y numeric yes Normalised vertical position within that face image. 0 is the TOP edge.
pano_ath_deg numeric yes Panorama-relative azimuth computed from the anchor pixel. Immutable pixel geometry — see Coordinates below.
grounding_quality text no Which rung of the reliability ladder this observation sits on.
grounding_source text no How the position was established: computed from a reading, clicked by a reviewer, or inherited from before pixel grounding existed.
grounding_confidence real yes Confidence in the COORDINATE only. This is what the ladder thresholds on.
grounding_issue text yes Why an observation failed validation, when it did.
corrected_by bigint yes Reviewer account that corrected the position. Never served publicly.
corrected_at timestamp with time zone yes When the correction was made. Never served publicly.
Values the database enforces
scene_entities_anchor_pair_check
  CHECK (((grounding_quality = ANY (ARRAY['unreliable'::text, 'legacy'::text])) OR ((anchor_x IS NULL) = (anchor_y IS NULL))))
scene_entities_anchor_x_check
  CHECK (((anchor_x IS NULL) OR ((anchor_x >= (0)::numeric) AND (anchor_x <= (1)::numeric))))
scene_entities_anchor_y_check
  CHECK (((anchor_y IS NULL) OR ((anchor_y >= (0)::numeric) AND (anchor_y <= (1)::numeric))))
scene_entities_face_image_match_check
  CHECK (((grounding_quality = ANY (ARRAY['unreliable'::text, 'legacy'::text])) OR (source_image_index IS NULL) OR ((face = 'f'::bpchar) AND (source_image_index = 1)) OR ((face = 'r'::bpchar) AND (source_image_index = 2)) OR ((face = 'b'::bpchar) AND (source_image_index = 3)) OR ((face = 'l'::bpchar) AND (source_image_index = 4)) OR ((face = 'u'::bpchar) AND (source_image_index = 5)) OR ((face = 'd'::bpchar) AND (source_image_index = 6))))
scene_entities_grounding_confidence_check
  CHECK (((grounding_confidence IS NULL) OR ((grounding_confidence >= (0)::double precision) AND (grounding_confidence <= (1)::double precision))))
scene_entities_grounding_quality_check
  CHECK ((grounding_quality = ANY (ARRAY['verified'::text, 'reliable'::text, 'approximate'::text, 'unreliable'::text, 'legacy'::text])))
scene_entities_grounding_source_check
  CHECK ((grounding_source = ANY (ARRAY['ai'::text, 'manual'::text, 'legacy'::text])))
scene_entities_source_check
  CHECK ((source = ANY (ARRAY['ai'::text, 'human'::text])))
scene_entities_source_image_index_check
  CHECK (((source_image_index IS NULL) OR ((source_image_index >= 1) AND (source_image_index <= 6))))

maintain_data.scene_texts

One row per piece of text read off a sign, marker, or plate in the scene.

Column Type Null Notes
id bigint no Surrogate key.
scene_id integer no Panorama the text was read from.
trail_id integer no Corridor, denormalised for the public gate.
text text no Transcription as read from the imagery. Trigram-indexed.
object text yes What carried the text — sign, marker, gauge plate, posting.
legibility text yes clear or partial. Read the Sign text section below before building on this column.
verified boolean no True once a human has confirmed the transcription against the imagery.
source text no ai or human.
Values the database enforces
scene_texts_source_check
  CHECK ((source = ANY (ARRAY['ai'::text, 'human'::text])))

maintain_data.scene_intel_tag_dict

Controlled vocabulary of tag terms, built from what has actually been read rather than from a fixed list.

Column Type Null Notes
tag_id integer no Surrogate key referenced by scene_intel_tags.
tag text no The term itself. Unique.

maintain_data.scene_intel_tags

Join between panoramas and terms.

Column Type Null Notes
scene_id integer no Panorama.
tag_id integer no Term from the dictionary.
source text no ai or human.
Values the database enforces
scene_intel_tags_source_check
  CHECK ((source = ANY (ARRAY['ai'::text, 'human'::text])))

maintain_data.scene_search_documents

Search index over the record. Backs the search and facets endpoints.

Column Type Null Notes
scene_id integer no Panorama.
trail_id integer no Corridor.
doc tsvector yes Full-text vector over caption, labels, and transcribed text. GIN-indexed; queried with websearch syntax.
tags int4[] no Term ids as an integer array, GIN-indexed for containment queries.
These constraint definitions are read from pg_constraint verbatim. They are the authority on allowed values — if this page and a written specification ever disagree, the constraint is right.
Coordinates & bearings

Nothing is ever asked for a direction.

This is the part of the record most worth understanding before you build on it. Reading a panorama and locating something in it are two different jobs, and they are done by two different things. The reading pass identifies pixels. Deterministic code converts pixels into angles. A compass bearing is never estimated, requested, or returned by a reading pass — it is computed, and it is reproducible from the stored inputs.

What a reading pass returns

For every renderable observation, exactly this, and nothing directional:

{
  "source_image_index": 2,
  "face": "RIGHT",
  "bbox_center": { "x": 0.80, "y": 0.55 },
  "grounding_confidence": 0.96
}

Face and index mapping

Stored face codes, and the one-based image index each maps to. Read from the converter's own constant:

1  ·  f  ·  FRONT 2  ·  r  ·  RIGHT 3  ·  b  ·  BACK 4  ·  l  ·  LEFT 5  ·  u  ·  UP (no bearing) 6  ·  d  ·  DOWN (no bearing)

Only the four horizontal faces can carry a panorama marker. A point on the zenith or nadir face has no meaningful compass direction, so the converter refuses to produce one rather than inventing a plausible number. Observations on those faces can still exist as context; they simply never become located markers.

The conversion

Normalise the anchor into face-local coordinates, project onto the unit cube, then take the angles. One shared implementation serves every lens; a lens may not carry its own copy of this arithmetic.

// face-local, from the normalised anchor
u = 2x - 1        // left −1 … right +1
v = 1 - 2y        // top  +1 … bottom −1   (y is measured DOWN)

// direction vector, per horizontal face
FRONT  ( 1, v,  u)        RIGHT  (-u, v,  1)
BACK   (-1, v, -u)        LEFT   ( u, v, -1)

// angles
pano_ath_deg = atan2(z, x)                     // panorama-relative azimuth, 0–360
elev_deg     = atan2(v, sqrt(x² + z²))         // +up / −down from the horizon

// absolute compass bearing, computed at read time
bearing_deg  = normalize(panorama_front_bearing + pano_ath_deg)
Why pano_ath_deg is the stored value, and not the bearing. The panorama-relative azimuth is immutable pixel geometry: it depends only on which pixel the object occupies. The absolute bearing additionally depends on the corridor's calibrated panorama heading, which can be corrected later. Storing the relative angle and combining it at read time means a heading correction re-aims every observation in that corridor automatically, without rewriting a single observation row. If bearings were baked in, a heading fix would require a full re-read — and any human correction made in the meantime would be at risk.

Worked examples

Computed by calling the shipping converter while this page was rendered, so they cannot drift from it. Values are panorama-relative; add the corridor's calibrated front bearing for an absolute compass direction.

Face x y pano_ath_deg elev_deg Reading
f · FRONT 0.50 0.50 0.000 0.000 Centre of the FRONT face
f · FRONT 0.00 0.50 315.000 0.000 Left edge of FRONT
f · FRONT 1.00 0.50 45.000 0.000 Right edge of FRONT
f · FRONT 0.50 0.00 0.000 45.000 Top edge of FRONT
f · FRONT 0.50 1.00 0.000 -45.000 Bottom edge of FRONT
r · RIGHT 0.50 0.50 90.000 0.000 Centre of the RIGHT face
b · BACK 0.50 0.50 180.000 0.000 Centre of the BACK face
l · LEFT 0.50 0.50 270.000 0.000 Centre of the LEFT face
The case this design exists for. A roadside sign visible on the RIGHT face at x = 0.80, y = 0.53, in a panorama whose calibrated front bearing is 137.6°, converts to 120.964° relative and 258.564° absolute. An earlier generation of the record asked for a bearing directly and placed the same sign on the BACK face near 320° — visibly wrong, in the right-looking format. That regression is pinned as a test, and the numbers above are recomputed here every time this page loads.
Reliability tiers

Five rungs, and most of the record never gets drawn.

Every observation carries a grounding tier, and the tier travels with it through the API. An observation is placed as a precise marker only if its geometry holds up. Everything below that bar is kept, stays queryable, and stays reviewable — it is simply never presented as located. The counts are live.

Tier Condition Rendering Rows now
verified A reviewer clicked the object in the source pixels. Grounding source is recorded as manual. Placed as a precise marker. 0
reliable Valid face, index, and anchor, with grounding confidence at or above 0.75. Placed as a precise marker. 0
approximate Valid geometry, grounding confidence from 0.55 up to but not including 0.75. Retained for review. Not drawn as a precise marker, and not delivered as located. 0
unreliable Missing or invalid geometry, a face/index mismatch, or grounding confidence below 0.55. Retained for review. Not drawn. 0
legacy A pre-grounding row whose direction was estimated rather than computed from pixels. Labelled legacy and left labelled. Never silently reclassified upward. 50,658
Treat legacy as unlocated. Those rows predate pixel grounding; their direction was estimated, and relabelling them would be the one change that could quietly turn an honest record into a misleading one. They are being replaced by re-reads corridor by corridor, and until a row is re-read it keeps saying so.
Right now, every object observation you can reach publicly is legacy. The ladder above is live and enforced, but the corridors read under the current grounding contract are client corridors that are not public yet, and the public corpus was read before it existed. So: the tiers are real, the thresholds are real, and today the public read endpoints will hand you estimated directions, labelled as such, on every observation. Do not build a bearing-dependent integration against the public corpus in its current state. Ask us which corridors have been re-read — that is a question with a specific answer, not a roadmap.
Sign text

Clear is a fact. Partial is a guess, and stays labelled one.

Text read off signs, markers, gauge plates, and regulatory postings is stored with a legibility flag on every row. The distinction is preserved rather than smoothed over, because the two are not the same kind of evidence.

legibility = clear

Legible in the imagery

The text was readable at capture resolution. Treat it as a transcription of what the sign says. 1,440 rows.

legibility = partial

Only half-readable

The sign was too small, too oblique, too distant, or too degraded to read fully. The transcription is an unverified reading and is carried as one. 1,890 rows.

If what you are building is liability-sensitive, filter on this column. Closure notices, hazard warnings, regulatory postings, and permit conditions are exactly the text that tends to be small and weathered — which is exactly the text most likely to come back partial. A partial transcription is evidence that a sign exists and roughly what it concerns; it is not evidence of what it says. There is also a separate verified boolean, set only once a person has confirmed a transcription against the imagery. For anything that has to survive review, require both: legibility = 'clear' and verified = true, and go and look at the panorama.
Vocabulary

The type vocabulary is observed, not declared.

There is no fixed enumeration of object types. The vocabulary is whatever has actually been read out of captured corridors, which means it grows as coverage grows and as new corridor kinds are captured. Below are the most common types on record right now, out of 28 in use. Query /api/scene-intel/facets for the current list rather than hardcoding one.

other17,463 structure8,221 powerline8,187 vehicle5,924 sign5,311 building3,316 person695 bridge465 rock-formation370 vegetation220 boat154 railroad148 road75 animal73

Tag terms are a separate, larger free vocabulary over the same scenes — 54,828 distinct terms are in the dictionary today. The facets endpoint returns the top terms by count for whatever area you scope it to.

Lens themes

A theme is readable only when its adapter ships.

A lens is a named, versioned interpretation layered over the same universal scene record. A lens may join its own assessment record; it may never rewrite universal entities, text, tags, or captions. The table is generated from the server-side theme catalog when this page is served, so a theme cannot appear here as available before it is.

Theme URL key Table id Scopes Schema / prompt Public read
Scene Intelligence default default scene 2 / — served
RAPG Access Sites rapg access scene, trail, site, collection 2 / 1.3 served
NPS Visual Resource nps-vri nps-vri scene, trail, corridor, collection — / — 404 — adapter_required
MS4 Stream Assessment ms4 ms4 scene, trail, corridor, collection — / — 404 — adapter_required
2 of 4 themes are readable. NPS Visual Resource and MS4 Stream Assessment are declared names with no runtime adapter; requesting either from the theme endpoint returns 404. They are listed because a name in a catalog is not a capability, and you should be able to tell the difference from outside the system. An unknown or unavailable theme name never silently falls back to a different protocol's data. Version the assumption, not the date: compare schema_version before parsing a payload.
Read API

Five anonymous GET endpoints.

No key, no account, no registration. Cross-origin requests are permitted, so these can be called directly from a browser client. Responses are JSON. Requests are limited to 120 per minute per address; exceeding that returns 429 with a Retry-After header. Send a User-Agent that identifies your organisation — clients presenting generic scripted-library user agents are additionally capped and will start receiving 403 with a contact address. If you need sustained bulk access, ask; it is a conversation, not a scraping problem.

The standing privacy guarantee. Every one of these endpoints requires that the panorama's corridor is public and not soft-deleted. Where it is not, the response is an ordinary 404 — the same 404 you get for an id that does not exist. That is deliberate: an enumerable integer id must not be able to confirm the existence, extent, contents, or tag counts of a private or client corridor. Facet counts are filtered by the same rule, so they cannot be used to infer a private corpus either. Do not read a 404 as "not yet processed"; it also means "not yours to see", and the two are indistinguishable by design.

GET/api/scene-intel/scene/{id}

The full record for one panorama, plus gazetteer landmark cards for named places it can see. {id} is a panorama id, digits only.

{
  "scene_id":      1533202,
  "trail_id":      1459,
  "tier":          "full",        // "full" | "lite" | "gnis"
  "caption":       "…",
  "scenic":        3,
  "season":        "summer",
  "water_kind":    "river",
  "trail_surface": "gravel",
  "people_count":  0,
  "escalated":     false,
  "tags":     [ "…" ],
  "entities": [ {
      "type": "sign", "label": "…", "face": "r",
      "source_image_index": 2,
      "anchor_x": 0.82, "anchor_y": 0.53,
      "pano_ath_deg": 122.619,     // panorama-relative, immutable
      "bearing_deg":  260.219,     // computed per request from the current heading
      "elev_deg":     -1.2,
      "dist_m": 14, "condition": "…", "confidence": 0.9,
      "grounding_quality":    "reliable",
      "grounding_source":     "ai", // "ai" | "manual" | "legacy"
      "grounding_confidence": 0.96
  } ],
  "texts":     [ { "text": "…", "object": "sign",
                   "legibility": "clear", "verified": false } ],
  "landmarks": [ { "name": "…", "class": "Stream", "dist_m": 325,
                   "bearing": 96.4, "vision_seen": true,
                   "feature_id": 123456, "blurb": "…", "teaser": "…" } ]
}

Hidden observations are excluded. tier: "gnis" means the panorama has no reading pass behind it but does sit near named gazetteer features: you get the landmark cards and a caption synthesised from them, with every reading-derived field null. Check tier before assuming entities or texts will be populated. A panorama with neither a reading nor a landmark returns 404. Responses are cached server-side for an hour and invalidated on write, so a correction appears without waiting out the TTL.

GET/api/scene-intel/search

Search across the record. All parameters are optional and combine with AND.

ParamBehaviour
qFull-text query over caption, labels, and transcribed text. Supports quoted phrases and -exclusion. Results rank by relevance, then by panorama id so paging is stable.
tagsComma-separated terms. Containment, not union: a result must carry all of them. An unknown term yields an empty result set rather than being ignored.
typeRestrict to panoramas holding at least one visible observation of this object type.
bboxFour comma-separated degrees, minLon,minLat,maxLon,maxLat, matched against panorama geometry.
map_idScope to the public member corridors of one collection. Non-numeric input returns 422 rather than silently dropping the filter.
limitDefault 24, hard ceiling 100. Values above the ceiling are clamped, not rejected.
offsetZero-based. Negative values are treated as zero.
{
  "total": 128,                    // full match count, ignoring limit/offset
  "results": [ {
      "scene_id": 1533202, "trail_id": 1459,
      "trail": "…", "slug": "…", "scene": 12,
      "lat": 48.7712, "lon": -114.2831,
      "thumb": "https://…", "caption": "…", "tier": "full"
  } ]
}

GET/api/scene-intel/facets

The live vocabulary with counts: the most frequent tag terms and object types, each list capped. Accepts the same bbox parameter to scope counts to an area, in which case the counts describe exactly that box. Treat what it returns as the vocabulary — build your filter UI from this response rather than hardcoding an enumeration that will go stale as coverage grows.

{ "tags":  [ { "tag": "…",  "n": 4211 } ],
  "types": [ { "type": "sign", "n": 5359 } ] }
Response caching. Search and facet responses are cached server-side for a few minutes, keyed on the exact parameter set — the TTL is deliberately short because the corpus is actively being filled and a thin result must not be pinned as the answer. A per-scene payload is cached longer but is invalidated on write, so a reviewer's correction shows up immediately rather than waiting out the window. Cached entries hold public data only, by construction: every query behind them carries the public-corridor gate, so there is no key a private result could land in. New corridors land in overnight batches, so poll nightly rather than per-minute.

GET/api/lens/themes

Capability discovery. Pass an optional ?scene_id= to ask which themes have approved, public results for that specific panorama; a non-numeric value returns 422. Read available, not the presence of a row — every catalog theme is listed, including the ones with no adapter.

{ "themes": [ { "id": "access", "key": "rapg", "label": "…",
                "scopes": [ "scene", "trail", "site", "collection" ],
                "adapter_status": "active", "available": true } ] }

GET/api/lens/scene/{id}?theme=

The bounded render payload for one theme on one panorama. theme is required and accepts the URL key, the table id, or a documented legacy alias. Omitting it returns 422; asking for the universal record here returns 422 with a pointer to the scene endpoint. An unknown theme, a theme without a runtime adapter, a result that is not both approved and public, or a non-public corridor all return 404.

{
  "theme_id":       "access",
  "theme_key":      "rapg",
  "scene_id":       1533202,
  "schema_version": "2",
  "render":         { "markers": [ { "…": "…", "panoAth": 122.619,
                                     "bearing": 260.219 } ] },
  "analyzed_at":    "2026-07-29T14:02:11+00:00"
}

Bounded is load-bearing. The payload carries the reviewed render model only. Raw provider responses, unapproved recommendations, private sign text, reviewer identity, and account or authorisation data are excluded by construction, not by filtering at the edge. Marker bearings are recombined with the corridor's current heading on each read, exactly as in the universal payload.

Export

There is no self-serve bulk export. Read this before you plan around one.

The read endpoints above are the whole of the public surface. Scene Intelligence has no public GeoJSON, CSV, or PDF download, and no anonymous bulk dump. Being explicit about that is cheaper for everyone than letting an integration get designed around one.

The one bulk path

A staff-run command exports a complete, approved lens run as a single JSON document under the contract terrain360-lens-scene-export/v1. It refuses anything that is not both complete and approved, and it refuses a run whose scene count does not reconcile. The document carries theme and run provenance, exact panorama identity and location, schema version, and each bounded render payload — and deliberately excludes raw provider responses, private sign text, unapproved recommendations, account data, and authorisation data. It is produced per delivery, on request.

A different thing with a similar name

Public PDF, CSV, and GeoJSON exports do exist at /trail/{slug}/ai-analysis/export/…. They are real and they work, but they read an older, unrelated per-scene assessment table — not the scene record documented on this page. Do not treat their output as a Scene Intelligence export or expect the fields above to appear in it. The two record systems are not joined.

Integrating against a corridor and need something the endpoints do not give you — a scheduled extract, a specific projection, a join to your own asset ids? Say so. Those are delivery decisions made per corridor, and they are easier to get right at the start than to retrofit.

Integrating with this record?

Tell us the corridor, the system you are joining it to, and the identifiers you need to match on. If something on this page is wrong, ambiguous, or missing, that is worth knowing too — it is generated from the running system, so an error here is an error there.

Get in touch What Scene Intelligence is →

Schema, constraints, and counts on this page were read from the running system at 2026-07-30 20:45 UTC.