v2.0.10 — snappier boot + non-blocking relay push on save
DB - Six indices on the cards table (position+created_at, bucket_id, parent_id, updated_at, caldav_uid, relay_uid). The /api/cards ORDER BY position was a full-table scan + sort on every board reload; now it's an index walk. - PRAGMA synchronous=NORMAL (safe under WAL) + temp_store=MEMORY. Save path - pushCardToRelayRead and deleteCardFromRelayRead now run AFTER the response is flushed via fastcgi_finish_request (falls back to ignore_user_abort + flush on non-FPM setups). The user's save no longer blocks on the relay round-trip. - cURL timeouts dropped from 10s/30s to 5s/10s, plus a 2s connect-timeout. Worst-case on a dead relay goes from ~160s down to ~15s — and now that worst case is in the background anyway. Client - loadCards phase-2 batches bumped from 25 to 500 cards per fetch. For 300 cards that's 1 HTTP trip instead of 12 — spinner wall time drops from ~3s to ~0.25s. - renderBoard() is now requestAnimationFrame-coalesced. The boot sequence calls renderBoard from cache paint, meta paint, body paint, and the cards.reloaded plugin hook; they used to each trigger an innerHTML swap + layout pass. Now they collapse into one actual render per frame. Callers that really need a sync render (rare) can use the new renderBoardSync(). Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
This commit is contained in:
1 parent
87ebcd156b
commit
2d58cd993e
7 files changed
+124
-28
No files matched your search
@@ -493,8 +493,30 @@ export function renderCardHtml(c, inGroup = false, recent = []) {
|
||||
}
|
||||
|
||||
// ── Render ──
|
||||
//
|
||||
// Public renderBoard() is coalesced via requestAnimationFrame: multiple
|
||||
// callers in the same tick (cache paint → meta paint → body paint →
|
||||
// plugin-hook re-render → ...) collapse into a single actual render on
|
||||
// the next frame. Dropped the "three innerHTML swaps per reload" cost
|
||||
// that showed up as the "Gekringel" during boot. Callers that need the
|
||||
// DOM in a specific state before doing something else can call
|
||||
// renderBoardSync() explicitly — but in practice every existing caller
|
||||
// just wants the board to reflect the latest state.
|
||||
|
||||
let rafScheduled = 0;
|
||||
export function renderBoard() {
|
||||
if (rafScheduled) return;
|
||||
rafScheduled = requestAnimationFrame(() => {
|
||||
rafScheduled = 0;
|
||||
renderBoardSync();
|
||||
});
|
||||
}
|
||||
export function renderBoardSync() {
|
||||
if (rafScheduled) { cancelAnimationFrame(rafScheduled); rafScheduled = 0; }
|
||||
renderBoardImpl();
|
||||
}
|
||||
|
||||
function renderBoardImpl() {
|
||||
// Diff state.cards against the last seen ids so we can flag arrivals
|
||||
// as "unseen". The very first renderBoard runs with state.cards = []
|
||||
// (initial empty state, before the API has returned), so we wait
|
||||
|
||||
Reference in new issue
Block a user