Skip to content

BUG: apply wind factors to the ensemble member that was selected - #1160

Merged
Gui-FernandesBR merged 1 commit into
RocketPy-Team:developfrom
thc1006:bug/ensemble-member-overwrites-wind-factor
Aug 15, 2026
Merged

Gui-FernandesBR merged 1 commit into
RocketPy-Team:developfrom
thc1006:bug/ensemble-member-overwrites-wind-factor

Conversation

@thc1006

@thc1006 thc1006 commented Aug 14, 2026 •

Copy link
Copy Markdown
Contributor

Pull request type

  • Code changes (bugfix, features)

Checklist

  • Tests for the changes have been added (if needed)
  • Docs have been reviewed and added / updated
  • Lint (ruff check / ruff format --check) has passed locally
  • All tests (pytest tests/unit tests/integration) have passed locally

Current behavior

StochasticEnvironment.create_object() walks the generated dictionary and, when it meets ensemble_member, calls select_ensemble_member(). That call rebuilds the wind functions from the chosen member's own profile.

ensemble_member sits in exception_list, so _set_stochastic() skips it and _validate_ensemble() sets it after the base constructor has already put the wind factors in __dict__. The factors are therefore reached first, scaled into whichever member was loaded at construction, and then overwritten.

With two members whose winds are 10 and 30, member 1 selected and a factor of 2, the flight gets 30. The input record still says the factor was applied.

StochasticEnvironment(
    environment=ensemble_env,
    ensemble_member=[1],
    wind_velocity_x_factor=(2.0, 0),
)

A determinism test would not catch this: the same seed is consistently wrong.

New behavior

Factors are collected during the loop and applied after it, so which entry __dict__ happens to hold first no longer decides the result. When a member was selected, the baseline is the profile that member just loaded; otherwise it is the construction-time value, so repeated calls still do not compound.

The example above now gives 60.

Breaking change

  • No

Runs that combined an ensemble with a wind factor were silently ignoring the factor, so their results change. That was the bug.

Additional information

Three tests, filling the test_validate_ensemble gap that was commented out in tests/unit/stochastic/test_stochastic_environment.py:

  • the selected member's wind is scaled, rejecting both 30 (factor dropped) and 20 (member 0's cached wind)
  • repeated create_object() calls stay at 60 rather than compounding
  • without ensemble members the factor still multiplies the construction value

Reverting the fix turns the first two red; so does keeping the construction-time baseline after a member switch. The third stays green under both, which is what tells them apart.

Local run against develop at 1d04bcc: ruff clean, pylint exit 0, pytest tests/unit tests/integration 2216 passed, 51 skipped.

@thc1006
thc1006 requested a review from a team as a code owner August 14, 2026 16:32
@codecov

codecov Bot commented Aug 14, 2026 •

Copy link
Copy Markdown

Codecov Report

✅ All modified and coverable lines are covered by tests.
✅ Project coverage is 84.32%. Comparing base (7edbbc8) to head (3dc4ee7).
⚠️ Report is 3 commits behind head on develop.

Additional details and impacted files
@@             Coverage Diff             @@
##           develop    #1160      +/-   ##
===========================================
+ Coverage    84.28%   84.32%   +0.04%     
===========================================
  Files          130      130              
  Lines        17252    17258       +6     
===========================================
+ Hits         14540    14553      +13     
+ Misses        2712     2705       -7     

☔ View full report in Codecov by Harness.
📢 Have feedback on the report? Share it here.

🚀 New features to boost your workflow:
  • ❄️ Test Analytics: Detect flaky tests, report on failures, and find test suite problems.

select_ensemble_member() rebuilds the wind functions from the chosen member's
own profile, and create_object() reached it after the factors because that is
where __dict__ happened to put it. The factor was scaled into the previous
member's wind and then thrown away, so the run flew the raw member wind while
the input record still reported a factor.

Factors are now applied once the loop is done, so the order of __dict__ stops
mattering, and the baseline is the member just loaded rather than the value
cached at construction.

Signed-off-by: thc1006 <84045975+thc1006@users.noreply.github.com>
@Gui-FernandesBR
Gui-FernandesBR force-pushed the bug/ensemble-member-overwrites-wind-factor branch from 8c37fbb to 3dc4ee7 Compare August 15, 2026 02:26
@Gui-FernandesBR
Gui-FernandesBR merged commit f604534 into RocketPy-Team:develop Aug 15, 2026
8 checks passed
@thc1006
thc1006 deleted the bug/ensemble-member-overwrites-wind-factor branch August 15, 2026 07:39
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.

2 participants