-
Notifications
You must be signed in to change notification settings - Fork 15
Perf/frontend #86
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Merged
Merged
Perf/frontend #86
Conversation
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
The throughput chart x-axis label said "Time (ms)" but the values displayed are actually in seconds. Fixed to show "Time (s)". 🤖 Generated with [Claude Code](https://claude.com/claude-code) Co-Authored-By: Claude Opus 4.5 <[email protected]>
D3's ordinal color scale assigns colors by domain position - the first key in domain gets the first color (purple), second gets the second color, etc. When flow rankings change, colorScale.domain(fkeys) is updated with the new order, but the legend DOM wasn't being updated to match. Changes: - Add colorDomainSet cache to prevent D3's auto-domain-extension when getFlowColor() is called with an unknown key (returns grey instead) - Change legend rebuild check from unordered to ordered comparison, since order determines color assignment - Add merge/update path to update color boxes on existing legend rows - Add allRows.order() to reorder DOM elements to match data order The DOM reorder only occurs when flow rankings actually change, not on every frame, so performance impact is minimal. 🤖 Generated with [Claude Code](https://claude.com/claude-code) Co-Authored-By: Claude Opus 4.5 <[email protected]>
Replace CBuffer of objects with TypedRingBuffer classes that store numeric data directly in Float64Arrays. This eliminates ~64 object allocations per update cycle for sample and pgap data. Changes: - Add TypedRingBuffer2 class for samples (timestamp, value) - Add TypedRingBuffer4 class for pgaps (timestamp, min, max, mean) - Update Series constructor to use typed ring buffers - Update updateSeries() to pass values directly (no object creation) - Update updateData() to pass values directly (no object creation) - Update resizeCBuf() and clearSeries() for new buffer types The typed buffers provide a CBuffer-compatible API (.size, .get(), .last(), .slice()) so consumer code (updateMainChartData, updateStats, updatePacketGapChartData) works unchanged. Object allocation now only happens when reading data for chart updates, not on every data ingestion. This significantly reduces GC pressure during high-frequency streaming updates. 🤖 Generated with [Claude Code](https://claude.com/claude-code) Co-Authored-By: Claude Opus 4.5 <[email protected]>
Profile-driven optimization reducing function self-time from 7.6% to 2.2% (71% reduction). Key optimizations: - Use indexed array iteration instead of Set iterator (avoids iterator allocation overhead) - Calculate maxSlice incrementally during bin building (eliminates separate O(bins × flows) loop) - Build formattedData array during bin creation (avoids Map.values() iterator) - Only sort when data is out of order (server typically sends sorted data) 🤖 Generated with [Claude Code](https://claude.com/claude-code) Co-Authored-By: Claude Opus 4.5 <[email protected]>
Cache D3 selections for axes, grids, and line paths in all chart modules to avoid repeated svg.select() calls in redraw(). Each select() creates new selection objects that form cycles with DOM nodes, triggering expensive Firefox Cycle Collector scans (observed 175ms CC events with 53,920 suspected objects). The pattern applied: - Add cachedSelections object with null properties - Clear selections in reset() before removing DOM (breaks cycles) - Cache selections when appending elements - Use cached selections in redraw() instead of svg.select() 🤖 Generated with [Claude Code](https://claude.com/claude-code) Co-Authored-By: Claude Opus 4.5 <[email protected]>
Add primitive field accessors (timestampAt, valueAt, minAt, maxAt, meanAt, lastTimestamp, lastValue, lastMin, lastMax, lastMean) that return values directly without allocating wrapper objects. Update callers (updateStats, updatePacketGapChartData, updateMainChartData) to use the new accessors instead of get()/last() which allocate objects. Also add _selfTest() methods and runRingBufferSelfTests() for verifying the new accessors match the allocating ones (callable via console). 🤖 Generated with [Claude Code](https://claude.com/claude-code) Co-Authored-By: Claude Opus 4.5 <[email protected]>
Instead of clearing arrays and creating new objects each update, reuse existing objects by mutating their properties. New objects are only allocated during initial fill. This reduces Firefox Cycle Collector workload: - Suspected objects: 53,920 → 18,554 (65% reduction) - Max CC slice: 20ms → 9ms (55% reduction) 🤖 Generated with [Claude Code](https://claude.com/claude-code) Co-Authored-By: Claude Opus 4.5 <[email protected]>
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.
No description provided.