---
title: "Update the draft policy version"
method: PUT
path: "/api/policy_version"
tags: ["Policy Versions"]
---

# Update the draft policy version

`PUT /api/policy_version`

## Request

- Base URL: `https://app.herondata.io`
- URL: `https://app.herondata.io/api/policy_version`
- Auth: API key in header `x-api-key`

Update the draft's policy_definition and/or change_description. Section names must be unique within the definition. Send each existing check's heron_id back: a check without one is saved as a new check with a new heron_id.

## Query parameters

- `user_id` integer

## Request body

- PolicyVersionUpdateSchema
  - `change_description` string, nullable
  - `policy_definition` PolicyDefinition
    - `policy_sections` PolicyVersionSection[], required
      - `branches` PolicyBranch[]: Ordered routes through the section; the section's own checks run on every route
        - `checks` Check[]
          - `attribute_description` string, nullable: What the attribute measures. Present only for accounts on policy versions
          - `attribute_display_name` string, nullable: The attribute's human-readable name. Present only for accounts on policy versions
          - `attribute_label` string, nullable
          - `attribute_unit` unknown
          - `attribute_validators` object[], nullable: The validity operators `attribute_label` offers, as in the catalogue's `check_options[].validators`, so a saved `is_valid` / `is_invalid` check can be worded. Empty for a check without an attribute or an attribute with no validity rule
          - `attribute_value_set` unknown
          - `boolean_check` BooleanCheck
            - `auto_decline` boolean
            - `decline_code` string, nullable: The CRM's identifier for this decline reason, e.g. a LendSaas reason id. Left unset, the CRM sync falls back to this check's decline_description.
            - `decline_description` string, nullable
            - `email_template_name` string, nullable
            - `ignore_metric_availability` boolean
            - `is_mandatory` boolean
            - `on_failure` 'fail' | 'review_required'
            - `on_missing` 'missing_data' | 'fail' | 'pass': What the check reports when it would report missing data: `missing_data` (the default), `fail` or `pass`. A check saved with an older flag (`pass_if_value_missing` on a date-delta check) reads as the setting it stands for. With `ignore_metric_availability` or `pass_if_value_missing` set, only that setting is accepted
            - `pass_description` string, nullable
            - `transaction_scope` TransactionScope
              - …
            - `value` boolean
          - `composite_check` CompositeCheck
            - `auto_decline` boolean
            - `checks` Check[]
            - `decline_code` string, nullable: The CRM's identifier for this decline reason, e.g. a LendSaas reason id. Left unset, the CRM sync falls back to this check's decline_description.
            - `decline_description` string, nullable
            - `email_template_name` string, nullable
            - `ignore_metric_availability` boolean
            - `is_mandatory` boolean
            - `max_failing` integer, nullable
            - `on_failure` 'fail' | 'review_required'
            - `on_missing` 'missing_data' | 'fail' | 'pass': What the check reports when it would report missing data: `missing_data` (the default), `fail` or `pass`. A check saved with an older flag (`pass_if_value_missing` on a date-delta check) reads as the setting it stands for. With `ignore_metric_availability` or `pass_if_value_missing` set, only that setting is accepted
            - `pass_description` string, nullable
            - `transaction_scope` TransactionScope
              - …
            - `type` 'AND' | 'OR' | 'AT_MOST_FAILING'
          - `date_check` DateCheck
            - `auto_decline` boolean
            - `decline_code` string, nullable: The CRM's identifier for this decline reason, e.g. a LendSaas reason id. Left unset, the CRM sync falls back to this check's decline_description.
            - `decline_description` string, nullable
            - `email_template_name` string, nullable
            - `ignore_metric_availability` boolean
            - `is_mandatory` boolean
            - `on_failure` 'fail' | 'review_required'
            - `on_missing` 'missing_data' | 'fail' | 'pass': What the check reports when it would report missing data: `missing_data` (the default), `fail` or `pass`. A check saved with an older flag (`pass_if_value_missing` on a date-delta check) reads as the setting it stands for. With `ignore_metric_availability` or `pass_if_value_missing` set, only that setting is accepted
            - `pass_description` string, nullable
            - `transaction_scope` TransactionScope
              - …
            - `type` 'equal' | 'not_equal' | 'before' | 'before_or_on' | 'after' | 'after_or_on'
            - `value` string, date, nullable
          - `date_delta_to_now_check` DateDeltaToNowCheck
            - `auto_decline` boolean
            - `decline_code` string, nullable: The CRM's identifier for this decline reason, e.g. a LendSaas reason id. Left unset, the CRM sync falls back to this check's decline_description.
            - `decline_description` string, nullable
            - `email_template_name` string, nullable
            - `ignore_metric_availability` boolean
            - `is_mandatory` boolean
            - `on_failure` 'fail' | 'review_required'
            - `on_missing` 'missing_data' | 'fail' | 'pass': What the check reports when it would report missing data: `missing_data` (the default), `fail` or `pass`. A check saved with an older flag (`pass_if_value_missing` on a date-delta check) reads as the setting it stands for. With `ignore_metric_availability` or `pass_if_value_missing` set, only that setting is accepted
            - `pass_description` string, nullable
            - `pass_if_value_missing` boolean
            - `transaction_scope` TransactionScope
              - …
            - `type` 'greater_than' | 'greater_than_or_equal' | 'less_than' | 'less_than_or_equal'
            - `value` object, nullable
          - `enhanced_sql_check` EnhancedSQLCheck
            - `auto_decline` boolean
            - `check_type` 'equal' | 'not_equal' | 'greater_than' | 'greater_than_or_equal' | 'less_than' | 'less_than_or_equal' | 'before' | 'before_or_on' | 'after' | 'after_or_on' | 'is_in' | 'is_not_in', required
            - `column_name` string, required
            - `comparison_value` unknown, required
            - `data_type` 'numeric' | 'date' | 'string', required
            - `decline_code` string, nullable: The CRM's identifier for this decline reason, e.g. a LendSaas reason id. Left unset, the CRM sync falls back to this check's decline_description.
            - `decline_description` string, nullable
            - `email_template_name` string, nullable
            - `ignore_metric_availability` boolean
            - `is_mandatory` boolean
            - `on_failure` 'fail' | 'review_required'
            - `on_missing` 'missing_data' | 'fail' | 'pass': What the check reports when it would report missing data: `missing_data` (the default), `fail` or `pass`. A check saved with an older flag (`pass_if_value_missing` on a date-delta check) reads as the setting it stands for. With `ignore_metric_availability` or `pass_if_value_missing` set, only that setting is accepted
            - `pass_description` string, nullable
            - `query_name` string, required
            - `transaction_scope` TransactionScope
              - …
          - `group` string, nullable
          - `heron_id` string, nullable: Stable across edits; omit for a new check and one is minted. Policy versions only
          - `identity` string, nullable: Stable kind:key identity used to match stored check evaluations
          - `name` string, nullable
          - `numeric_check` NumericCheck
            - `auto_decline` boolean
            - `decline_code` string, nullable: The CRM's identifier for this decline reason, e.g. a LendSaas reason id. Left unset, the CRM sync falls back to this check's decline_description.
            - `decline_description` string, nullable
            - `email_template_name` string, nullable
            - `ignore_metric_availability` boolean
            - `is_mandatory` boolean
            - `on_failure` 'fail' | 'review_required'
            - `on_missing` 'missing_data' | 'fail' | 'pass': What the check reports when it would report missing data: `missing_data` (the default), `fail` or `pass`. A check saved with an older flag (`pass_if_value_missing` on a date-delta check) reads as the setting it stands for. With `ignore_metric_availability` or `pass_if_value_missing` set, only that setting is accepted
            - `pass_description` string, nullable
            - `transaction_scope` TransactionScope
              - …
            - `type` 'equal' | 'not_equal' | 'greater_than' | 'greater_than_or_equal' | 'less_than' | 'less_than_or_equal'
            - `value` union: The threshold: a number as a string, {"variable": {...}} to compare with another variable (with an optional "factor" that scales it), or {"lookup": {"table_heron_id", "column_id"}} to read it from a lookup table column
              - …
          - `parameters` object, nullable
          - `sql_check` SQLCheck
            - `auto_decline` boolean
            - `column_name` string, required
            - `decline_code` string, nullable: The CRM's identifier for this decline reason, e.g. a LendSaas reason id. Left unset, the CRM sync falls back to this check's decline_description.
            - `decline_description` string, nullable
            - `email_template_name` string, nullable
            - `ignore_metric_availability` boolean
            - `is_mandatory` boolean
            - `on_failure` 'fail' | 'review_required'
            - `on_missing` 'missing_data' | 'fail' | 'pass': What the check reports when it would report missing data: `missing_data` (the default), `fail` or `pass`. A check saved with an older flag (`pass_if_value_missing` on a date-delta check) reads as the setting it stands for. With `ignore_metric_availability` or `pass_if_value_missing` set, only that setting is accepted
            - `pass_description` string, nullable
            - `query_name` string, required
            - `transaction_scope` TransactionScope
              - …
          - `string_check` StringCheck
            - `auto_decline` boolean
            - `decline_code` string, nullable: The CRM's identifier for this decline reason, e.g. a LendSaas reason id. Left unset, the CRM sync falls back to this check's decline_description.
            - `decline_description` string, nullable
            - `email_template_name` string, nullable
            - `ignore_metric_availability` boolean
            - `is_mandatory` boolean
            - `match_count` integer, nullable
            - `on_failure` 'fail' | 'review_required'
            - `on_missing` 'missing_data' | 'fail' | 'pass': What the check reports when it would report missing data: `missing_data` (the default), `fail` or `pass`. A check saved with an older flag (`pass_if_value_missing` on a date-delta check) reads as the setting it stands for. With `ignore_metric_availability` or `pass_if_value_missing` set, only that setting is accepted
            - `pass_description` string, nullable
            - `transaction_scope` TransactionScope
              - …
            - `type` 'equal' | 'not_equal' | 'starts_with' | 'starts_with_any_of' | 'does_not_start_with_any_of' | 'contains' | 'does_not_start_with' | 'does_not_contain' | 'is_in' | 'is_not_in' | 'has_none_of' | 'has_any_of' | 'has_only' | 'has_fewer_than_n_matches' | 'has_more_than_n_matches' | 'is_valid' | 'is_invalid'
            - `value` union: The value as a string, or {"lookup": {"table_heron_id"}} for is_in, is_not_in, has_any_of, has_none_of or has_only to read the list from a lookup table's rows
              - …
        - `condition` Check, required
          - `attribute_description` string, nullable: What the attribute measures. Present only for accounts on policy versions
          - `attribute_display_name` string, nullable: The attribute's human-readable name. Present only for accounts on policy versions
          - `attribute_label` string, nullable
          - `attribute_unit` unknown
          - `attribute_validators` object[], nullable: The validity operators `attribute_label` offers, as in the catalogue's `check_options[].validators`, so a saved `is_valid` / `is_invalid` check can be worded. Empty for a check without an attribute or an attribute with no validity rule
          - `attribute_value_set` unknown
          - `boolean_check` BooleanCheck
            - `auto_decline` boolean
            - `decline_code` string, nullable: The CRM's identifier for this decline reason, e.g. a LendSaas reason id. Left unset, the CRM sync falls back to this check's decline_description.
            - `decline_description` string, nullable
            - `email_template_name` string, nullable
            - `ignore_metric_availability` boolean
            - `is_mandatory` boolean
            - `on_failure` 'fail' | 'review_required'
            - `on_missing` 'missing_data' | 'fail' | 'pass': What the check reports when it would report missing data: `missing_data` (the default), `fail` or `pass`. A check saved with an older flag (`pass_if_value_missing` on a date-delta check) reads as the setting it stands for. With `ignore_metric_availability` or `pass_if_value_missing` set, only that setting is accepted
            - `pass_description` string, nullable
            - `transaction_scope` TransactionScope
              - …
            - `value` boolean
          - `composite_check` CompositeCheck
            - `auto_decline` boolean
            - `checks` Check[]
            - `decline_code` string, nullable: The CRM's identifier for this decline reason, e.g. a LendSaas reason id. Left unset, the CRM sync falls back to this check's decline_description.
            - `decline_description` string, nullable
            - `email_template_name` string, nullable
            - `ignore_metric_availability` boolean
            - `is_mandatory` boolean
            - `max_failing` integer, nullable
            - `on_failure` 'fail' | 'review_required'
            - `on_missing` 'missing_data' | 'fail' | 'pass': What the check reports when it would report missing data: `missing_data` (the default), `fail` or `pass`. A check saved with an older flag (`pass_if_value_missing` on a date-delta check) reads as the setting it stands for. With `ignore_metric_availability` or `pass_if_value_missing` set, only that setting is accepted
            - `pass_description` string, nullable
            - `transaction_scope` TransactionScope
              - …
            - `type` 'AND' | 'OR' | 'AT_MOST_FAILING'
          - `date_check` DateCheck
            - `auto_decline` boolean
            - `decline_code` string, nullable: The CRM's identifier for this decline reason, e.g. a LendSaas reason id. Left unset, the CRM sync falls back to this check's decline_description.
            - `decline_description` string, nullable
            - `email_template_name` string, nullable
            - `ignore_metric_availability` boolean
            - `is_mandatory` boolean
            - `on_failure` 'fail' | 'review_required'
            - `on_missing` 'missing_data' | 'fail' | 'pass': What the check reports when it would report missing data: `missing_data` (the default), `fail` or `pass`. A check saved with an older flag (`pass_if_value_missing` on a date-delta check) reads as the setting it stands for. With `ignore_metric_availability` or `pass_if_value_missing` set, only that setting is accepted
            - `pass_description` string, nullable
            - `transaction_scope` TransactionScope
              - …
            - `type` 'equal' | 'not_equal' | 'before' | 'before_or_on' | 'after' | 'after_or_on'
            - `value` string, date, nullable
          - `date_delta_to_now_check` DateDeltaToNowCheck
            - `auto_decline` boolean
            - `decline_code` string, nullable: The CRM's identifier for this decline reason, e.g. a LendSaas reason id. Left unset, the CRM sync falls back to this check's decline_description.
            - `decline_description` string, nullable
            - `email_template_name` string, nullable
            - `ignore_metric_availability` boolean
            - `is_mandatory` boolean
            - `on_failure` 'fail' | 'review_required'
            - `on_missing` 'missing_data' | 'fail' | 'pass': What the check reports when it would report missing data: `missing_data` (the default), `fail` or `pass`. A check saved with an older flag (`pass_if_value_missing` on a date-delta check) reads as the setting it stands for. With `ignore_metric_availability` or `pass_if_value_missing` set, only that setting is accepted
            - `pass_description` string, nullable
            - `pass_if_value_missing` boolean
            - `transaction_scope` TransactionScope
              - …
            - `type` 'greater_than' | 'greater_than_or_equal' | 'less_than' | 'less_than_or_equal'
            - `value` object, nullable
          - `enhanced_sql_check` EnhancedSQLCheck
            - `auto_decline` boolean
            - `check_type` 'equal' | 'not_equal' | 'greater_than' | 'greater_than_or_equal' | 'less_than' | 'less_than_or_equal' | 'before' | 'before_or_on' | 'after' | 'after_or_on' | 'is_in' | 'is_not_in', required
            - `column_name` string, required
            - `comparison_value` unknown, required
            - `data_type` 'numeric' | 'date' | 'string', required
            - `decline_code` string, nullable: The CRM's identifier for this decline reason, e.g. a LendSaas reason id. Left unset, the CRM sync falls back to this check's decline_description.
            - `decline_description` string, nullable
            - `email_template_name` string, nullable
            - `ignore_metric_availability` boolean
            - `is_mandatory` boolean
            - `on_failure` 'fail' | 'review_required'
            - `on_missing` 'missing_data' | 'fail' | 'pass': What the check reports when it would report missing data: `missing_data` (the default), `fail` or `pass`. A check saved with an older flag (`pass_if_value_missing` on a date-delta check) reads as the setting it stands for. With `ignore_metric_availability` or `pass_if_value_missing` set, only that setting is accepted
            - `pass_description` string, nullable
            - `query_name` string, required
            - `transaction_scope` TransactionScope
              - …
          - `group` string, nullable
          - `heron_id` string, nullable: Stable across edits; omit for a new check and one is minted. Policy versions only
          - `identity` string, nullable: Stable kind:key identity used to match stored check evaluations
          - `name` string, nullable
          - `numeric_check` NumericCheck
            - `auto_decline` boolean
            - `decline_code` string, nullable: The CRM's identifier for this decline reason, e.g. a LendSaas reason id. Left unset, the CRM sync falls back to this check's decline_description.
            - `decline_description` string, nullable
            - `email_template_name` string, nullable
            - `ignore_metric_availability` boolean
            - `is_mandatory` boolean
            - `on_failure` 'fail' | 'review_required'
            - `on_missing` 'missing_data' | 'fail' | 'pass': What the check reports when it would report missing data: `missing_data` (the default), `fail` or `pass`. A check saved with an older flag (`pass_if_value_missing` on a date-delta check) reads as the setting it stands for. With `ignore_metric_availability` or `pass_if_value_missing` set, only that setting is accepted
            - `pass_description` string, nullable
            - `transaction_scope` TransactionScope
              - …
            - `type` 'equal' | 'not_equal' | 'greater_than' | 'greater_than_or_equal' | 'less_than' | 'less_than_or_equal'
            - `value` union: The threshold: a number as a string, {"variable": {...}} to compare with another variable (with an optional "factor" that scales it), or {"lookup": {"table_heron_id", "column_id"}} to read it from a lookup table column
              - …
          - `parameters` object, nullable
          - `sql_check` SQLCheck
            - `auto_decline` boolean
            - `column_name` string, required
            - `decline_code` string, nullable: The CRM's identifier for this decline reason, e.g. a LendSaas reason id. Left unset, the CRM sync falls back to this check's decline_description.
            - `decline_description` string, nullable
            - `email_template_name` string, nullable
            - `ignore_metric_availability` boolean
            - `is_mandatory` boolean
            - `on_failure` 'fail' | 'review_required'
            - `on_missing` 'missing_data' | 'fail' | 'pass': What the check reports when it would report missing data: `missing_data` (the default), `fail` or `pass`. A check saved with an older flag (`pass_if_value_missing` on a date-delta check) reads as the setting it stands for. With `ignore_metric_availability` or `pass_if_value_missing` set, only that setting is accepted
            - `pass_description` string, nullable
            - `query_name` string, required
            - `transaction_scope` TransactionScope
              - …
          - `string_check` StringCheck
            - `auto_decline` boolean
            - `decline_code` string, nullable: The CRM's identifier for this decline reason, e.g. a LendSaas reason id. Left unset, the CRM sync falls back to this check's decline_description.
            - `decline_description` string, nullable
            - `email_template_name` string, nullable
            - `ignore_metric_availability` boolean
            - `is_mandatory` boolean
            - `match_count` integer, nullable
            - `on_failure` 'fail' | 'review_required'
            - `on_missing` 'missing_data' | 'fail' | 'pass': What the check reports when it would report missing data: `missing_data` (the default), `fail` or `pass`. A check saved with an older flag (`pass_if_value_missing` on a date-delta check) reads as the setting it stands for. With `ignore_metric_availability` or `pass_if_value_missing` set, only that setting is accepted
            - `pass_description` string, nullable
            - `transaction_scope` TransactionScope
              - …
            - `type` 'equal' | 'not_equal' | 'starts_with' | 'starts_with_any_of' | 'does_not_start_with_any_of' | 'contains' | 'does_not_start_with' | 'does_not_contain' | 'is_in' | 'is_not_in' | 'has_none_of' | 'has_any_of' | 'has_only' | 'has_fewer_than_n_matches' | 'has_more_than_n_matches' | 'is_valid' | 'is_invalid'
            - `value` union: The value as a string, or {"lookup": {"table_heron_id"}} for is_in, is_not_in, has_any_of, has_none_of or has_only to read the list from a lookup table's rows
              - …
        - `heron_id` string, nullable: Stable across renames; omit for a new branch and one is minted
        - `name` string, required
      - `checks` Check[]
        - `attribute_description` string, nullable: What the attribute measures. Present only for accounts on policy versions
        - `attribute_display_name` string, nullable: The attribute's human-readable name. Present only for accounts on policy versions
        - `attribute_label` string, nullable
        - `attribute_unit` unknown
        - `attribute_validators` object[], nullable: The validity operators `attribute_label` offers, as in the catalogue's `check_options[].validators`, so a saved `is_valid` / `is_invalid` check can be worded. Empty for a check without an attribute or an attribute with no validity rule
        - `attribute_value_set` unknown
        - `boolean_check` BooleanCheck
          - `auto_decline` boolean
          - `decline_code` string, nullable: The CRM's identifier for this decline reason, e.g. a LendSaas reason id. Left unset, the CRM sync falls back to this check's decline_description.
          - `decline_description` string, nullable
          - `email_template_name` string, nullable
          - `ignore_metric_availability` boolean
          - `is_mandatory` boolean
          - `on_failure` 'fail' | 'review_required'
          - `on_missing` 'missing_data' | 'fail' | 'pass': What the check reports when it would report missing data: `missing_data` (the default), `fail` or `pass`. A check saved with an older flag (`pass_if_value_missing` on a date-delta check) reads as the setting it stands for. With `ignore_metric_availability` or `pass_if_value_missing` set, only that setting is accepted
          - `pass_description` string, nullable
          - `transaction_scope` TransactionScope
            - `file_classes` string[], nullable
            - `min_reconciliation_status` 'failed' | 'not_possible' | 'reconciled' | 'null', nullable
          - `value` boolean
        - `composite_check` CompositeCheck
          - `auto_decline` boolean
          - `checks` Check[]
          - `decline_code` string, nullable: The CRM's identifier for this decline reason, e.g. a LendSaas reason id. Left unset, the CRM sync falls back to this check's decline_description.
          - `decline_description` string, nullable
          - `email_template_name` string, nullable
          - `ignore_metric_availability` boolean
          - `is_mandatory` boolean
          - `max_failing` integer, nullable
          - `on_failure` 'fail' | 'review_required'
          - `on_missing` 'missing_data' | 'fail' | 'pass': What the check reports when it would report missing data: `missing_data` (the default), `fail` or `pass`. A check saved with an older flag (`pass_if_value_missing` on a date-delta check) reads as the setting it stands for. With `ignore_metric_availability` or `pass_if_value_missing` set, only that setting is accepted
          - `pass_description` string, nullable
          - `transaction_scope` TransactionScope
            - `file_classes` string[], nullable
            - `min_reconciliation_status` 'failed' | 'not_possible' | 'reconciled' | 'null', nullable
          - `type` 'AND' | 'OR' | 'AT_MOST_FAILING'
        - `date_check` DateCheck
          - `auto_decline` boolean
          - `decline_code` string, nullable: The CRM's identifier for this decline reason, e.g. a LendSaas reason id. Left unset, the CRM sync falls back to this check's decline_description.
          - `decline_description` string, nullable
          - `email_template_name` string, nullable
          - `ignore_metric_availability` boolean
          - `is_mandatory` boolean
          - `on_failure` 'fail' | 'review_required'
          - `on_missing` 'missing_data' | 'fail' | 'pass': What the check reports when it would report missing data: `missing_data` (the default), `fail` or `pass`. A check saved with an older flag (`pass_if_value_missing` on a date-delta check) reads as the setting it stands for. With `ignore_metric_availability` or `pass_if_value_missing` set, only that setting is accepted
          - `pass_description` string, nullable
          - `transaction_scope` TransactionScope
            - `file_classes` string[], nullable
            - `min_reconciliation_status` 'failed' | 'not_possible' | 'reconciled' | 'null', nullable
          - `type` 'equal' | 'not_equal' | 'before' | 'before_or_on' | 'after' | 'after_or_on'
          - `value` string, date, nullable
        - `date_delta_to_now_check` DateDeltaToNowCheck
          - `auto_decline` boolean
          - `decline_code` string, nullable: The CRM's identifier for this decline reason, e.g. a LendSaas reason id. Left unset, the CRM sync falls back to this check's decline_description.
          - `decline_description` string, nullable
          - `email_template_name` string, nullable
          - `ignore_metric_availability` boolean
          - `is_mandatory` boolean
          - `on_failure` 'fail' | 'review_required'
          - `on_missing` 'missing_data' | 'fail' | 'pass': What the check reports when it would report missing data: `missing_data` (the default), `fail` or `pass`. A check saved with an older flag (`pass_if_value_missing` on a date-delta check) reads as the setting it stands for. With `ignore_metric_availability` or `pass_if_value_missing` set, only that setting is accepted
          - `pass_description` string, nullable
          - `pass_if_value_missing` boolean
          - `transaction_scope` TransactionScope
            - `file_classes` string[], nullable
            - `min_reconciliation_status` 'failed' | 'not_possible' | 'reconciled' | 'null', nullable
          - `type` 'greater_than' | 'greater_than_or_equal' | 'less_than' | 'less_than_or_equal'
          - `value` object, nullable
        - `enhanced_sql_check` EnhancedSQLCheck
          - `auto_decline` boolean
          - `check_type` 'equal' | 'not_equal' | 'greater_than' | 'greater_than_or_equal' | 'less_than' | 'less_than_or_equal' | 'before' | 'before_or_on' | 'after' | 'after_or_on' | 'is_in' | 'is_not_in', required
          - `column_name` string, required
          - `comparison_value` unknown, required
          - `data_type` 'numeric' | 'date' | 'string', required
          - `decline_code` string, nullable: The CRM's identifier for this decline reason, e.g. a LendSaas reason id. Left unset, the CRM sync falls back to this check's decline_description.
          - `decline_description` string, nullable
          - `email_template_name` string, nullable
          - `ignore_metric_availability` boolean
          - `is_mandatory` boolean
          - `on_failure` 'fail' | 'review_required'
          - `on_missing` 'missing_data' | 'fail' | 'pass': What the check reports when it would report missing data: `missing_data` (the default), `fail` or `pass`. A check saved with an older flag (`pass_if_value_missing` on a date-delta check) reads as the setting it stands for. With `ignore_metric_availability` or `pass_if_value_missing` set, only that setting is accepted
          - `pass_description` string, nullable
          - `query_name` string, required
          - `transaction_scope` TransactionScope
            - `file_classes` string[], nullable
            - `min_reconciliation_status` 'failed' | 'not_possible' | 'reconciled' | 'null', nullable
        - `group` string, nullable
        - `heron_id` string, nullable: Stable across edits; omit for a new check and one is minted. Policy versions only
        - `identity` string, nullable: Stable kind:key identity used to match stored check evaluations
        - `name` string, nullable
        - `numeric_check` NumericCheck
          - `auto_decline` boolean
          - `decline_code` string, nullable: The CRM's identifier for this decline reason, e.g. a LendSaas reason id. Left unset, the CRM sync falls back to this check's decline_description.
          - `decline_description` string, nullable
          - `email_template_name` string, nullable
          - `ignore_metric_availability` boolean
          - `is_mandatory` boolean
          - `on_failure` 'fail' | 'review_required'
          - `on_missing` 'missing_data' | 'fail' | 'pass': What the check reports when it would report missing data: `missing_data` (the default), `fail` or `pass`. A check saved with an older flag (`pass_if_value_missing` on a date-delta check) reads as the setting it stands for. With `ignore_metric_availability` or `pass_if_value_missing` set, only that setting is accepted
          - `pass_description` string, nullable
          - `transaction_scope` TransactionScope
            - `file_classes` string[], nullable
            - `min_reconciliation_status` 'failed' | 'not_possible' | 'reconciled' | 'null', nullable
          - `type` 'equal' | 'not_equal' | 'greater_than' | 'greater_than_or_equal' | 'less_than' | 'less_than_or_equal'
          - `value` union: The threshold: a number as a string, {"variable": {...}} to compare with another variable (with an optional "factor" that scales it), or {"lookup": {"table_heron_id", "column_id"}} to read it from a lookup table column
            - string
            - VariableThreshold
              - …
        - `parameters` object, nullable
        - `sql_check` SQLCheck
          - `auto_decline` boolean
          - `column_name` string, required
          - `decline_code` string, nullable: The CRM's identifier for this decline reason, e.g. a LendSaas reason id. Left unset, the CRM sync falls back to this check's decline_description.
          - `decline_description` string, nullable
          - `email_template_name` string, nullable
          - `ignore_metric_availability` boolean
          - `is_mandatory` boolean
          - `on_failure` 'fail' | 'review_required'
          - `on_missing` 'missing_data' | 'fail' | 'pass': What the check reports when it would report missing data: `missing_data` (the default), `fail` or `pass`. A check saved with an older flag (`pass_if_value_missing` on a date-delta check) reads as the setting it stands for. With `ignore_metric_availability` or `pass_if_value_missing` set, only that setting is accepted
          - `pass_description` string, nullable
          - `query_name` string, required
          - `transaction_scope` TransactionScope
            - `file_classes` string[], nullable
            - `min_reconciliation_status` 'failed' | 'not_possible' | 'reconciled' | 'null', nullable
        - `string_check` StringCheck
          - `auto_decline` boolean
          - `decline_code` string, nullable: The CRM's identifier for this decline reason, e.g. a LendSaas reason id. Left unset, the CRM sync falls back to this check's decline_description.
          - `decline_description` string, nullable
          - `email_template_name` string, nullable
          - `ignore_metric_availability` boolean
          - `is_mandatory` boolean
          - `match_count` integer, nullable
          - `on_failure` 'fail' | 'review_required'
          - `on_missing` 'missing_data' | 'fail' | 'pass': What the check reports when it would report missing data: `missing_data` (the default), `fail` or `pass`. A check saved with an older flag (`pass_if_value_missing` on a date-delta check) reads as the setting it stands for. With `ignore_metric_availability` or `pass_if_value_missing` set, only that setting is accepted
          - `pass_description` string, nullable
          - `transaction_scope` TransactionScope
            - `file_classes` string[], nullable
            - `min_reconciliation_status` 'failed' | 'not_possible' | 'reconciled' | 'null', nullable
          - `type` 'equal' | 'not_equal' | 'starts_with' | 'starts_with_any_of' | 'does_not_start_with_any_of' | 'contains' | 'does_not_start_with' | 'does_not_contain' | 'is_in' | 'is_not_in' | 'has_none_of' | 'has_any_of' | 'has_only' | 'has_fewer_than_n_matches' | 'has_more_than_n_matches' | 'is_valid' | 'is_invalid'
          - `value` union: The value as a string, or {"lookup": {"table_heron_id"}} for is_in, is_not_in, has_any_of, has_none_of or has_only to read the list from a lookup table's rows
            - string
            - TableList
              - …
      - `default_branch` DefaultPolicyBranch
        - `checks` Check[]
          - `attribute_description` string, nullable: What the attribute measures. Present only for accounts on policy versions
          - `attribute_display_name` string, nullable: The attribute's human-readable name. Present only for accounts on policy versions
          - `attribute_label` string, nullable
          - `attribute_unit` unknown
          - `attribute_validators` object[], nullable: The validity operators `attribute_label` offers, as in the catalogue's `check_options[].validators`, so a saved `is_valid` / `is_invalid` check can be worded. Empty for a check without an attribute or an attribute with no validity rule
          - `attribute_value_set` unknown
          - `boolean_check` BooleanCheck
            - `auto_decline` boolean
            - `decline_code` string, nullable: The CRM's identifier for this decline reason, e.g. a LendSaas reason id. Left unset, the CRM sync falls back to this check's decline_description.
            - `decline_description` string, nullable
            - `email_template_name` string, nullable
            - `ignore_metric_availability` boolean
            - `is_mandatory` boolean
            - `on_failure` 'fail' | 'review_required'
            - `on_missing` 'missing_data' | 'fail' | 'pass': What the check reports when it would report missing data: `missing_data` (the default), `fail` or `pass`. A check saved with an older flag (`pass_if_value_missing` on a date-delta check) reads as the setting it stands for. With `ignore_metric_availability` or `pass_if_value_missing` set, only that setting is accepted
            - `pass_description` string, nullable
            - `transaction_scope` TransactionScope
              - …
            - `value` boolean
          - `composite_check` CompositeCheck
            - `auto_decline` boolean
            - `checks` Check[]
            - `decline_code` string, nullable: The CRM's identifier for this decline reason, e.g. a LendSaas reason id. Left unset, the CRM sync falls back to this check's decline_description.
            - `decline_description` string, nullable
            - `email_template_name` string, nullable
            - `ignore_metric_availability` boolean
            - `is_mandatory` boolean
            - `max_failing` integer, nullable
            - `on_failure` 'fail' | 'review_required'
            - `on_missing` 'missing_data' | 'fail' | 'pass': What the check reports when it would report missing data: `missing_data` (the default), `fail` or `pass`. A check saved with an older flag (`pass_if_value_missing` on a date-delta check) reads as the setting it stands for. With `ignore_metric_availability` or `pass_if_value_missing` set, only that setting is accepted
            - `pass_description` string, nullable
            - `transaction_scope` TransactionScope
              - …
            - `type` 'AND' | 'OR' | 'AT_MOST_FAILING'
          - `date_check` DateCheck
            - `auto_decline` boolean
            - `decline_code` string, nullable: The CRM's identifier for this decline reason, e.g. a LendSaas reason id. Left unset, the CRM sync falls back to this check's decline_description.
            - `decline_description` string, nullable
            - `email_template_name` string, nullable
            - `ignore_metric_availability` boolean
            - `is_mandatory` boolean
            - `on_failure` 'fail' | 'review_required'
            - `on_missing` 'missing_data' | 'fail' | 'pass': What the check reports when it would report missing data: `missing_data` (the default), `fail` or `pass`. A check saved with an older flag (`pass_if_value_missing` on a date-delta check) reads as the setting it stands for. With `ignore_metric_availability` or `pass_if_value_missing` set, only that setting is accepted
            - `pass_description` string, nullable
            - `transaction_scope` TransactionScope
              - …
            - `type` 'equal' | 'not_equal' | 'before' | 'before_or_on' | 'after' | 'after_or_on'
            - `value` string, date, nullable
          - `date_delta_to_now_check` DateDeltaToNowCheck
            - `auto_decline` boolean
            - `decline_code` string, nullable: The CRM's identifier for this decline reason, e.g. a LendSaas reason id. Left unset, the CRM sync falls back to this check's decline_description.
            - `decline_description` string, nullable
            - `email_template_name` string, nullable
            - `ignore_metric_availability` boolean
            - `is_mandatory` boolean
            - `on_failure` 'fail' | 'review_required'
            - `on_missing` 'missing_data' | 'fail' | 'pass': What the check reports when it would report missing data: `missing_data` (the default), `fail` or `pass`. A check saved with an older flag (`pass_if_value_missing` on a date-delta check) reads as the setting it stands for. With `ignore_metric_availability` or `pass_if_value_missing` set, only that setting is accepted
            - `pass_description` string, nullable
            - `pass_if_value_missing` boolean
            - `transaction_scope` TransactionScope
              - …
            - `type` 'greater_than' | 'greater_than_or_equal' | 'less_than' | 'less_than_or_equal'
            - `value` object, nullable
          - `enhanced_sql_check` EnhancedSQLCheck
            - `auto_decline` boolean
            - `check_type` 'equal' | 'not_equal' | 'greater_than' | 'greater_than_or_equal' | 'less_than' | 'less_than_or_equal' | 'before' | 'before_or_on' | 'after' | 'after_or_on' | 'is_in' | 'is_not_in', required
            - `column_name` string, required
            - `comparison_value` unknown, required
            - `data_type` 'numeric' | 'date' | 'string', required
            - `decline_code` string, nullable: The CRM's identifier for this decline reason, e.g. a LendSaas reason id. Left unset, the CRM sync falls back to this check's decline_description.
            - `decline_description` string, nullable
            - `email_template_name` string, nullable
            - `ignore_metric_availability` boolean
            - `is_mandatory` boolean
            - `on_failure` 'fail' | 'review_required'
            - `on_missing` 'missing_data' | 'fail' | 'pass': What the check reports when it would report missing data: `missing_data` (the default), `fail` or `pass`. A check saved with an older flag (`pass_if_value_missing` on a date-delta check) reads as the setting it stands for. With `ignore_metric_availability` or `pass_if_value_missing` set, only that setting is accepted
            - `pass_description` string, nullable
            - `query_name` string, required
            - `transaction_scope` TransactionScope
              - …
          - `group` string, nullable
          - `heron_id` string, nullable: Stable across edits; omit for a new check and one is minted. Policy versions only
          - `identity` string, nullable: Stable kind:key identity used to match stored check evaluations
          - `name` string, nullable
          - `numeric_check` NumericCheck
            - `auto_decline` boolean
            - `decline_code` string, nullable: The CRM's identifier for this decline reason, e.g. a LendSaas reason id. Left unset, the CRM sync falls back to this check's decline_description.
            - `decline_description` string, nullable
            - `email_template_name` string, nullable
            - `ignore_metric_availability` boolean
            - `is_mandatory` boolean
            - `on_failure` 'fail' | 'review_required'
            - `on_missing` 'missing_data' | 'fail' | 'pass': What the check reports when it would report missing data: `missing_data` (the default), `fail` or `pass`. A check saved with an older flag (`pass_if_value_missing` on a date-delta check) reads as the setting it stands for. With `ignore_metric_availability` or `pass_if_value_missing` set, only that setting is accepted
            - `pass_description` string, nullable
            - `transaction_scope` TransactionScope
              - …
            - `type` 'equal' | 'not_equal' | 'greater_than' | 'greater_than_or_equal' | 'less_than' | 'less_than_or_equal'
            - `value` union: The threshold: a number as a string, {"variable": {...}} to compare with another variable (with an optional "factor" that scales it), or {"lookup": {"table_heron_id", "column_id"}} to read it from a lookup table column
              - …
          - `parameters` object, nullable
          - `sql_check` SQLCheck
            - `auto_decline` boolean
            - `column_name` string, required
            - `decline_code` string, nullable: The CRM's identifier for this decline reason, e.g. a LendSaas reason id. Left unset, the CRM sync falls back to this check's decline_description.
            - `decline_description` string, nullable
            - `email_template_name` string, nullable
            - `ignore_metric_availability` boolean
            - `is_mandatory` boolean
            - `on_failure` 'fail' | 'review_required'
            - `on_missing` 'missing_data' | 'fail' | 'pass': What the check reports when it would report missing data: `missing_data` (the default), `fail` or `pass`. A check saved with an older flag (`pass_if_value_missing` on a date-delta check) reads as the setting it stands for. With `ignore_metric_availability` or `pass_if_value_missing` set, only that setting is accepted
            - `pass_description` string, nullable
            - `query_name` string, required
            - `transaction_scope` TransactionScope
              - …
          - `string_check` StringCheck
            - `auto_decline` boolean
            - `decline_code` string, nullable: The CRM's identifier for this decline reason, e.g. a LendSaas reason id. Left unset, the CRM sync falls back to this check's decline_description.
            - `decline_description` string, nullable
            - `email_template_name` string, nullable
            - `ignore_metric_availability` boolean
            - `is_mandatory` boolean
            - `match_count` integer, nullable
            - `on_failure` 'fail' | 'review_required'
            - `on_missing` 'missing_data' | 'fail' | 'pass': What the check reports when it would report missing data: `missing_data` (the default), `fail` or `pass`. A check saved with an older flag (`pass_if_value_missing` on a date-delta check) reads as the setting it stands for. With `ignore_metric_availability` or `pass_if_value_missing` set, only that setting is accepted
            - `pass_description` string, nullable
            - `transaction_scope` TransactionScope
              - …
            - `type` 'equal' | 'not_equal' | 'starts_with' | 'starts_with_any_of' | 'does_not_start_with_any_of' | 'contains' | 'does_not_start_with' | 'does_not_contain' | 'is_in' | 'is_not_in' | 'has_none_of' | 'has_any_of' | 'has_only' | 'has_fewer_than_n_matches' | 'has_more_than_n_matches' | 'is_valid' | 'is_invalid'
            - `value` union: The value as a string, or {"lookup": {"table_heron_id"}} for is_in, is_not_in, has_any_of, has_none_of or has_only to read the list from a lookup table's rows
              - …
        - `condition` unknown
        - `decline_code` string, nullable: Optional code sent with a failed or review_required result
        - `decline_description` string, nullable: Required when result is failed or review_required
        - `heron_id` string, nullable
        - `name` string
        - `result` unknown
      - `display_order` integer, nullable
      - `heron_id` string, nullable
      - `name` string, required
      - `use_case` 'background_check' | 'cashflow'

