Skip to content

Feat: Varied heating/cooling schedule approaches in STEBBS#1261

Merged
sunt05 merged 76 commits intomasterfrom
YL/STEBBS_schedule
Mar 31, 2026
Merged

Feat: Varied heating/cooling schedule approaches in STEBBS#1261
sunt05 merged 76 commits intomasterfrom
YL/STEBBS_schedule

Conversation

@yiqing1021
Copy link
Copy Markdown

@yiqing1021 yiqing1021 commented Mar 23, 2026

Summary

This PR extends STEBBS with configurable heating and cooling setpoint profiles, and improves robustness of wall and window surface-temperature calculations for the extreme WWR cases (0 and 1).

Description

This PR adds new STEBBS inputs for scheduled heating/cooling setpoints, wires the new model option through the data model and runtime path, and avoids unnecessary wall or window calculations when the corresponding surface does not exist.

1.1 New Input

  • HeatingSetpointTemperatureProfile
    User-defined ten-minute heating setpoint profile.

  • CoolingSetpointTemperatureProfile
    User-defined ten-minute cooling setpoint profile.

  • setpointmethod
    Model option controlling how space heating and cooling setpoints are determined in STEBBS.

    • 0: Constant
      Use fixed HeatingSetpointTemperature and CoolingSetpointTemperature throughout the day.

    • 1: Dependent
      Use user-provided setpoint temperatures with metabolism-dependent variation.

    • 2: Scheduled
      Use user-provided diurnal profiles from HeatingSetpointTemperatureProfile and CoolingSetpointTemperatureProfile.

1.2 New Function / New Features

  • Add support for scheduled heating and cooling setpoints in STEBBS.
  • Enable STEBBS to read and use HeatingSetpointTemperatureProfile and CoolingSetpointTemperatureProfile when setpointmethod = 2.
  • Propagate the new setpoint inputs through the Python data model, driver, and bridge layers.
  • Add WWR-based guards for surface-temperature calculations:
    • WWR = 0: skip window calculations
    • WWR = 1: skip wall calculations
    • 0 < WWR < 1: calculate both wall and window temperatures
  • Refactor the wall and window surface-energy calculation blocks to make the logic clearer and avoid unnecessary calculations for non-existent surfaces.

1.3 Validation logics

  • Add SetpointMethod to model.py list of physics model options
  • Add HeatingSetpointTemperatureProfile and CoolingSetpointTemperatureProfile ten minutes profiles to site.py
  • Extended all relevant YAML file to include new inputs
  • Add new registry rule validate_model_option_setpoint() to physics_rules.py:
  Validates that HeatingSetpointTemperature and CoolingSetpointTemperature are set
  in building_archetype when setpointmethod == 0 or 1.
  For setpointmethod == 2, validates that all entries in HeatingSetpointTemperatureProfile
  and CoolingSetpointTemperatureProfile are set (not null), and that heating values < 30.0,
  cooling values > 15.0.
  • Add new adjustment rule adjust_model_option_setpointmethod in phase_b.py:
  If setpointmethod == 0 or 1, set all entries in HeatingSetpointTemperatureProfile and
  CoolingSetpointTemperatureProfile in building_archetype to null for all sites.
  If setpointmethod == 2, set HeatingSetpointTemperature and CoolingSetpointTemperature
  in building_archetype to null for all sites (they are not needed).
  • Add tests for registry rule and adjustment rule in test_validation.py
  • Extend PHASE_B_DETAILED.md and PHASE_A_DETAILED.md with info about new checks and model option

@github-actions
Copy link
Copy Markdown

github-actions Bot commented Mar 23, 2026

CI Build Plan

Changed Files

Fortran source (4 files)

  • src/suews/src/suews_ctrl_driver.f95
  • src/suews/src/suews_ctrl_type.f95
  • src/suews/src/suews_phys_stebbs.f95
  • src/suews/src/suews_type_stebbs.f95

Rust bridge (6 files)

  • src/suews_bridge/c_api/building_archetype_prm.f95
  • src/suews_bridge/c_api/config.f95
  • src/suews_bridge/c_api/driver.f95
  • src/suews_bridge/src/building_archetype_prm.rs
  • src/suews_bridge/src/config.rs
  • src/suews_bridge/src/yaml_config.rs

Python source (11 files)

  • src/supy/_var_metadata.py
  • src/supy/data_model/core/config.py
  • src/supy/data_model/core/model.py
  • src/supy/data_model/core/profile.py
  • src/supy/data_model/core/site.py
  • src/supy/data_model/validation/pipeline/PHASE_A_DETAILED.md
  • src/supy/data_model/validation/pipeline/PHASE_B_DETAILED.md
  • src/supy/data_model/validation/pipeline/phase_a.py
  • src/supy/data_model/validation/pipeline/phase_b.py
  • src/supy/data_model/validation/pipeline/phase_b_rules/physics_rules.py
  • src/supy/sample_data/sample_config.yml

