Skip to content

fix(octave): guard isvalid calls so Octave CI passes#146

Merged
HanSur94 merged 3 commits into
mainfrom
claude/fix-octave-isvalid
May 19, 2026
Merged

fix(octave): guard isvalid calls so Octave CI passes#146
HanSur94 merged 3 commits into
mainfrom
claude/fix-octave-isvalid

Conversation

@HanSur94
Copy link
Copy Markdown
Owner

Summary

Octave 7+ does not implement isvalid() for classdef handles — every unguarded isvalid(...) call on a user-defined handle throws 'isvalid' undefined. The project already has a self-handle polyfill (DashboardEngine.isObjValid_), but several call sites on non-self handles (widgets, FastSense objects, cached widget refs) bypass it. The latest Octave CI run (https://github.com/HanSur94/FastSense/actions/runs/25863120537) reports these as the dominant failure mode.

Smallest-possible surgical patch: at each unguarded site, inline isOctave = exist('OCTAVE_VERSION', 'builtin') ~= 0; and short-circuit the isvalid() check on Octave. Behaviour on MATLAB is unchanged.

Sites touched (5 in 3 files)

File Line(s) Function Pattern
libs/Dashboard/DashboardEngine.m 2022 refreshActivePageWidgetsAfterResize_ Pass 1 ~isvalid(w) -> (~isOctave && ~isvalid(w))
libs/Dashboard/DashboardEngine.m 2045 refreshActivePageWidgetsAfterResize_ Pass 2 ~isvalid(w) -> (~isOctave && ~isvalid(w))
libs/Dashboard/DashboardEngine.m 2048 refreshActivePageWidgetsAfterResize_ Pass 2 ~isvalid(w.FastSenseObj) -> (~isOctave && ~isvalid(w.FastSenseObj))
libs/Dashboard/FastSenseWidget.m 453 autoScaleY_ (Follow-mode guard) isvalid(obj.FastSenseObj) -> (isOctave || isvalid(obj.FastSenseObj))
libs/Dashboard/DashboardLayout.m 1038 syncYLimitButtonsState_ (cached widget ref) isvalid(w) -> (isOctave || isvalid(w))

The two DashboardEngine sites in Pass 1/Pass 2 share one isOctave flag at the top of the function; the other two files declare the flag inline next to the guard.

Octave tests this unblocks (from the failing CI log)

  • test_dashboard_perf_fixes::test_engine_preview_nbuckets_reset (line 2022)
  • test_dashboard_preview_envelope (autoScaleY_ at line 453, then syncYLimitButtonsState_ at 1038)
  • test_fastsense_widget_ylimit_modes::test_set_y_limit_mode_* (5 cases, all hit line 453)
  • test_fastsense_widget_ylimit_modes::test_follow_mode_still_short_circuits_autoscale (line 453)
  • suite/TestFastSenseWidget::testPropertiesForwardToInnerFastSense, testRefreshTriggersRerenderOnAdded, testRefreshTriggersRerenderOnOpenToClosed (line 453)
  • suite/TestSensorStaleDetection::testDetectStaleWithFrozenSensor (line 453)
  • The four secondary refreshActivePageWidgetsAfterResize_ failures observed downstream in the same CI run

What I deliberately did NOT touch

  • DashboardEngine.m:2086-2087 (isWidgetLineWhite_) — already inside a try/catch block; Octave swallows the error.
  • DashboardEngine.m:1844, 521, 1861, 1871, 1892, 1934, 3095 — all inside try/catch or guard timer (UDD) handles that Octave handles differently.
  • libs/FastSenseCompanion/** — companion is gated behind a notSupported throw on Octave (constructor line 103). The "warning: error caught while executing handle class delete method" in test_companion_shell is cosmetic (test still PASSES on Octave per CI log).
  • libs/FastSense/HoverCrosshair.m — MATLAB-only, tests skip with SKIPPED (Octave: HoverCrosshair is MATLAB-only — uses isvalid).
  • libs/Dashboard/DashboardToolbar.m:311/315 — only reached via the Follow toolbar toggle, no current Octave test exercises it.
  • The existing isObjValid_ self-handle polyfill — reused as-is at the entry guard of refreshActivePageWidgetsAfterResize_, only the per-widget probes needed changing.

Test plan

  • Octave CI on this branch now runs test_dashboard_perf_fixes to completion (no isvalid failure on test_engine_preview_nbuckets_reset).
  • test_dashboard_preview_envelope reaches the envelope assertions instead of erroring inside autoScaleY_.
  • test_fastsense_widget_ylimit_modes runs all test_set_y_limit_mode_* cases without the near line 453 error.
  • MATLAB CI is unchanged (the guard short-circuits to the original isvalid call on MATLAB).
  • No new MISS_HIT mh_style / mh_lint violations in the three touched files (verified locally).

HanSur94 added 3 commits May 19, 2026 08:40
Octave 7+ has no isvalid() for classdef handles, so the three unguarded
isvalid(w) / isvalid(w.FastSenseObj) calls in DashboardEngine line 2022
and 2045/2048 broke Octave CI (test_engine_preview_nbuckets_reset).
Inline an isOctave flag and short-circuit the check on Octave; behaviour
unchanged on MATLAB.
Octave 7+ has no isvalid() for classdef handles, so the unguarded
isvalid(obj.FastSenseObj) check in autoScaleY_ broke every test that
renders a FastSenseWidget or calls setYLimitMode (testDetectStaleWithFrozenSensor,
testRefreshTriggers*, test_set_y_limit_mode_*, test_dashboard_preview_envelope).
Inline an isOctave flag and short-circuit on Octave.
Octave 7+ has no isvalid() for classdef handles. Once autoScaleY_ is
fixed, dashboard tests proceed to addYLimitButtons_ which calls
syncYLimitButtonsState_ — the unguarded isvalid(w) on the cached widget
handle would then throw. Inline isOctave and short-circuit on Octave.
@codecov
Copy link
Copy Markdown

codecov Bot commented May 19, 2026

Codecov Report

❌ Patch coverage is 87.50000% with 1 line in your changes missing coverage. Please review.

Files with missing lines Patch % Lines
libs/Dashboard/DashboardEngine.m 75.00% 1 Missing ⚠️

📢 Thoughts on this report? Let us know!

Copy link
Copy Markdown
Contributor

@github-actions github-actions Bot left a comment

Choose a reason for hiding this comment

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

⚠️ Performance Alert ⚠️

Possible performance regression was detected for benchmark 'FastSense Performance'.
Benchmark result of this commit is worse than the previous benchmark result exceeding threshold 1.10.

Benchmark suite Current: e19b113 Previous: 17a9ff3 Ratio
Downsample mean std(1M) 0.022 ms 0.006 ms 3.67
Instantiation mean std(1M) 1.339 ms 1.207 ms 1.11
Render mean std(1M) 1.546 ms 1.153 ms 1.34
Downsample mean std(5M) 0.086 ms 0.026 ms 3.31
Instantiation mean std(5M) 0.455 ms 0.319 ms 1.43
Zoom cycle mean std(5M) 0.552 ms 0.463 ms 1.19
Zoom cycle mean ( std00M) 0.783 ms 0.622 ms 1.26
Render mean ( std00M) 96.912 ms 10.524 ms 9.21
Zoom cycle mean ( std00M) 0.807 ms 0.622 ms 1.30
Dashboard create+render mean 1134.795 ms 974.447 ms 1.16
Dashboard live tick stdmean 2.571 ms 1.295 ms 1.99
Dashboard page switch stdmean 1.917 ms 0.081 ms 23.67
Dashboard broadcastTimeRange stdmean 0.174 ms 0.143 ms 1.22

This comment was automatically generated by workflow using github-action-benchmark.

CC: @HanSur94

@HanSur94 HanSur94 merged commit 13534e0 into main May 19, 2026
16 of 18 checks passed
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.

1 participant