## Response `200`

OK

- object
  - `issues` PublishIssueSchema[]: What publishing this draft would break. Saving never blocks; an issue with blocks_publish set will stop the publish.
    - `attribute_label` string, nullable: The variable the check reads
    - `available_after` string, nullable: Customer-facing name of the step after which every deal has the variable
    - `blocks_publish` boolean, required: Publishing is refused while this is true; saving never is
    - `check_name` string, nullable: The top-level check, even when a condition in it reads the variable
    - `code` 'data_on_no_path' | 'data_not_in_workflow' | 'data_on_some_paths_only' | 'data_unverified' | 'policy_node_left_without_sections' | 'unknown_attribute' | 'invalid_attribute_parameters' | 'incompatible_compared_variable' | 'unreadable_lookup_threshold' | 'email_address_compared_with_domain', required
    - `message` string, required
    - `path` unknown[], required: The check that reads the variable, as a save error would point at it, down to a condition inside a group; empty for a workflow node
      - unknown
    - `policy_node_id` string, nullable: Workflow node left with no sections
    - `section_heron_id` string, nullable
    - `section_name` string, nullable
  - `policy_version` PolicyVersionSchema
    - `author_email` string: Email of whoever last acted on this version: the drafter while it is a draft, the publisher once published
    - `backtest_status` PolicyVersionBacktestStatus
      - `backtest_heron_id` string, nullable
      - `deal_count` integer, nullable: Deals the backtest covered
      - `finished_at` string, date-time, nullable
      - `flipped_deal_count` integer, nullable: Deals whose outcome changed, null unless the run completed
      - `run_status` unknown
      - `stale` boolean: The version was edited after that backtest was asked for, so re-run before publishing
    - `change_description` string, nullable: What changed in this version
    - `created` string, date-time
    - `last_edited_at` string, date-time, nullable
    - `policy_definition` PolicyDefinition
      - `policy_sections` PolicyVersionSection[], required
        - `branches` PolicyBranch[]: Ordered routes through the section; the section's own checks run on every route
          - `checks` Check[]
            - `attribute_description` string, nullable: What the attribute measures. Present only for accounts on policy versions
            - `attribute_display_name` string, nullable: The attribute's human-readable name. Present only for accounts on policy versions
            - `attribute_label` string, nullable
            - `attribute_unit` unknown
            - `attribute_validators` object[], nullable: The validity operators `attribute_label` offers, as in the catalogue's `check_options[].validators`, so a saved `is_valid` / `is_invalid` check can be worded. Empty for a check without an attribute or an attribute with no validity rule
              - …
            - `attribute_value_set` unknown
            - `boolean_check` BooleanCheck
              - …
            - `composite_check` CompositeCheck
              - …
            - `date_check` DateCheck
              - …
            - `date_delta_to_now_check` DateDeltaToNowCheck
              - …
            - `enhanced_sql_check` EnhancedSQLCheck
              - …
            - `group` string, nullable
            - `heron_id` string, nullable: Stable across edits; omit for a new check and one is minted. Policy versions only
            - `identity` string, nullable: Stable kind:key identity used to match stored check evaluations
            - `name` string, nullable
            - `numeric_check` NumericCheck
              - …
            - `parameters` object, nullable
            - `sql_check` SQLCheck
              - …
            - `string_check` StringCheck
              - …
          - `condition` Check, required
            - `attribute_description` string, nullable: What the attribute measures. Present only for accounts on policy versions
            - `attribute_display_name` string, nullable: The attribute's human-readable name. Present only for accounts on policy versions
            - `attribute_label` string, nullable
            - `attribute_unit` unknown
            - `attribute_validators` object[], nullable: The validity operators `attribute_label` offers, as in the catalogue's `check_options[].validators`, so a saved `is_valid` / `is_invalid` check can be worded. Empty for a check without an attribute or an attribute with no validity rule
              - …
            - `attribute_value_set` unknown
            - `boolean_check` BooleanCheck
              - …
            - `composite_check` CompositeCheck
              - …
            - `date_check` DateCheck
              - …
            - `date_delta_to_now_check` DateDeltaToNowCheck
              - …
            - `enhanced_sql_check` EnhancedSQLCheck
              - …
            - `group` string, nullable
            - `heron_id` string, nullable: Stable across edits; omit for a new check and one is minted. Policy versions only
            - `identity` string, nullable: Stable kind:key identity used to match stored check evaluations
            - `name` string, nullable
            - `numeric_check` NumericCheck
              - …
            - `parameters` object, nullable
            - `sql_check` SQLCheck
              - …
            - `string_check` StringCheck
              - …
          - `heron_id` string, nullable: Stable across renames; omit for a new branch and one is minted
          - `name` string, required
        - `checks` Check[]
          - `attribute_description` string, nullable: What the attribute measures. Present only for accounts on policy versions
          - `attribute_display_name` string, nullable: The attribute's human-readable name. Present only for accounts on policy versions
          - `attribute_label` string, nullable
          - `attribute_unit` unknown
          - `attribute_validators` object[], nullable: The validity operators `attribute_label` offers, as in the catalogue's `check_options[].validators`, so a saved `is_valid` / `is_invalid` check can be worded. Empty for a check without an attribute or an attribute with no validity rule
          - `attribute_value_set` unknown
          - `boolean_check` BooleanCheck
            - `auto_decline` boolean
            - `decline_code` string, nullable: The CRM's identifier for this decline reason, e.g. a LendSaas reason id. Left unset, the CRM sync falls back to this check's decline_description.
            - `decline_description` string, nullable
            - `email_template_name` string, nullable
            - `ignore_metric_availability` boolean
            - `is_mandatory` boolean
            - `on_failure` 'fail' | 'review_required'
            - `on_missing` 'missing_data' | 'fail' | 'pass': What the check reports when it would report missing data: `missing_data` (the default), `fail` or `pass`. A check saved with an older flag (`pass_if_value_missing` on a date-delta check) reads as the setting it stands for. With `ignore_metric_availability` or `pass_if_value_missing` set, only that setting is accepted
            - `pass_description` string, nullable
            - `transaction_scope` TransactionScope
              - …
            - `value` boolean
          - `composite_check` CompositeCheck
            - `auto_decline` boolean
            - `checks` Check[]
            - `decline_code` string, nullable: The CRM's identifier for this decline reason, e.g. a LendSaas reason id. Left unset, the CRM sync falls back to this check's decline_description.
            - `decline_description` string, nullable
            - `email_template_name` string, nullable
            - `ignore_metric_availability` boolean
            - `is_mandatory` boolean
            - `max_failing` integer, nullable
            - `on_failure` 'fail' | 'review_required'
            - `on_missing` 'missing_data' | 'fail' | 'pass': What the check reports when it would report missing data: `missing_data` (the default), `fail` or `pass`. A check saved with an older flag (`pass_if_value_missing` on a date-delta check) reads as the setting it stands for. With `ignore_metric_availability` or `pass_if_value_missing` set, only that setting is accepted
            - `pass_description` string, nullable
            - `transaction_scope` TransactionScope
              - …
            - `type` 'AND' | 'OR' | 'AT_MOST_FAILING'
          - `date_check` DateCheck
            - `auto_decline` boolean
            - `decline_code` string, nullable: The CRM's identifier for this decline reason, e.g. a LendSaas reason id. Left unset, the CRM sync falls back to this check's decline_description.
            - `decline_description` string, nullable
            - `email_template_name` string, nullable
            - `ignore_metric_availability` boolean
            - `is_mandatory` boolean
            - `on_failure` 'fail' | 'review_required'
            - `on_missing` 'missing_data' | 'fail' | 'pass': What the check reports when it would report missing data: `missing_data` (the default), `fail` or `pass`. A check saved with an older flag (`pass_if_value_missing` on a date-delta check) reads as the setting it stands for. With `ignore_metric_availability` or `pass_if_value_missing` set, only that setting is accepted
            - `pass_description` string, nullable
            - `transaction_scope` TransactionScope
              - …
            - `type` 'equal' | 'not_equal' | 'before' | 'before_or_on' | 'after' | 'after_or_on'
            - `value` string, date, nullable
          - `date_delta_to_now_check` DateDeltaToNowCheck
            - `auto_decline` boolean
            - `decline_code` string, nullable: The CRM's identifier for this decline reason, e.g. a LendSaas reason id. Left unset, the CRM sync falls back to this check's decline_description.
            - `decline_description` string, nullable
            - `email_template_name` string, nullable
            - `ignore_metric_availability` boolean
            - `is_mandatory` boolean
            - `on_failure` 'fail' | 'review_required'
            - `on_missing` 'missing_data' | 'fail' | 'pass': What the check reports when it would report missing data: `missing_data` (the default), `fail` or `pass`. A check saved with an older flag (`pass_if_value_missing` on a date-delta check) reads as the setting it stands for. With `ignore_metric_availability` or `pass_if_value_missing` set, only that setting is accepted
            - `pass_description` string, nullable
            - `pass_if_value_missing` boolean
            - `transaction_scope` TransactionScope
              - …
            - `type` 'greater_than' | 'greater_than_or_equal' | 'less_than' | 'less_than_or_equal'
            - `value` object, nullable
          - `enhanced_sql_check` EnhancedSQLCheck
            - `auto_decline` boolean
            - `check_type` 'equal' | 'not_equal' | 'greater_than' | 'greater_than_or_equal' | 'less_than' | 'less_than_or_equal' | 'before' | 'before_or_on' | 'after' | 'after_or_on' | 'is_in' | 'is_not_in', required
            - `column_name` string, required
            - `comparison_value` unknown, required
            - `data_type` 'numeric' | 'date' | 'string', required
            - `decline_code` string, nullable: The CRM's identifier for this decline reason, e.g. a LendSaas reason id. Left unset, the CRM sync falls back to this check's decline_description.
            - `decline_description` string, nullable
            - `email_template_name` string, nullable
            - `ignore_metric_availability` boolean
            - `is_mandatory` boolean
            - `on_failure` 'fail' | 'review_required'
            - `on_missing` 'missing_data' | 'fail' | 'pass': What the check reports when it would report missing data: `missing_data` (the default), `fail` or `pass`. A check saved with an older flag (`pass_if_value_missing` on a date-delta check) reads as the setting it stands for. With `ignore_metric_availability` or `pass_if_value_missing` set, only that setting is accepted
            - `pass_description` string, nullable
            - `query_name` string, required
            - `transaction_scope` TransactionScope
              - …
          - `group` string, nullable
          - `heron_id` string, nullable: Stable across edits; omit for a new check and one is minted. Policy versions only
          - `identity` string, nullable: Stable kind:key identity used to match stored check evaluations
          - `name` string, nullable
          - `numeric_check` NumericCheck
            - `auto_decline` boolean
            - `decline_code` string, nullable: The CRM's identifier for this decline reason, e.g. a LendSaas reason id. Left unset, the CRM sync falls back to this check's decline_description.
            - `decline_description` string, nullable
            - `email_template_name` string, nullable
            - `ignore_metric_availability` boolean
            - `is_mandatory` boolean
            - `on_failure` 'fail' | 'review_required'
            - `on_missing` 'missing_data' | 'fail' | 'pass': What the check reports when it would report missing data: `missing_data` (the default), `fail` or `pass`. A check saved with an older flag (`pass_if_value_missing` on a date-delta check) reads as the setting it stands for. With `ignore_metric_availability` or `pass_if_value_missing` set, only that setting is accepted
            - `pass_description` string, nullable
            - `transaction_scope` TransactionScope
              - …
            - `type` 'equal' | 'not_equal' | 'greater_than' | 'greater_than_or_equal' | 'less_than' | 'less_than_or_equal'
            - `value` union: The threshold: a number as a string, {"variable": {...}} to compare with another variable (with an optional "factor" that scales it), or {"lookup": {"table_heron_id", "column_id"}} to read it from a lookup table column
              - …
          - `parameters` object, nullable
          - `sql_check` SQLCheck
            - `auto_decline` boolean
            - `column_name` string, required
            - `decline_code` string, nullable: The CRM's identifier for this decline reason, e.g. a LendSaas reason id. Left unset, the CRM sync falls back to this check's decline_description.
            - `decline_description` string, nullable
            - `email_template_name` string, nullable
            - `ignore_metric_availability` boolean
            - `is_mandatory` boolean
            - `on_failure` 'fail' | 'review_required'
            - `on_missing` 'missing_data' | 'fail' | 'pass': What the check reports when it would report missing data: `missing_data` (the default), `fail` or `pass`. A check saved with an older flag (`pass_if_value_missing` on a date-delta check) reads as the setting it stands for. With `ignore_metric_availability` or `pass_if_value_missing` set, only that setting is accepted
            - `pass_description` string, nullable
            - `query_name` string, required
            - `transaction_scope` TransactionScope
              - …
          - `string_check` StringCheck
            - `auto_decline` boolean
            - `decline_code` string, nullable: The CRM's identifier for this decline reason, e.g. a LendSaas reason id. Left unset, the CRM sync falls back to this check's decline_description.
            - `decline_description` string, nullable
            - `email_template_name` string, nullable
            - `ignore_metric_availability` boolean
            - `is_mandatory` boolean
            - `match_count` integer, nullable
            - `on_failure` 'fail' | 'review_required'
            - `on_missing` 'missing_data' | 'fail' | 'pass': What the check reports when it would report missing data: `missing_data` (the default), `fail` or `pass`. A check saved with an older flag (`pass_if_value_missing` on a date-delta check) reads as the setting it stands for. With `ignore_metric_availability` or `pass_if_value_missing` set, only that setting is accepted
            - `pass_description` string, nullable
            - `transaction_scope` TransactionScope
              - …
            - `type` 'equal' | 'not_equal' | 'starts_with' | 'starts_with_any_of' | 'does_not_start_with_any_of' | 'contains' | 'does_not_start_with' | 'does_not_contain' | 'is_in' | 'is_not_in' | 'has_none_of' | 'has_any_of' | 'has_only' | 'has_fewer_than_n_matches' | 'has_more_than_n_matches' | 'is_valid' | 'is_invalid'
            - `value` union: The value as a string, or {"lookup": {"table_heron_id"}} for is_in, is_not_in, has_any_of, has_none_of or has_only to read the list from a lookup table's rows
              - …
        - `default_branch` DefaultPolicyBranch
          - `checks` Check[]
            - `attribute_description` string, nullable: What the attribute measures. Present only for accounts on policy versions
            - `attribute_display_name` string, nullable: The attribute's human-readable name. Present only for accounts on policy versions
            - `attribute_label` string, nullable
            - `attribute_unit` unknown
            - `attribute_validators` object[], nullable: The validity operators `attribute_label` offers, as in the catalogue's `check_options[].validators`, so a saved `is_valid` / `is_invalid` check can be worded. Empty for a check without an attribute or an attribute with no validity rule
              - …
            - `attribute_value_set` unknown
            - `boolean_check` BooleanCheck
              - …
            - `composite_check` CompositeCheck
              - …
            - `date_check` DateCheck
              - …
            - `date_delta_to_now_check` DateDeltaToNowCheck
              - …
            - `enhanced_sql_check` EnhancedSQLCheck
              - …
            - `group` string, nullable
            - `heron_id` string, nullable: Stable across edits; omit for a new check and one is minted. Policy versions only
            - `identity` string, nullable: Stable kind:key identity used to match stored check evaluations
            - `name` string, nullable
            - `numeric_check` NumericCheck
              - …
            - `parameters` object, nullable
            - `sql_check` SQLCheck
              - …
            - `string_check` StringCheck
              - …
          - `condition` unknown
          - `decline_code` string, nullable: Optional code sent with a failed or review_required result
          - `decline_description` string, nullable: Required when result is failed or review_required
          - `heron_id` string, nullable
          - `name` string
          - `result` unknown
        - `display_order` integer, nullable
        - `heron_id` string, nullable
        - `name` string, required
        - `use_case` 'background_check' | 'cashflow'
    - `published_at` string, date-time, nullable
    - `status` 'draft' | 'active' | 'archived'
    - `version` integer: Version number, unique per account

