---
id: TST-PFM-MTD-105
title: custom fields
kind: api-lifecycle
product_area: platform
module: metadata
revision: 1
status: draft
source_sha:
  services-platform: ad3f6a6582843008ed0f5a17b131878d15829af1
repository: services-platform
files:
  - modules/metadata/tests/e2e/custom-fields.e2e.spec.js
implements:
  - ATS-PFM-MTD-005-03
  - ATS-PFM-MTD-005-05
  - ATS-PFM-MTD-005-06
  - ATS-PFM-MTD-005-07
  - ATS-PFM-MTD-005-11
environment: local
implementation_state: implemented
latest_result: not-run
latest_run_at: null
latest_run_ref: null
conformance: not-verified
estimated_minutes: 5
isolation: >-
  Prepared integration database and the suite fixture records; fixture teardown restores or removes its own
  rows.
evidence:
  - 'services-platform:modules/metadata/tests/e2e/custom-fields.e2e.spec.js'
  - >-
    services-platform:modules/metadata/tests/e2e/custom-fields.e2e.spec.js#answers 200 with the field it
    created
  - >-
    services-platform:modules/metadata/tests/e2e/custom-fields.e2e.spec.js#identifies the field by its object
    and key, with the display its data type implies and the signed caller as its creator
  - >-
    services-platform:modules/metadata/tests/e2e/custom-fields.e2e.spec.js#describes the new field after the
    standard fields
  - >-
    services-platform:modules/metadata/tests/e2e/custom-fields.e2e.spec.js#creates a field required by the API
    and describes its level, so the console and the portal can enforce theirs
  - >-
    services-platform:modules/metadata/tests/e2e/custom-fields.e2e.spec.js#refuses a required level outside
    api, console, portal and none as 400
  - >-
    services-platform:modules/metadata/tests/e2e/custom-fields.e2e.spec.js#refuses an incompatible display as
    400 with the reason
  - >-
    services-platform:modules/metadata/tests/e2e/custom-fields.e2e.spec.js#refuses a key that does not end in
    the custom suffix as 400
  - >-
    services-platform:modules/metadata/tests/e2e/custom-fields.e2e.spec.js#refuses a body with no data type as
    400
  - >-
    services-platform:modules/metadata/tests/e2e/custom-fields.e2e.spec.js#refuses an object that is not
    registered as 404
  - >-
    services-platform:modules/metadata/tests/e2e/custom-fields.e2e.spec.js#refuses a path tenant outside the
    signed context as 403
  - 'services-platform:modules/metadata/tests/e2e/custom-fields.e2e.spec.js#refuses an anonymous call as 401'
  - >-
    services-platform:modules/metadata/tests/e2e/custom-fields.e2e.spec.js#answers the field exactly as the
    create answered it
  - >-
    services-platform:modules/metadata/tests/e2e/custom-fields.e2e.spec.js#refuses a key no tenant ever
    defined as 404
  - >-
    services-platform:modules/metadata/tests/e2e/custom-fields.e2e.spec.js#answers 404 for the other tenant's
    own view of the field
  - 'services-platform:modules/metadata/tests/e2e/custom-fields.e2e.spec.js#refuses an anonymous call as 401'
  - 'services-platform:modules/metadata/tests/e2e/custom-fields.e2e.spec.js#lists the tenant''s own field'
  - >-
    services-platform:modules/metadata/tests/e2e/custom-fields.e2e.spec.js#shows the other tenant none of the
    first tenant's fields
  - >-
    services-platform:modules/metadata/tests/e2e/custom-fields.e2e.spec.js#refuses an object that is not
    registered as 404
  - 'services-platform:modules/metadata/tests/e2e/custom-fields.e2e.spec.js#refuses an anonymous call as 401'
  - >-
    services-platform:modules/metadata/tests/e2e/custom-fields.e2e.spec.js#answers 200 with the new label and
    the next version
  - >-
    services-platform:modules/metadata/tests/e2e/custom-fields.e2e.spec.js#persists the new label, read back
    through the API
  - 'services-platform:modules/metadata/tests/e2e/custom-fields.e2e.spec.js#refuses a changed key as 400'
  - 'services-platform:modules/metadata/tests/e2e/custom-fields.e2e.spec.js#refuses a stale version as 409'
  - >-
    services-platform:modules/metadata/tests/e2e/custom-fields.e2e.spec.js#refuses a key no tenant ever
    defined as 404
  - 'services-platform:modules/metadata/tests/e2e/custom-fields.e2e.spec.js#refuses an anonymous call as 401'
  - >-
    services-platform:modules/metadata/tests/e2e/custom-fields.e2e.spec.js#answers the archive with the moment
    the field was archived
  - >-
    services-platform:modules/metadata/tests/e2e/custom-fields.e2e.spec.js#answers the restore with a field
    that is archived no longer
  - 'services-platform:modules/metadata/tests/e2e/custom-fields.e2e.spec.js#describes the restored field again'
  - >-
    services-platform:modules/metadata/tests/e2e/custom-fields.e2e.spec.js#refuses archiving a key no tenant
    ever defined as 404
  - >-
    services-platform:modules/metadata/tests/e2e/custom-fields.e2e.spec.js#refuses restoring a key no tenant
    ever defined as 404
  - 'services-platform:modules/metadata/tests/e2e/custom-fields.e2e.spec.js#refuses an anonymous archive as 401'
  - 'services-platform:modules/metadata/tests/e2e/custom-fields.e2e.spec.js#refuses an anonymous restore as 401'
