{ "version": 1, "bugs": [ { "error_message": "Email layout flattened: width/height/colspan/align/bgcolor stripped; background images never restored after 'show images'", "root_cause": "Custom DOMPurify ALLOWED_URI_REGEXP replaced the default that accepts non-URL values, so every non-URL attribute was rejected; blockRemoteImages deleted url()/background irreversibly", "fix": "Added DOMPurify's default non-URL alternatives to the regexp; block/unblock now rewrite backgrounds reversibly (lm-blocked- scheme, data-blocked-background)", "tags": [ "webmail", "sanitizer", "dompurify", "remote-images" ], "date": "2026-10-13" }, { "error_message": "Domain admin dashboard showed server-wide totals (all domains, queue, DMARC, storage)", "root_cause": "dashboardStats, queueSummary, dmarcSummary, preflightSummary and the diagnostics queueByStatus took no AdminScope and queried every tenant; only listDomains/listMailboxes were scoped", "fix": "Each now takes the session's AdminScope; mailboxScope() reaches outbound_jobs/email_messages through mailboxes.domain_id; DMARC matches by domain_id or name. Covered by services/auth/src/adminScope.test.ts against a real Postgres", "tags": [ "auth", "authz", "tenant-isolation", "dashboard" ], "date": "2026-10-13" }, { "error_message": "Discard in the composer did not discard the draft", "root_cause": "The button was a Link to /user/mail/inbox; the autosaved draft stayed in Drafts, and a save already in flight could recreate it. Delete would also only have moved it to Trash", "fix": "discardMessage stops autosave, calls /mail/delete with discard_draft:true (WebmailUseCase.DiscardDraft expunges from Drafts only) and cleans up an in-flight save via discardedRef. Covered by compose-draft-integrity.test.ts and TestDiscardingADraftRemovesItForGood", "tags": [ "webmail", "compose", "drafts" ], "date": "2026-10-22" } ] }