Skip to content

Updates related to demand_tech in SLC framework#784

Merged
johnjasa merged 18 commits into
NatLabRockies:developfrom
elenya-grant:slc/upstream_demand
Jul 8, 2026
Merged

Updates related to demand_tech in SLC framework#784
johnjasa merged 18 commits into
NatLabRockies:developfrom
elenya-grant:slc/upstream_demand

Conversation

@elenya-grant

@elenya-grant elenya-grant commented Jun 17, 2026

Copy link
Copy Markdown
Collaborator

Updates related to demand_tech in SLC framework

READY FOR REVIEW OF ALL TYPES

This PR aims to resolve two issues related to SLC:

In this draft implementation, I've required that the user specify the demand technology in the system_level_control section of the plant configuration file. This looks like below:

system_level_control:
  control_strategy: DemandFollowingControl
  demand_component: h2_load_demand # this is new
  solver_options:
    solver_name: gauss_seidel
    max_iter: 20
    convergence_tolerance: 1.0e-6

Background and Questions for reviewers on the above implementation:
An alternative approach would be have the demand_component defined under the control_parameters section. The reason I did not do that approach is to be consistent with the current organization, usage, and distinction between slc_config and control_parameters. The SLC gets two "configuration" dictionaries, slc_config and control_parameters. slc_config is created in H2IntegrateModel._classify_slc_technologies(). The slc_config contains information that is used by both H2IntegrateModel and the SLC for set-up and connection logic. The parameters within the control_parameters dictionary are controller-specific parameters that is only accessed within the SLC (not used by H2IntegrateModel). This is my justification for the route I went, but I'd be curious to hear opinions on the alternative approach if a reviewer finds it appealing.

This simplifies some of the logic in H2IntegrateModel_classify_slc_technologies(). I've also updated it so that only technologies that are upstream and connected to the demand technology are included in the information contained in the slc_config.

Additional Questions for reviewers are noted in Section 2

Example use-cases that would be enabled with this functionality:

  • demand component downstream of the demand component specified for SLC: may be used as the commodity stream for a finance subgroup if wanting to calculate the LCO with a commodity stream that is saturated below some value
  • demand component upstream of the demand component specified for SLC:
    • may be used similar to a splitter (but is able to be used a commodity stream for finance groups - splitters cannot be used as a commodity stream for finance groups).
    • may be used to intentionally manipulate some SLC behavior. If we have the system used in Example 12 and we want the ammonia plant to operate at 90% CF, then we may pre-calculate the hydrogen demand required to achieve that 90% CF and have that demand used in the hydrogen system. The ammonia demand (which is the demand component for the SLC) would also be targeted at the 90% CF - but the SLC would not be aware of the excess hydrogen that is curtailed from the hydrogen system to enforce this.

Section 1: Type of Contribution

  • Feature Enhancement
    • Framework
    • New Model
    • Updated Model
    • Tools/Utilities
    • Other (please describe):
  • Bug Fix
  • Documentation Update
  • CI Changes
  • Other (please describe):

Section 2: Draft PR Checklist

  • Open draft PR
  • Describe the feature that will be added
  • Fill out TODO list steps
  • Describe requested feedback from reviewers on draft PR
  • Complete Section 7: New Model Checklist (if applicable)

TODO:

  • Remove commented out code in methods changed in H2IntegrateModel

Section 3: General PR Checklist

  • PR description thoroughly describes the new feature, bug fix, etc.
  • Added tests for new functionality or bug fixes
  • Tests pass (If not, and this is expected, please elaborate in the Section 6: Test Results)
  • Documentation
    • Docstrings are up-to-date
    • Related docs/ files are up-to-date, or added when necessary
    • Documentation has been rebuilt successfully
    • Examples have been updated (if applicable)
  • CHANGELOG.md
    • At least one complete sentence has been provided to describe the changes made in this PR
    • After the above, a hyperlink has been provided to the PR using the following format:
      "A complete thought. [PR XYZ]((https://github.com/NatLabRockies/H2Integrate/pull/XYZ)", where
      XYZ should be replaced with the actual number.

Section 4: Related Issues

Resolves Issue #739 and #740

TODO: make an issue for the possible future use-case of having multiple demand components feed into the SLC (or even if thats a use-case worth considering)

Section 5: Impacted Areas of the Software

