Skip to content

Sequence payload merges values across templates for parameters inherited from a shared base class #620

Description

@AntoineGautier

constructSelectionPath (client/src/interpreter/interpreter.ts:23) builds each selection key as `${optionPath}-${instancePath}`, where optionPath is the parameter's modelicaPath — i.e. the class where the parameter is declared. When two templates contain an instance at the same relative instancePath whose type is redeclared to different concrete classes, and the toggled parameter is declared in a common base class of those concrete classes, the optionPath (base class) and the instancePath are both identical, so the two templates produce the same key.

DownloadModal.getSequenceData() (client/src/components/modal/DownloadModal.tsx:50) then merges the per-config values under that one key into a single array, and mogrifier evaluates section toggles with any() over it — so a subsection is kept if any selected template uses the feature, and attributed to the wrong template's section in the generated document.

Root cause

The key uses the parameter's declaration site rather than a canonical Modelica path anchored at the concrete template. It should be, e.g.:

Buildings.Templates.ZoneEquipment.VAVBoxCoolingOnly.ctl.have_reqNeeCoo
Buildings.Templates.ZoneEquipment.VAVBoxReheat.ctl.have_reqNeeCoo

which are distinct and carry the template context, instead of:

Buildings.Templates.ZoneEquipment.Components.Interfaces.ControllerG36VAVBox.have_reqNeeCoo-ctl.have_reqNeeCoo

which discards it.

Impact

  • mogrifier cannot resolve a toggle to the correct template's value; any() is the only thing it can do with the merged array.
  • Any sequence template with per-template sections that reference an inherited parameter is affected.

Proposed fix: group by template, keep templates separate

Note

Canonical Modelica paths in the payload are still the correct long-term data model. But that's a major refactoring impacting config store keys, modifier/redeclare resolution, evaluatedValues, record redirection, and the display-option tree.
The proposed fix is scoped to the sequence generation, with minimum refactoring effort.

The declaration-site keys are unambiguous within a single config — inside one config, ctl.have_reqNeeCoo resolves to one value. The collision is created solely by merging configs of different templates into one dict. The interpreter, path construction, value resolution, and redeclare handling are not involved and do not need to change.

Collapse configs of the same template. Keep different templates in separate dicts.

  1. Client — getSequenceData(): groupBy(projectConfigs, "templatePath"), run the current per-config merge within each group, and emit:

    {
      "<templatePath>": { ...mergedEvaluatedValues, ...mergedSelections },
      ...
      "DEL_INFO_BOX": [...],
      "UNITS": [...]
    }
    

    The top-level Buildings.Templates.ZoneEquipment list (consumed by block-selector toggles) becomes the set of present group keys — same mechanism as today.

  2. Server: passthrough; update SequenceData type in server/src/sequence/index.ts.

  3. mogrifier — scope nested toggles per template block (single walk): when entering a template Heading 3 block kept by its block toggle, resolve the toggle's short IDs to templatePath(s) via mappings.csv ([EQUALS VAV RH]RH…VAVBoxReheat; [ANY VAV PFBCV SFBCV]{…FanParallelConstant, …FanSeriesConstant}, whose group dicts are merged for that block). Evaluate that block's nested toggles against the selected group dict(s). Toggles outside any template block use a global union dict.

  4. mappings.csv: unchanged — keys stay unambiguous within a template group.

Important

The refactoring must cover the case where the sequence document includes a single section covering multiple system types (e.g. parallel and series fan-powered box), which may be configured differently. To handle such a case, we need to implement specific merge logic.

Activity

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Metadata

Metadata

Assignees

No one assigned

    Labels

    Top PriorityTop of the Priority ListbugSomething isn't working

    Type

    No type

    Projects

    No projects

      Milestone

      No milestone

      Relationships

      None yet

      Development

      No branches or pull requests

      Issue actions