fix: adding a beat could wipe a beat timeline after "Set amount in measure" - #577
Open
FelipeDefensor wants to merge 1 commit into
Open
fix: adding a beat could wipe a beat timeline after "Set amount in measure"#577FelipeDefensor wants to merge 1 commit into
FelipeDefensor wants to merge 1 commit into
Conversation
"Set amount in measure" puts an arbitrary number of beats in a measure, so beats_in_measure[-1] can hold more than the beat pattern prescribes for that slot. get_extension_from_beat_pattern treated that as impossible and raised, and extend_beats_in_measure only recognised an exactly-full measure as complete. Adding a beat in that state raised out of recalculate_measures. The command handler recovers by restoring the snapshot it took beforehand, but restoring re-runs the same code, so the recovery failed too and left the timeline empty -- every beat on it was lost. Both places now treat a measure at or over its prescribed size as full, so the extension starts a new measure instead.
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Summary
"Set amount in measure" puts an arbitrary number of beats in a measure — that is the point of the feature. So
beats_in_measure[-1]can legitimately hold more beats than the beat pattern prescribes for that slot.get_extension_from_beat_patterntreated that as impossible and raised:and
extend_beats_in_measureonly recognised an exactly full measure as complete, so it would have grown the over-full measure further rather than starting a new one.The data loss. Adding a beat in that state raises out of
recalculate_measures.TimelineUIs.on_timeline_commandrecovers by restoring the snapshot it took before the command — but restoring re-runsrecalculate_measures, hits the same exception, and aborts after clearing the timeline. The user gets an error dialog and an empty beat timeline; every beat is gone.Both places now treat a measure at or over its prescribed size as full, so the extension starts a new measure.
Reproducing on
dev4, add 24 beats →beats_in_measure == [4, 4, 4, 4, 4, 4]5→[4, 4, 4, 4, 5, 3][4, 4, 4, 4, 5]With this change step 4 gives
[4, 4, 4, 4, 5, 1]and all 22 beats are present.Test plan
test_add_beat_when_last_measure_is_fuller_than_beat_pattern— end-to-end through the commands, walks the steps above; raises ondevtest_starting_measure_fuller_than_beat_pattern— the previously-raising case;get_extension_from_beat_patternwas otherwise untested, so the two neighbouring cases (emptier / exactly as full) are pinned alongside ittests/test_app.pyfailures underpytest -n autoreproduce ondevwithout this change and pass serially)dev, 0 of 25 with this changeFound by fuzzing while reviewing #480; independent of it.
🤖 Generated with Claude Code