Property contracts and concepts

Every key=value tag is schemaless by default. Existing tags therefore keep working without configuration. A root administrator can optionally give a key a property contract to add validation, cardinality, units, or a controlled concept vocabulary.

Supported value kinds are text, concept, number, quantity, range, date, datetime, boolean, and identifier. Cardinality is many (the default) or one; applying a new value to a single-valued property replaces the previous value for that file/subject.

Declarative CLI management

Property resources are versioned JSON documents, designed for source control and repeatable application in the same spirit as kubectl apply -f:

{
  "apiVersion": "tessera.dev/v1alpha1",
  "kind": "PropertySet",
  "properties": [
    {
      "name": "size-class",
      "value_kind": "concept",
      "cardinality": "one",
      "concepts": [
        {
          "value": "small",
          "labels": [
            { "language": "nl", "label": "klein", "preferred": true },
            { "language": "en", "label": "small", "preferred": true },
            { "language": "en", "label": "S", "preferred": false }
          ]
        },
        {
          "value": "microscopic",
          "parent": "small",
          "labels": [
            { "language": "nl", "label": "microscopisch", "preferred": true }
          ]
        }
      ]
    },
    {
      "name": "fibre-diameter",
      "value_kind": "quantity",
      "cardinality": "many",
      "canonical_unit": "µm",
      "allowed_units": ["µm", "nm", "mm"]
    }
  ]
}
tessera property apply -f properties.json
tessera property apply -f - < properties.json
tessera property get
tessera property get size-class
tessera property delete size-class

get always emits a complete PropertySet, so its output can be edited and applied again. Applying a manifest replaces the concept metadata for the named properties but never rewrites unrelated properties or tag assignments. Deleting a contract also leaves assignments intact; the key simply becomes schemaless again.

Controlled concepts

A concept has a stable canonical value, an optional parent, and any number of language-aware labels. Labels work as key-scoped aliases in equality queries:

size-class=klein

matches assignments stored as size-class=small. A query for a parent concept also includes its descendants, so size-class=small includes size-class=microscopic.

Concepts can carry typed properties whose names refer to other property contracts. Files and subjects still store only the stable concept value; shared facts about that concept live in one place:

{
  "properties": [
    {
      "name": "typical-age",
      "value_kind": "range",
      "cardinality": "one",
      "canonical_unit": "years",
      "allowed_units": ["years"]
    },
    {
      "name": "life-stage",
      "value_kind": "concept",
      "cardinality": "one",
      "concepts": [
        {
          "value": "menopause",
          "labels": [
            { "language": "nl", "label": "overgang", "preferred": true }
          ],
          "properties": [
            { "name": "typical-age", "value": "40-60 years" }
          ]
        }
      ]
    }
  ]
}

An assignment such as life-stage=menopause is therefore the reference. Its typical-age metadata is validated using the range contract. Referenced property contracts may appear before or after the concept in one manifest.

Quantities

A quantity validates a numeric magnitude followed by an optional unit. When allowed_units is non-empty, input must use one of those exact units. The initial v1alpha1 contract does not convert magnitudes between units: the canonical unit records intent and supports consistent administration, but queries still compare the stored textual values using Tessera's existing numeric behaviour. Unit conversion can be added without turning each measured value into a concept.

Ranges

A range is one value with two bounds. Bounds may be numeric with a shared unit, such as type1/size=2-10 µm or age=40-60 years, textual (letter=a-z), or ISO dates (period=2020-01-01..2022-12-31). The separators -, , , and .. are accepted. Use .. when a bound itself contains a hyphen, especially for dates and compound words.

Numeric lower bounds must not exceed their upper bounds. ISO date bounds are also checked chronologically. As with quantities, allowed_units can restrict the shared unit; configured units make numeric bounds mandatory.

range is a value kind, not a cardinality. Cardinality independently says whether one or several ranges may be assigned to the same file or subject.

Web administration

Select a tag in Tag Manager and open Property contract. The editor can set the value kind, cardinality, quantity/range units, description, and controlled concept structure. Removing a contract from this screen never removes tags from files, directories, or subjects.