Tests (16 files)

  • test/core/data/issue_1097/yaml_setup.yml
  • test/data_model/test_data_model.py
  • test/data_model/test_validation.py
  • test/data_model/test_yaml_processing.py
  • test/fixtures/benchmark1/benchmark1.yml
  • test/fixtures/benchmark1/benchmark1_short.yml
  • test/fixtures/benchmark1/benchmark1b.yml
  • test/fixtures/data_test/AVL_1_LDN1/RunControl.nml
  • test/fixtures/data_test/AVL_6_310/RunControl.nml
  • test/fixtures/data_test/stebbs_test/sample_config.yml
  • test/fixtures/legacy_format/2018a/RunControl.nml
  • test/fixtures/legacy_format/2019a/RunControl.nml
  • test/fixtures/legacy_format/2020a/RunControl.nml
  • test/fixtures/precheck_testcase/precheck_testcase1.yml
  • test/fixtures/precheck_testcase/precheck_testcase2.yml
  • ...and 1 more

Documentation (10 files)

  • CHANGELOG.md
  • src/supy/data_model/core/config.py
  • src/supy/data_model/core/model.py
  • src/supy/data_model/core/profile.py
  • src/supy/data_model/core/site.py
  • src/supy/data_model/validation/pipeline/PHASE_A_DETAILED.md
  • src/supy/data_model/validation/pipeline/PHASE_B_DETAILED.md
  • src/supy/data_model/validation/pipeline/phase_a.py
  • src/supy/data_model/validation/pipeline/phase_b.py
  • src/supy/data_model/validation/pipeline/phase_b_rules/physics_rules.py

Build Configuration

Configuration
Platforms Linux x86_64, macOS ARM64, Windows x64
Python 3.9, 3.14
Test tier standard (all except slow)
UMEP build Yes (compiled extension may differ)
PR status Ready (standard matrix)

Rationale

  • Fortran source changed -> multiplatform build required
  • Rust bridge changed -> multiplatform build required
  • Python source changed -> single-platform build
  • Test files changed -> validation build
  • Compiled extension ABI may differ -> UMEP (NumPy 1.x) build included

Updated by CI on each push. See path-filters.yml for category definitions.

@github-actions
Copy link
Copy Markdown

Preview Deployed

Content Preview URL
Site https://suews.io/preview/pr-1261/
Docs https://suews.io/preview/pr-1261/docs/

Note

This preview is ephemeral. It will be lost when:

  • Another PR with site/ or docs/ changes is pushed
  • Changes are merged to master
  • A manual workflow dispatch runs

To restore, push any commit to this PR.

…odel_option_setpointmethod_2_invalid_slice_keys accordingly
@yiqing1021
Copy link
Copy Markdown
Author

Thank you @sunt05 , @dayantur and I have revised the code based on your comments. But we are still not fully confident about the suews-bridge changes in yaml_config.rs, so could you please take a look and let us know if they make sense? Many thanks again.

sunt05
sunt05 previously approved these changes Mar 31, 2026
Copy link
Copy Markdown

@sunt05 sunt05 left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Thanks @yiqing1021 for addressing all the previous review comments — the physics logic looks solid now. The CASE 0/1/2 branching, WWR guards, and 1..144 profile validation are all in good shape.

I'll push a small follow-up commit to tidy up a few minor items (typo, indentation, stray profiles.yml at repo root) and then merge.

…ev artefact

