Skip to main content

Semantic Layer YAML Specification

Coming Soon

The Semantic Catalog is currently in development. This reference documents the planned YAML format. We'll update these docs when the feature launches.

Reference for the semantic layer YAML format.

Overview

Semantic layers are defined in YAML with three main sections:

models:
- name: model_name
table: schema.table_name
dimensions: [...]
measures: [...]

relationships:
- name: relationship_name
from: model_a
to: model_b
type: left
sql: "model_a.id = model_b.model_a_id"

Models

A model maps to a database table or view.

models:
- name: accounts
table: public.accounts
description: "Customer accounts"

dimensions:
- name: segment
type: string
sql: segment
description: "Account segment: Enterprise, Mid-Market, SMB"

- name: created_date
type: date
sql: created_at::date
description: "Account creation date"

measures:
- name: total_arr
type: sum
sql: arr
description: "Total annual recurring revenue"

Dimensions

Dimensions are attributes used to group or filter data.

PropertyRequiredDescription
nameYesUnique identifier
typeYesstring, number, date, datetime, boolean
sqlYesSQL expression
descriptionNoHuman-readable description
primary_keyNoSet true for primary key

Dimension Types

dimensions:
# String dimension
- name: status
type: string
sql: status

# Date dimension
- name: signup_date
type: date
sql: created_at::date

# Boolean dimension
- name: is_active
type: boolean
sql: "status = 'active'"

Measures

Measures are aggregated values.

PropertyRequiredDescription
nameYesUnique identifier
typeYescount, count_distinct, sum, avg, min, max, number
sqlYesSQL expression (column or formula)
descriptionNoHuman-readable description
filtersNoArray of filter conditions

Measure Types

measures:
# Count all rows
- name: total_accounts
type: count
sql: id

# Count distinct values
- name: unique_users
type: count_distinct
sql: user_id

# Sum a column
- name: total_revenue
type: sum
sql: amount

# Average
- name: avg_deal_size
type: average
sql: amount

# Custom formula
- name: conversion_rate
type: number
sql: "COUNT(CASE WHEN converted THEN 1 END)::float / NULLIF(COUNT(*), 0)"

Filtered Measures

Apply filters to restrict which rows are aggregated:

measures:
- name: active_arr
type: sum
sql: arr
filters:
- sql: "status = 'active'"

- name: enterprise_count
type: count
sql: id
filters:
- sql: "segment = 'Enterprise'"

Relationships

Define how models join together.

PropertyRequiredDescription
nameYesUnique identifier
fromYesSource model name
toYesTarget model name
typeYesinner, left, right, full
sqlYesJoin condition
relationships:
- name: account_users
from: accounts
to: users
type: left
sql: "accounts.id = users.account_id"

- name: user_events
from: users
to: events
type: left
sql: "users.id = events.user_id"

Complete Example

models:
- name: accounts
table: public.accounts
description: "Customer accounts"

dimensions:
- name: id
type: string
sql: id
primary_key: true
- name: segment
type: string
sql: segment
- name: status
type: string
sql: status
- name: created_date
type: date
sql: created_at::date

measures:
- name: count
type: count
sql: id
- name: total_arr
type: sum
sql: arr
- name: avg_arr
type: average
sql: arr

- name: users
table: public.users
description: "User accounts"

dimensions:
- name: id
type: string
sql: id
primary_key: true
- name: account_id
type: string
sql: account_id
- name: role
type: string
sql: role

measures:
- name: count
type: count
sql: id
- name: unique_accounts
type: count_distinct
sql: account_id

relationships:
- name: account_users
from: accounts
to: users
type: left
sql: "accounts.id = users.account_id"

Validation

The semantic layer validates:

  • Table and column existence
  • Type compatibility
  • Circular relationship detection
  • Unique names within a model

Validation errors appear when saving a draft or publishing a version.