docs(templates): record derive-on-compose decisions (naming, migration, tree UX)
This commit is contained in:
@@ -243,30 +243,30 @@ Each phase is independently shippable and reviewable.
|
||||
`ParentTemplateId`, but the UX hasn't been designed.
|
||||
- Cross-tenant template libraries.
|
||||
|
||||
## Open questions
|
||||
## Decisions
|
||||
|
||||
- **Derived-template names**: `Pump.TempSensor` vs `Pump_TempSensor` vs
|
||||
`${parentName}::${instanceName}`? Visible only on the edit page since the
|
||||
tree hides derived templates, but appears in audit logs and error messages.
|
||||
Default: dot-separated mirrors the canonical path format already used in
|
||||
flattening (`TempSensor.Temperature`). Pick this unless the dot is
|
||||
problematic for any existing pipeline.
|
||||
- **Naming**: dot-separated (`Pump.TempSensor`). Matches the canonical-path
|
||||
format used in flattening. Visible in audit logs / error messages.
|
||||
- **Delete base with derivatives**: block the delete and list the derivatives.
|
||||
User must remove or repoint them first.
|
||||
- **Migration of existing data**: EF Core migration on next startup
|
||||
auto-derives every existing composition. After deploy all compositions are
|
||||
derived; no mixed-mode code paths.
|
||||
- **Tree UX**: derived templates hidden by default. "Show derived templates"
|
||||
toggle on the tree page reveals them indented under their base. Always
|
||||
reachable from the parent's Compositions tab.
|
||||
|
||||
- **Re-composing the same base in two slots on the same parent**: e.g., Pump
|
||||
composes Sensor twice as `IntakeSensor` and `OutletSensor`. Two derived
|
||||
templates: `Pump.IntakeSensor` and `Pump.OutletSensor`. Both inherit from
|
||||
`Sensor`. Confirmed OK.
|
||||
## Confirmed semantics
|
||||
|
||||
- **Composition order / dependency**: if the user composes A inside B and
|
||||
later edits A's base — does B's derived template auto-pick up the changes?
|
||||
Answer per inheritance: yes for `IsInherited = true` fields, no for
|
||||
overrides. Aveva-consistent.
|
||||
- **Re-composing the same base on the same parent in two slots** (e.g. Pump
|
||||
composes Sensor twice as `IntakeSensor` and `OutletSensor`) produces two
|
||||
derived templates: `Pump.IntakeSensor` and `Pump.OutletSensor`, both
|
||||
inheriting from `Sensor`.
|
||||
|
||||
- **Cascade-delete confirmation**: deleting a base template that has
|
||||
derivatives — block with a clear error listing the derivatives, force user
|
||||
to delete them first? Aveva blocks. Likely we should too.
|
||||
- **Inheritance updates flow downward**: if a base attribute changes value
|
||||
later and the derivative has `IsInherited = true` for that attribute, the
|
||||
derived value updates. Once overridden (`IsInherited = false`), changes to
|
||||
the base no longer affect that field.
|
||||
|
||||
- **Validation**: if base adds an attribute, derived inherits it on next load.
|
||||
But what about derived overriding a field that base subsequently locks via
|
||||
`LockedInDerived`? Force-revert the override on next deploy? Surface as a
|
||||
validation error? Probably the latter.
|
||||
- **Subsequent `LockedInDerived` after overrides exist**: surface as a
|
||||
validation error at deploy time; do not force-revert silently.
|
||||
|
||||
Reference in New Issue
Block a user