fixture_imports:
  - chai
  - '@rhythmsoftware/macroservice-testing/stage'
  - ./support
  - ../integration/support
test_doubles: []
limitations: []
unmatched_specification: null
binding_assertions:
  - scenario: ATS-PFM-MTD-005-03
    provenance: test
    source:
      - 'services-platform:modules/metadata/tests/e2e/custom-fields.e2e.spec.js#refuses a changed key as 400'
    note: >-
      These references identify the assertions this suite contributes; bindings to additional suites remain
      part of the scenario’s proof.
  - scenario: ATS-PFM-MTD-005-05
    provenance: test
    source:
      - >-
        services-platform:modules/metadata/tests/e2e/custom-fields.e2e.spec.js#refuses an incompatible display
        as 400 with the reason
    note: >-
      These references identify the assertions this suite contributes; bindings to additional suites remain
      part of the scenario’s proof.
  - scenario: ATS-PFM-MTD-005-06
    provenance: test
    source:
      - >-
        services-platform:modules/metadata/tests/e2e/custom-fields.e2e.spec.js#creates a field required by the
        API and describes its level, so the console and the portal can enforce theirs
    note: >-
      These references identify the assertions this suite contributes; bindings to additional suites remain
      part of the scenario’s proof.
  - scenario: ATS-PFM-MTD-005-07
    provenance: test
    source:
      - >-
        services-platform:modules/metadata/tests/e2e/custom-fields.e2e.spec.js#describes the restored field
        again
    note: >-
      These references identify the assertions this suite contributes; bindings to additional suites remain
      part of the scenario’s proof.
  - scenario: ATS-PFM-MTD-005-11
    provenance: test
    source:
      - 'services-platform:modules/metadata/tests/e2e/custom-fields.e2e.spec.js#refuses a stale version as 409'
    note: >-
      These references identify the assertions this suite contributes; bindings to additional suites remain
      part of the scenario’s proof.
---

# Custom fields

## Verification Boundary

This API suite checks record descriptions and field configuration within the local test harness. The registered file and pinned revision define its boundary.

## What This Suite Proves

The bindings identify the detailed or feature scenarios whose outcomes have assertions in this suite. Original case references remain attached to the detailed scenarios so a reviewer can inspect the exact assertion. Assertions are evidence of implemented checks; no execution result is claimed.

## What It Does Not Prove

The register does not establish a current passing run or full specification conformance. Behavior outside the suite’s fixtures and assertions remains unverified.

## Real Dependencies and Test Doubles

The fixture uses PostgreSQL and the imported persistence or API code. The fixture imports identify the setup seams; this register makes no broader claim that dependencies are undoubled.

## Must Not Be Doubled

The operation under examination and its asserted stored outcomes must remain real within the declared harness. A fixture cannot replace the write, refusal or transactional effect that the bound scenario checks.
