detached afa6c9d

feat: Enhance user status update throttling with force update mechanism

- Increase status update intervals to reduce unnecessary network calls
- Implement force update every 5 minutes regardless of status change
- Add detailed logging for skipped status updates
- Include additional context in status update payload (reason, time since last update)
commit
afa6c9d9131ee9c2ebde985f40d39315b28297ca
author
Kit · · 2025-02-15 08:34 UTC
parent
a3b34f2
signature
SSH UnverifiedSHA256:H91DFuEG4jpk5edzLA4aUKkpv4zv9Q339ipRmkph6Tk The key is unknown
1 file · +19 -8
M src/routes/+layout.svelte +19 -8
@@ -13,22 +13,31 @@
1313 // New throttle state variables
1414 let lastSentStatus = $state<string | null>(null);
1515 let lastStatusSentAt = $state<number>(0);
16- const STATUS_UPDATE_INTERVAL = 5000; // 5 seconds
17- const THROTTLE_TIME_MS = 4000; // 4 seconds to prevent edge case overlaps
16+ const STATUS_UPDATE_INTERVAL = 15000; // Changed to 15 seconds
17+ const THROTTLE_TIME_MS = 10000; // Changed to 10 seconds to prevent edge case overlaps
18+ const FORCE_UPDATE_INTERVAL = 5 * 60000; // Force update every 5 minutes regardless of status change
1819
1920 async function updateUserStatus(status: 'online' | 'offline' | 'busy') {
2021 if (!data.user?.id || updateInProgress) return;
2122
22- // Throttle duplicate status updates
23+ const now = Date.now();
24+ const timeSinceLastUpdate = now - lastStatusSentAt;
25+
26+ // Only update if:
27+ // 1. Status has changed OR
28+ // 2. We haven't updated in FORCE_UPDATE_INTERVAL (5 minutes)
2329 if (
24- status === lastSentStatus &&
25- Date.now() - lastStatusSentAt < THROTTLE_TIME_MS
30+ status === lastSentStatus &&
31+ timeSinceLastUpdate < FORCE_UPDATE_INTERVAL &&
32+ timeSinceLastUpdate < THROTTLE_TIME_MS
2633 ) {
27- console.debug('Throttling duplicate status update:', status);
34+ console.debug('Skipping status update - no change and within throttle period:', {
35+ status,
36+ timeSinceLastUpdate,
37+ lastUpdate: new Date(lastStatusSentAt).toISOString()
38+ });
2839 return;
2940 }
30- lastSentStatus = status;
31- lastStatusSentAt = Date.now();
3241
3342 updateInProgress = true;
3443 const timestamp = new Date().toISOString();
@@ -36,6 +45,8 @@
3645 userId: data.user.id,
3746 status,
3847 timestamp,
48+ reason: status !== lastSentStatus ? 'status_changed' : 'force_update',
49+ timeSinceLastUpdate,
3950 trigger: new Error().stack?.split('\n')[2]?.trim(),
4051 hasSession: true,
4152 cookiePresent: browser ? document.cookie.includes('session=') : false
@@ -13,22 +13,31 @@
13 // New throttle state variables13 // New throttle state variables
14 let lastSentStatus = $state<string | null>(null);14 let lastSentStatus = $state<string | null>(null);
15 let lastStatusSentAt = $state<number>(0);15 let lastStatusSentAt = $state<number>(0);
16- const STATUS_UPDATE_INTERVAL = 5000; // 5 seconds16+ const STATUS_UPDATE_INTERVAL = 15000; // Changed to 15 seconds
17- const THROTTLE_TIME_MS = 4000; // 4 seconds to prevent edge case overlaps17+ const THROTTLE_TIME_MS = 10000; // Changed to 10 seconds to prevent edge case overlaps
18+ const FORCE_UPDATE_INTERVAL = 5 * 60000; // Force update every 5 minutes regardless of status change
18 19
19 async function updateUserStatus(status: 'online' | 'offline' | 'busy') {20 async function updateUserStatus(status: 'online' | 'offline' | 'busy') {
20 if (!data.user?.id || updateInProgress) return;21 if (!data.user?.id || updateInProgress) return;
21 22
22- // Throttle duplicate status updates23+ const now = Date.now();
24+ const timeSinceLastUpdate = now - lastStatusSentAt;
25+
26+ // Only update if:
27+ // 1. Status has changed OR
28+ // 2. We haven't updated in FORCE_UPDATE_INTERVAL (5 minutes)
23 if (29 if (
24- status === lastSentStatus &&30+ status === lastSentStatus &&
25- Date.now() - lastStatusSentAt < THROTTLE_TIME_MS31+ timeSinceLastUpdate < FORCE_UPDATE_INTERVAL &&
32+ timeSinceLastUpdate < THROTTLE_TIME_MS
26 ) {33 ) {
27- console.debug('Throttling duplicate status update:', status);34+ console.debug('Skipping status update - no change and within throttle period:', {
35+ status,
36+ timeSinceLastUpdate,
37+ lastUpdate: new Date(lastStatusSentAt).toISOString()
38+ });
28 return;39 return;
29 }40 }
30- lastSentStatus = status;
31- lastStatusSentAt = Date.now();
32 41
33 updateInProgress = true;42 updateInProgress = true;
34 const timestamp = new Date().toISOString();43 const timestamp = new Date().toISOString();
@@ -36,6 +45,8 @@
36 userId: data.user.id,45 userId: data.user.id,
37 status,46 status,
38 timestamp,47 timestamp,
48+ reason: status !== lastSentStatus ? 'status_changed' : 'force_update',
49+ timeSinceLastUpdate,
39 trigger: new Error().stack?.split('\n')[2]?.trim(),50 trigger: new Error().stack?.split('\n')[2]?.trim(),
40 hasSession: true,51 hasSession: true,
41 cookiePresent: browser ? document.cookie.includes('session=') : false52 cookiePresent: browser ? document.cookie.includes('session=') : false

Keyboard shortcuts

Single-key shortcuts are on. ctrl k and esc work whatever this says.

ctrl k :
go to a section, branch, tag, file or repository
?
this list
j k
move the row cursor down / up
enter
open the row under the cursor; on Files, a directory opens or closes in place
↑ ↓ ← → home end
in the file tree (focus on a row): previous / next row, close / open a directory or go to its parent / first entry, first / last row. They never open a file
l h
on Files: open a directory or a file / close a directory or go up to its parent, then to the parent page. Elsewhere: into the side panel (on a merge request, its files) / back to the content; there j k move between its controls
g g G
first / last row
/
filter the list; on Files, find a file anywhere in the repository (esc clears, enter opens the best match)
b
switch branch or tag
g s g f g c g b g m g i g r g a
tabs: summary, files, commits, branches & tags, merge requests, issues, releases, actions (when available)
g h
home
w
wide mode: use the whole width of the screen, or not (remembered)
y
copy a permalink pinned to the commit
d u x
diff: split / unified / collapse or expand all
e E
diff: the whole file in view / every file, with the lines the hunks hide
n
merge request: next note in the diff
esc
close a dialog, leave a field

Branches 3

Tags 8

↑↓ moveenter openesc close