From 17b7a4364b4c26208325bb54d1fbc872d447400b Mon Sep 17 00:00:00 2001 From: delchev Date: Thu, 13 Aug 2026 10:18:07 +0300 Subject: [PATCH] docs(intent): locksWithMaster - a child collection that outlives its master's lock A master's immutableWhen locks that entity, but the generated UI extended the lock to every child PANEL, so an issued invoice's allocation rows could not be added by hand - in the one state where allocations matter. The child's own controller always accepted the writes. Documents locksWithMaster: false, its default, the two parse-time validations, and the boundary: a document's own line items are unaffected. Co-Authored-By: Claude Opus 5 --- docs/help/intent/dsl-reference.md | 25 +++++++++++++++++++++++++ 1 file changed, 25 insertions(+) diff --git a/docs/help/intent/dsl-reference.md b/docs/help/intent/dsl-reference.md index 443b4f822..2364698b8 100644 --- a/docs/help/intent/dsl-reference.md +++ b/docs/help/intent/dsl-reference.md @@ -221,6 +221,31 @@ mutually exclusive with it. Workflow/system writes through the repository stay p corrections to an immutable record are flow-generated reversals, never edits. (`immutableIn:` is the pre-rename spelling, rejected with a migration message.) +## locksWithMaster - a child collection that outlives its master's lock + +```yaml +- name: SalesInvoice + immutableWhen: "Status == 3" # ISSUED: the document's own content freezes +- name: SalesInvoiceCustomerPayment + locksWithMaster: false # ...but money keeps being recorded against it + relations: + - { name: SalesInvoice, kind: manyToOne, to: SalesInvoice, composition: true, required: true } +``` + +A master's immutability locks **that entity**. A composition child is a different entity with its +own generated controller - which already accepts the writes - so freezing its panel too was the +generated UI extending a rule the model never declared: the Add button and row actions on the +allocations panel existed only while the invoice was DRAFT, i.e. never in the state where +allocations matter. + +`locksWithMaster: false` keeps that panel's affordances alive while the master is locked. Content +and settlement are different lifecycles on the same document. + +Default `true`. Parse-validated on both halves - it must be a composition child, and its master must +actually declare `immutableWhen` / `immutable`, so an inert declaration fails at generate time +instead of quietly doing nothing. A document's own **line items** are unaffected: they render in the +items pane, not a child panel, and stay locked. + ## hierarchy / leafOnly - tree entities ```yaml