Skip to main content

max / makenotwork

mt: mirror full identity on userinfo refresh, not just perks apply_userinfo wrote username/display_name/avatar_url to the session but its users-table UPDATE set only is_fan_plus/is_creator, so POST /auth/refresh left the mirrored row every other user's posts JOIN against stale until a full re-login. Reuse upsert_login_user so refresh and login can never drift into two mirror shapes. Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
Author: Max Johnson <me@maxj.phd> · 2026-07-07 14:46 UTC
Commit: cb4d22ff07f38173d0dc74461a97d8f77990a5f3
Parent: 1b1f654
1 file changed, +8 insertions, -13 deletions
@@ -359,20 +359,15 @@ async fn apply_userinfo(state: &AppState, session: &Session, info: &UserinfoResp
359 359 if let Err(e) = session.insert(SESSION_DISPLAY_NAME, &info.display_name).await {
360 360 tracing::error!(error = %e, "failed to save refreshed display_name");
361 361 }
362 - // Mirror perks into users table so post rendering sees the change without
363 - // consulting MNW per-post. Best-effort: rendering tolerates a stale row.
364 - if let Err(e) = sqlx::query(
365 - "UPDATE users SET is_fan_plus = $2, is_creator = $3 WHERE mnw_account_id = $1",
366 - )
367 - .bind(info.user_id)
368 - .bind(info.perks.fan_plus)
369 - .bind(info.perks.is_creator)
370 - .execute(&state.db)
371 - .await
372 - {
373 - tracing::warn!(error = %e, "failed to mirror refreshed perks to users table");
362 + // Mirror the full identity snapshot (username/display_name/avatar_url + perks)
363 + // into the users table so *other* users' posts JOIN against the current author
364 + // row, not a login-time freeze. This reuses the exact login upsert — including
365 + // the stale-username vacate — so "refresh" and "login" can never drift into two
366 + // different mirror shapes (audit_review.md: apply_userinfo stale mirror).
367 + // Best-effort: rendering tolerates a momentarily stale row.
368 + if let Err(e) = upsert_login_user(&state.db, info).await {
369 + tracing::warn!(error = %e, "failed to mirror refreshed identity to users table");
374 370 }
375 - let _ = info.avatar_url; // not stored in session yet
376 371 }
377 372
378 373 /// Refresh the cached perks for the current session via the MNW refresh token.