## Other responses

- `404`: No draft policy version
- `422`: The policy definition is invalid. `errors` lists every problem with the path of the field it belongs to, a stable code and a message.

## Changes

- **2026-11-03** `1ec936e17fef`: 4 warning, 4 info
  - added the new `industry_category` enum value to the `policy_version/policy_definition/allOf[#/components/schemas/PolicyDefinition]/policy_sections/items/branches/items/checks/items/attribute_value_set` response property for the response status `200`
  - added the new `industry_category` enum value to the `policy_version/policy_definition/allOf[#/components/schemas/PolicyDefinition]/policy_sections/items/branches/items/condition/allOf[#/components/schemas/Check]/attribute_value_set` response property for the response status `200`
  - added the new `industry_category` enum value to the `policy_version/policy_definition/allOf[#/components/schemas/PolicyDefinition]/policy_sections/items/checks/items/attribute_value_set` response property for the response status `200`
  - added the new `industry_category` enum value to the `policy_version/policy_definition/allOf[#/components/schemas/PolicyDefinition]/policy_sections/items/default_branch/allOf[#/components/schemas/DefaultPolicyBranch]/checks/items/attribute_value_set` response property for the response status `200`
  - …4 more
- **2026-11-03** `bd8008e49534`: 1 info
  - endpoint added

[Operation history](https://skmtc.dev/herondata/apis/heron-data-api/changes/api/policy_version/put.md)

---

[API](https://skmtc.dev/herondata/apis/heron-data-api.md) - [All operations](https://skmtc.dev/herondata/apis/heron-data-api/llms.txt) - [OpenAPI document](https://skmtc.dev/herondata/apis/heron-data-api/revisions/1ec936e17fef?raw)
