Summary
Two unit tests are flaky (intermittent failures locally and in CI), both due to timing races where the test waits a fixed amount rather than on the actual condition.
1. src/plugins/imagery/pluginSpec.js — "should show the clicked thumbnail as the main image"
Failure signature: Expected -1 not to equal -1.
Measured baseline flake rate: ~12–40% across local runs.
Root cause: Imagery history loads asynchronously (requestCollection), and the view re-focuses the most recent image every time imageHistory changes. The imageHistory deep watcher sets focus to the latest image and only restores the user's selection when matchIndexOfPreviousImage succeeds. The test clicks the thumbnail after a fixed two nextTick()s and asserts after one more, so a history update landing just after the click resets the focused image back to the most recent one, and the assertion fails.
2. src/plugins/performanceIndicator/pluginSpec.js — "calculates an fps value"
Failure signature: Expected NaN to be greater than 0.
Root cause: The indicator only replaces its initial ~ fps text after a full second of animation frames. The test loops a fixed number of frames (> 90); when requestAnimationFrame runs faster than realtime (e.g. headless CI), 90 frames complete in under a second, so the fps value is never calculated and parseInt('~') yields NaN.
Proposed fix
Replace the fixed waits with condition-based polling: wait for imagery history to settle before selecting a thumbnail (and select until the selection takes effect), and loop animation frames until the fps text is actually calculated rather than a fixed frame count.
Summary
Two unit tests are flaky (intermittent failures locally and in CI), both due to timing races where the test waits a fixed amount rather than on the actual condition.
1.
src/plugins/imagery/pluginSpec.js— "should show the clicked thumbnail as the main image"Failure signature:
Expected -1 not to equal -1.Measured baseline flake rate: ~12–40% across local runs.
Root cause: Imagery history loads asynchronously (
requestCollection), and the view re-focuses the most recent image every timeimageHistorychanges. TheimageHistorydeep watcher sets focus to the latest image and only restores the user's selection whenmatchIndexOfPreviousImagesucceeds. The test clicks the thumbnail after a fixed twonextTick()s and asserts after one more, so a history update landing just after the click resets the focused image back to the most recent one, and the assertion fails.2.
src/plugins/performanceIndicator/pluginSpec.js— "calculates an fps value"Failure signature:
Expected NaN to be greater than 0.Root cause: The indicator only replaces its initial
~ fpstext after a full second of animation frames. The test loops a fixed number of frames (> 90); whenrequestAnimationFrameruns faster than realtime (e.g. headless CI), 90 frames complete in under a second, so the fps value is never calculated andparseInt('~')yieldsNaN.Proposed fix
Replace the fixed waits with condition-based polling: wait for imagery history to settle before selecting a thumbnail (and select until the selection takes effect), and loop animation frames until the fps text is actually calculated rather than a fixed frame count.