- Fix typo 'setpoinbts' -> 'setpoints' in suews_phys_stebbs.f95
- Add INTENT(IN) to wall_surface_active/window_surface_active in tstep
- Fix Python indentation in config.py and phase_b.py
- Correct old_value description in ScientificAdjustment
- Remove stray profiles.yml from repo root

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
@sunt05 sunt05 enabled auto-merge March 31, 2026 05:30
@sunt05 sunt05 added this pull request to the merge queue Mar 31, 2026
Merged via the queue into master with commit fbe57b4 Mar 31, 2026
18 checks passed
sunt05 added a commit that referenced this pull request Mar 31, 2026
Resolve merge conflicts between forcing-height validation (this branch)
and setpointmethod validation (master, PR #1261). Both features are
independent additions to physics_rules.py and CHANGELOG.md.

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
sunt05 added a commit that referenced this pull request Apr 19, 2026
Registers the first real cross-release upgrade handler alongside the
identity placeholder in `src/supy/util/converter/yaml_upgrade.py`. The
handler migrates YAMLs produced by release `2026.1.28` (and its
`.dev0` sibling) into the current `2025.12` schema:

  * relocates each site's profile-shaped
    `HeatingSetpointTemperature` / `CoolingSetpointTemperature`
    building-archetype fields into the post-#1261
    `*Profile` siblings, and seeds the scalar form expected by the
    current validator from the first working-day value;
  * sets `model.physics.setpointmethod = 2` (SCHEDULED) so the
    migrated run honours the supplied hourly schedule by default.

Adds a retrofit schema label `2026.1` for the pre-#1261 shape and
maps the affected package tags through `_PACKAGE_TO_SCHEMA`. The
`_HANDLERS` registry now carries the real `(2026.1, 2025.12)`
transition.

Tests:

  * `test/fixtures/release_configs/2026.1.28.yml` - vendored verbatim
    from tag `2026.1.28` via `git show
    2026.1.28:src/supy/sample_data/sample_config.yml`, per the
    policy in the sibling README.
  * `test_release_compat.py` is split on upgrade-need: current-schema
    fixtures still parse directly; pre-drift fixtures (auto-detected
    from `_PACKAGE_TO_SCHEMA`) must upgrade and then parse via the
    same pipeline a user would invoke.
  * `test_yaml_upgrade.py` gains targeted regressions for the new
    handler: it renames the two profile fields, preserves their
    contents, stamps `schema_version`, and defaults
    `setpointmethod` to SCHEDULED.

Refs #1301, #1304. Post-#1306 follow-up: turns the upgrade CLI from
scaffold into a path that actually unblocks existing user YAMLs.
sunt05 added a commit that referenced this pull request Apr 20, 2026
CURRENT_SCHEMA_VERSION stayed at "2025.12" through several breaking
changes (#879 STEBBS clean-up, #1240 DeepSoilTemperature rename, #1242
DHW volume-bound removal, #1261 setpoint split). The YAML-upgrade
dispatch had no real schema versions to key on, get_schema_compatibility_message
returned inverted verdicts, and StebbsProperties' default extra="ignore"
silently swallowed removed fields.

Phase A - retrospective bump:
- CURRENT_SCHEMA_VERSION -> 2026.4
- SCHEMA_VERSIONS populated with 2025.12 / 2026.1 / 2026.4 entries
- COMPATIBLE_VERSIONS lineage extended monotonically
- sample_config.yml schema_version synced to 2026.4

Phase B - YAML upgrade tooling on real schema versions:
- _PACKAGE_TO_SCHEMA maps release tags to real schema versions; synthetic
  labels retired, _HANDLERS dispatch keys monotonic
- New _migrate_2025_12_to_2026_1 absorbs the #879 clean-up (Wallx1/Roofx1
  -> *OuterCapFrac rename, IndoorAirStartTemperature /
  OutdoorAirStartTemperature -> Initial* rename, drop DHWVesselEmissivity
  plus runtime-state fields with logged reasons)
- _migrate_2026_1_to_current extended for #1240 / #1242 / #1261
- TestNoSilentFieldDrops asserts each source STEBBS key either survives
  or appears in a rename/drop/split log line

Phase C - guardrails:
- New rule .claude/rules/python/schema-versioning.md
- CI gate .github/workflows/schema-version-audit.yml + backing script
  scripts/lint/check_schema_version_bump.py; bypass via schema-audit-ok
  label
- pytest test_schema_version_sync.py asserts sample_config carries
  CURRENT_SCHEMA_VERSION on every PR
- prep-release skill gained a schema-audit step; audit-pr skill
  acknowledges the CI gate
sunt05 added a commit that referenced this pull request Apr 20, 2026
Closes the remaining gaps in the retrospective schema-version work:

- docs: rewrite schema_versioning.rst onto the actual CalVer lineage
  (2025.12 / 2026.1 / 2026.4) and the migration-registry compatibility
  model; add a 'YAML Schema Migrations' section to transition_guide.rst
  walking users through the 2026.1 (#879) and 2026.4 (#1240/#1242/#1261)
  upgrades; refresh schema-developer.rst and schema_cli.rst; note the
  migration chain in version-history/v2026.4.3.rst
- audit: extend check_schema_version_bump.py to require a matching doc
  edit when CURRENT_SCHEMA_VERSION moves; broaden the workflow path
  filter to pick up schema doc changes; add regression tests for the
  merge-base + repo-root semantics
- hardening: narrow the lazy-import in SchemaMigrator to ImportError
  only (so genuine registration bugs surface), guard the CalVer
  fallback path against synthetic hops without a registered handler
  (was silently no-op'ing), and cache the migration-pair registry used
  by is_schema_compatible
- rule + audit-pr skill: Step 6 of schema-versioning.md lists the exact
  RST files that must move with every bump; audit-pr checklist + steps
  mirror the rule so review catches silent-docs PRs before CI does
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

3 participants