Section 5.1: New Files

  • h2integrate/core/test/test_slc_framework.py: added in tests for H2Integrate._classify_slc_technologies()
  • h2integrate/core/test/inputs/tech_connection_cases.yaml: input file for tests in h2integrate/core/test/test_slc_framework.py
  • examples/35_system_level_control/upstream_demand/*: new example for integration testing of new functionality

Section 5.2: Modified Files

  • H2IntegrateModel in h2integrate/core/h2integrate_model.py
    • __init__(): Updated call to create_technology_graph()
    • create_technology_graph(): updated to take an input list of tech connections and return the graph (rather than set it as an attribute) so it can be used in _classify_slc_technologies()
    • _classify_slc_technologies():
      • updated to use demand_component specified in the system_level_control config instead of looping through technology_interconnections. This included adding in checking for the following cases where an error is raised:
        • demand_tech is missing from the system_level_control section in the plant config
        • the technology specified as the demand_tech is missing from the technology config
        • the technology specified as the demand_tech is not connected in technology_interconnections
        • the technology specified as the demand_tech is not a valid demand technology type (i.e., the performance model name does not include "DemandComponent")
      • updated so that only technologies that are upstream and have a path to the specified demand_tech are included in the tech_to_commodity and technology_graph parameters of the SLC config.
  • examples/35_system_level_control/*/plant_config.yaml: added in demand_component to system_level_control section.
  • h2integrate/control/control_strategies/system_level/test/test_slc_examples.py: added new test named test_slc_upstream_demand that tests the example examples/35_system_level_control/upstream_demand/

Section 6: Additional Supporting Information

Section 7: Test Results, if applicable

@elenya-grant elenya-grant added ready for review This PR is ready for input from folks dispatch related to dispatch and control labels Jun 17, 2026

@genevievestarke genevievestarke left a comment

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

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

I really like this functionality, thank you @elenya-grant !! I think it's much clearer what's happening in the code.
I don't have a problem with called the input demand_component since it needs to be a demand module to use system level control.
I don't think that we should throw an error for having upstream demand components in the system as long as it doesn't change the behavior of the system level control. I'm still working through why you would want a second demand component (so you can see how much of a steady-state demand you've met, maybe?).
It looks good to me!

@jaredthomas68 jaredthomas68 left a comment

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

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

This looks fine to me, but I am concerned we are running in to the difficulties to start with because our SLC is not as extensible as it should be. This PR helps, but I think we may want to have some more discussions around how to make the SLC as extensible and modular as the rest of H2I.

Comment thread h2integrate/core/h2integrate_model.py Outdated
slc_config["tech_to_commodity"] = tech_to_commodity
slc_config["storage_techs_to_control"] = storage_tech_to_control
slc_config["technology_graph"] = self.technology_graph
slc_config["technology_graph"] = tech_graph

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

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

If you need to create tech_graph for line length purposes, can we keep the assignment close by so there is no concern about tech_graph in the local scope diverging from the the class attribute self.technology_graph? I'm also concerned about them diverging with the use of the new create_technology_graph method.

Copy link
Copy Markdown
Collaborator Author

Choose a reason for hiding this comment

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

talked to Jared - call tech_graph like upstream_tech_graph or local_tech_graph to make it clear that its not the entire technology graph. maybe consider renaming slc_config["technology_graph"] to slc_config["slc_technology_graph"].

Copy link
Copy Markdown
Collaborator Author

Choose a reason for hiding this comment

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

I changed the name from tech_graph to upstream_tech_graph

@kbrunik kbrunik left a comment

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

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

Feeling good about this from a high-level, seems like this is making the SLC more explicit and allowing for the use of multiple demand components.

Feeling good about demand_component, I'm not married to it because I could imagine SLC at some point not requiring demand as an input.

Agreed with @genevievestarke let's not throw an error, it makes it more flexible for folks.

@kbrunik kbrunik marked this pull request as ready for review June 30, 2026 19:39
@johnjasa

johnjasa commented Jul 6, 2026

Copy link
Copy Markdown
Collaborator

There's enough overlap and potential confusion between slc_config and the control_parameters section of the plant_config's SLC section that I'm going to push up a change now where we change slc_config to slc_topology. This avoids the confusion of potentially having another "config" object that doesn't really behave like the tech, plant, or driver configs. @elenya-grant going into detail in the PR body about the intricate differences between those configs makes me think this is a worthwhile and good change. Let me know if you disagree!

@johnjasa johnjasa left a comment

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

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

Thanks for this improvement! I've pushed some changes directly to the branch, primarily the renaming of slc_config to slc_topology for clarity. This is ready to come in, imo. I know that SLC is a continual work in progress and this is a nice step forward!

@johnjasa johnjasa marked this pull request as draft July 8, 2026 16:36
@johnjasa johnjasa marked this pull request as ready for review July 8, 2026 16:36
@johnjasa johnjasa enabled auto-merge (squash) July 8, 2026 16:36
@johnjasa johnjasa marked this pull request as draft July 8, 2026 16:57
auto-merge was automatically disabled July 8, 2026 16:57

Pull request was converted to draft

@johnjasa johnjasa marked this pull request as ready for review July 8, 2026 16:57
@johnjasa johnjasa merged commit 241c7a4 into NatLabRockies:develop Jul 8, 2026
12 checks passed
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

dispatch related to dispatch and control ready for review This PR is ready for input from folks

Projects

None yet

Development

Successfully merging this pull request may close these issues.

5 participants