Repository navigation
bug(desktop): Settings Usage can hang after selecting the All range #5019
Description
What happened
When running Desktop from the latest main, opening Settings → Usage and changing the time range to All can make the application completely unresponsive with an existing local Usage history.
The Usage page stops responding and does not recover within the observed time. Command+Q also does not cause the Electron application to exit. I have to return to the terminal and manually kill the Electron processes.
Expected behavior:
- Selecting All should keep the Desktop responsive while Usage data is loading.
- The page should present a loading, partial, or paginated state rather than materializing an unbounded activity history.
- The application should remain possible to quit while a Usage query is running.
How to reproduce
- Build and run Desktop from commit
5a1514c1donmain. - Use an existing local profile containing accumulated model-call and tool-usage history.
- Open Settings.
- Select Usage.
- Change the time range to All.
- Observe that the Usage page and application become unresponsive.
- Press
Command+Q. - Observe that the Electron application remains running.
- Kill the Electron processes manually from the terminal.
The issue appears to depend on the amount of accumulated Usage data. I have not yet reduced it to an exact record-count threshold or reproduced it with a clean profile.
Environment
- Maka version or commit:
5a1514c1d - Branch:
main - OS and version: macOS 15.6 (
24G84), arm64 - Surface: Desktop, running from source
- Node.js version:
v24.19.0 - npm version:
11.17.0
Logs, screenshots, or additional context
This report is related to the same Settings → Usage read path as #4058 and #4068, but the observed defect is different:
- fix(runtime-host): serve one revision-consistent Usage snapshot #4058 tracks revision consistency across summary, activity, and pricing reads.
- This report tracks liveness and scalability when the All range is selected.
- I did not observe or verify mixed-revision values before the application became unresponsive.
Initial static investigation of main found the following potential amplification path:
loadUsageStats()loads the summary, all LLM activity, all tool activity, and pricing together.- Activity is paged in protocol frames of 100 records, but Desktop continues requesting pages until it has accumulated the complete activity set, capped at 50,000 LLM rows and 50,000 tool rows.
- The current SQLite Usage reader materializes, JSON-decodes, filters, and sorts the matching range before applying
slice(offset, offset + limit), so each protocol page can repeat work over the full range. - Desktop then merges, aggregates, and sorts the accumulated arrays.
- When request details are displayed, renderer code maps the complete activity array into a non-paginated/non-virtualized table.
Relevant paths:
apps/desktop/src/main/runtime-host-usage-ipc-main.tsapps/desktop/src/renderer/features/usage/ui/usage-settings-view.tsxapps/desktop/src/renderer/features/usage/ui/usage-stats-table.tsxpackages/storage/src/sqlite-usage-store.tspackages/runtime-host/src/protocol/usage-pricing.ts
The current implementation in #4068 may reduce repeated Storage scans and serialize overlapping range reloads, but it still:
- captures up to 50,000 LLM rows and 50,000 tool rows into a Host memory snapshot;
- pages both snapshots to Desktop until the arrays are complete;
- aggregates all returned rows in Desktop main;
- can pass the complete activity array to the renderer table.
For that reason, #4068 may mitigate this reproduction but does not appear to establish a bounded end-to-end read or render path.
The P1 design proposed in the final #4068 review appears relevant to this defect:
- return summary and SQL
GROUP BYprojections with only the first bounded activity page in one Storage transaction; - fetch later activity pages on demand using a stable
(ts, id)-style cursor; - stamp pages with a Usage revision and return
revision_changedfor stale continuations; - use
hasMoreinstead of traversing the full data set to compute or transfer an exact total; - keep the Runtime Host stateless rather than retaining a full in-memory activity snapshot;
- render only a bounded page of activity rows.
Related:
- fix(runtime-host): serve one revision-consistent Usage snapshot #4058
- fix(runtime-host): serve revision-consistent Usage snapshots #4068
- [DISCUSS] Storage and protocol: four published rules, each enforced in exactly one path #4876
Additional evidence that would be useful but has not yet been collected:
- model-call and tool-invocation row counts for the affected profile;
- Activity Monitor CPU and memory observations;
- a macOS Sample Process capture while the application is stuck;
- whether request details were enabled at the time of reproduction;
- comparison with a clean profile and with the
24h,7d, and30dranges.
Activity
Sun-GLiang commentedon Sep 8, 2026
take
Sun-GLiang commentedon Sep 8, 2026
Live CPU, memory, and stack sampling during the reproduced hang
Captured while the reported Settings → Usage → All hang was still present. This supplies the process-resource observations and macOS sampling evidence listed as missing in the issue.
Environment and collection
5a1514c1d43894691186174cc0683e0b6fd88f53. The running build artifacts were not independently verified against that source commit.ps, repeatedtopsamples,sample,vm_stat, andsysctl vm.swapusage. No processes were terminated or restarted, and no application code was changed during collection.Process observations
CPU of 100% corresponds approximately to one logical core. RSS and footprint are different memory-accounting measures and should not be interpreted as consecutive measurements of the same metric.
Successive
topobservations reported renderer memory of 4,231 MB → 4,251 MB → 4,373 MB over several seconds. The renderer remained busy and its memory was still increasing during observation; this alone does not establish a memory leak. A subsequentsamplereport recorded a peak footprint of approximately 4.4 GB.System-wide observations
topsamples.These are system-wide figures, not memory or swap attributable exclusively to Maka. The observations show a busy renderer and substantial memory usage rather than exhaustion of all CPU cores.
Stack-sampling observations
Interpretation and limits
The sustained activity at the time of capture was concentrated in the renderer, while Electron main and Runtime Host were largely idle. This makes renderer-side data processing, component updates, and activity-table rendering the next profiling targets. It does not rule out expensive Host/Storage work earlier in the load.
The user also reported that
Command+Qdid not exit the application, but this sampling does not establish why quitting failed.The evidence is relevant to the bounded-read and bounded-render direction discussed in #4068, but it does not yet prove that full-history loading is the root cause or that the proposed redesign alone resolves this hang. A JavaScript CPU profile is still needed to locate the hot path. Exact record counts, request-details visibility, and clean-profile/range comparisons remain unverified.
AI assistance: Codex collected and summarized the process observations at the reporter's request; the reporter reproduced the hang.
Astro-Han commentedon Sep 17, 2026
@Sun-GLiang could you re-test this on current
main? The amplification path described here has since changed: #5387 (c980b93a3) made the Usage screen read statistics, breakdowns, pricing and the first activity page in one SQLite transaction behind a revision-fenced keyset cursor, and #4539 (f2b6066a6) limits activity rendering to 50 records per page, so the 50,000-row accumulation in Desktop main no longer exists in production code. Neither change was made against this report, so the All-range hang has not been confirmed fixed. If it no longer reproduces on your existing profile we can close this.Sun-GLiang commentedon Sep 18, 2026
Rechecked current main against my existing Usage profile (6,544 activity records): the All-range query completes and returns a bounded 50-row first page. The original unbounded loading and rendering path has been resolved by #5387 and #4539. Closing this issue as fixed.