Conversation
added 3 commits
September 17, 2026 07:46
Add Base UI menu and context-menu primitives, shared floating styles, and the component registry/specimen entry. Signed-off-by: Carl <acda9e433d19dcd0e6b6840f7f4b98f3a56f1fab98049d444c087019e6d36560@buzz.block.builderlab.xyz>
Expose group assignment and Star/Unstar through confirmed host-owned preference writes. Preserve unrelated encrypted data, fence stale reads and cancelled sessions, and restore keyboard focus after exclusive row relocation. Signed-off-by: Carl <acda9e433d19dcd0e6b6840f7f4b98f3a56f1fab98049d444c087019e6d36560@buzz.block.builderlab.xyz>
Offer Starred and saved groups in one destination chooser. Confirm the destination assignment before clearing Star so removal returns to Channels without restoring a hidden group after reload. Retain confirmed local placement through partial failures, fence overlapping refreshes, and cover ordered writes, cancellation, retry and browser focus. Signed-off-by: Carl <acda9e433d19dcd0e6b6840f7f4b98f3a56f1fab98049d444c087019e6d36560@buzz.block.builderlab.xyz>
added 2 commits
September 17, 2026 11:36
Resolve fresh relay-owned channel permissions, keep lifecycle commands outside the message outbox, and confirm authoritative state before removing rows. Preserve DM membership, fence cancelled sessions, and make ambiguous publication recoverable without blind resubmission. Signed-off-by: Carl <acda9e433d19dcd0e6b6840f7f4b98f3a56f1fab98049d444c087019e6d36560@buzz.block.builderlab.xyz>
Accept the relay's four-field membership roster without using hints as administrator authority. Exercise valid and malformed roster shapes, correct browser fixtures, and offer safe retry copy instead of raw protocol errors. Signed-off-by: Carl <acda9e433d19dcd0e6b6840f7f4b98f3a56f1fab98049d444c087019e6d36560@buzz.block.builderlab.xyz>
tellaho
force-pushed
the
tho/sidebar-lifecycle
branch
from
September 22, 2026 17:51
db4efaf to
a455718
Compare
tellaho
force-pushed
the
tho/sidebar-grouping-star
branch
from
September 22, 2026 22:02
0cbb69a to
67146d8
Compare
added 2 commits
September 22, 2026 17:02
Remove action ellipses and omit forbidden Leave actions instead of displaying a disabled item and ownership guidance. Preserve confirmation and domain authorization, with mounted and browser regressions. Signed-off-by: Carl <acda9e433d19dcd0e6b6840f7f4b98f3a56f1fab98049d444c087019e6d36560@buzz.block.builderlab.xyz>
Wait silently for fresh menu permissions while retaining failed-read retry and all authorization checks. Cover pending initial and retry lookups without exposing unchecked actions. Signed-off-by: Carl <acda9e433d19dcd0e6b6840f7f4b98f3a56f1fab98049d444c087019e6d36560@buzz.block.builderlab.xyz>
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Overview
Category: new-feature
User Impact: Users can archive, delete or leave supported channels, and hide DMs without removing anyone from the conversation.
Problem: The new sidebar lacked channel lifecycle actions, leaving users dependent on another client to manage their conversations.
Solution: Add type-appropriate actions backed by fresh channel permissions and explicit confirmation. Remove rows only after relay-owned state confirms the change, retaining recovery when publication is rejected or uncertain.
Stack: targets the same-repository
tho/sidebar-grouping-starmirror of grouping/Star #10, notmain; menu #89 → grouping/Star #10 → this lifecycle sibling. #90 was superseded by #10. Exact base:0cbb69ab8e33b5ac11b1e97d503b45f660b1fd09. Sorting and mute/read remain independent siblings. Reconciliation preserves the unified Move to… chooser, Starred-to-group moves, removal to Channels, and the preference owner's ordered two-record write queue and refresh/cancellation fencing.Source: buzz://message?channel=b9ab2a04-14c4-440d-8c82-aebfbc1caa68&id=2fafae420919217d2b096b02c22f0a045356b19708c16a52d1e65d54d1741d41
Changes
39000/39001/39002checks before signing and again before publication. The relay remains the final authorization boundary; these reads are not an atomic permission lease.9002/9008/9022/41012commands stay outside the durable message outbox. No automatic destructive replay.30622DM visibility only filters sidebar rows; exact conversation navigation remains available.ptags (plus two-/three-field forms), without granting authority from membership hints. Administrator authority stays in39001; invalid keys and duplicate members still fail closed. Failed menu permission reads show Channel actions unavailable with Retry instead of raw parser errors. Confirmation wording is unchanged.File changes
src/features/relay/channel-lifecycle-protocol.ts
Defines the narrow lifecycle wire shapes and projects direct role/type/membership capabilities from relay-authored channel records.
src/features/relay/channel-lifecycle.ts
Owns fresh permission checks, signing and publication confirmation, cancellation, uncertain outcomes and per-viewer DM visibility.
src/features/relay/channel-lifecycle.test.ts
Covers all four commands, malformed/foreign authority, role revocation, signer mutation, failed/uncertain delivery, session retirement and visibility replacement.
src/features/relay/transport.ts
Exposes an optional dedicated broker lifecycle capability without expanding message-outbox kinds.
src/features/relay/session.ts
Adds only 15 lines of explicitly authorized composition, cancellation, clear and disposal wiring; domain state stays outside FOUNDATION.
dev/relay-broker.mjs
Adds shape-limited lifecycle sign/publish routes through the existing authenticated host boundary.
dev/relay-broker-api.test.mjs
Exercises the real host routes and rejects general metadata changes, other-member removal, malformed commands, foreign signers and message-writer misuse.
src/bundled/channels/ChannelLifecycleMenu.tsx
Loads authority only while a row menu is mounted. Pending reads are silent; unavailable and retry states remain explicit.
src/bundled/channels/ChannelLifecycleDialog.tsx
Confirms every action, requires the channel name for Delete and keeps failures recoverable without blind resubmission after uncertainty.
src/bundled/channels/ChannelLifecycleDialog.module.css
Uses shared type, spacing, surface and color tokens for the responsive native modal.
src/bundled/channels/ChannelLifecycleMenu.test.tsx
Mounts the real menu/dialog to cover permissions, confirmations, lockout, recovery and stale completions after unmount.
src/bundled/channels/ChannelsPage.tsx
Integrates row actions, separate DM visibility, post-removal navigation and focus restoration; hidden DMs remain accessible by exact navigation.
tests/browser/channel-lifecycle.spec.mjs
Adds representative built-app Archive, Hide and Delete journeys across the real broker and native modal.
tests/browser/fixture.mjs
Adds opt-in signed lifecycle fixtures and modeled relay effects, without live destructive writes.
tests/browser/policy-relay.mjs
Recognizes the exact three-coordinate capability query in the production-broker fixture.
tests/browser/navigation-groups.spec.mjs
Preserves keyboard/group/star assertions with lifecycle items now following the existing menu items.
docs/channels.md
Documents authority boundaries, publication ambiguity, sidebar-only hiding and intentionally deferred parity.
Reproduction steps
41012was published.Validation and remaining gates
Latest head:
e34cbbe6087281260113f9dd6d1975e29801e4b1. Removed the “Checking channel permissions…” menu row. Fresh permission reads still run; actions appear only when verified, and failed reads retain Retry. Mounted tests gate both initial and retry lookups to verify silence without unchecked actions. Full Vitest passed 152 files / 1,644 tests (16.50s) on the working update atop2b59d01; pre-commit preserved that tree. Clean-head push hooks passed TypeScript and 65 files / 789 tests. Changed-file Biome and diff checks passed. Browser/build/native checks were not repeated for this presentation-only change; ready-state screenshots below are unchanged.Previous menu-label update:
2b59d0139991c6e53d9269e98cffcb05ea3e7711. Archive/Delete/Leave/Hide labels no longer end in ellipses. Forbidden Leave and its ownership-transfer explanation are omitted; permitted Leave, confirmation dialogs and domain authorization remain intact. “Move to…” is unchanged.Validation for this update: full Vitest 152 files / 1,644 tests (16.26s wall time), production build/TypeScript, changed-file Biome, and all 6 lifecycle browser cases across Chromium/WebKit (31.2s, zero retries) passed on the working update atop
a455718. The committed tree was verified unchanged by pre-commit; clean-head pre-push TypeScript plus 65 files / 789 tests passed. Two mounted cases added, no browser cases added/removed. No live destructive writes. Current-head hosted results, broader browser/native checks and acceptance are not claimed.The implementation still incorporates grouping snapshot
0cbb69a; its mirror has since advanced to67146d8. This menu-only update does not rebase or validate that newer dependency.Previous roster/grouping validation snapshot:
a4557189674d9572ff6d6cb3134fc98c51136d4e, base0cbb69ab8e33b5ac11b1e97d503b45f660b1fd09. The following full-suite/build/browser checks ran on the six-file working update atop rebased040898c220bc754eb10f333cbaf6a60c2730123d; the committed tree was verified identical after the pre-commit hook (33daf0d49ba63d258868522780773f10264066ab). Pre-push ran on the clean committed head.bin/pnpm check: passed Biome (657 files), TypeScript, design TypeScript and type/color/contrast/foundation checks.bin/pnpm exec vitest run: 152 files / 1,642 tests passed, 16.26s wall time. Includes broker-route integration, mounted UI and new roster regressions.bin/pnpm build: passed (existing >500 kB chunk warning remains).git diff --checkpassed against the exact base. Both outgoing lifecycle commits retain verified authorship and DCO trailers.a455718; CI run 35763295099 is running/queued on that exact head. Earlier all-green checks belong todb4efafand do not validate this rebased/fixed head. Remote branch andrefs/pull/92/headboth resolve toa4557189674d9572ff6d6cb3134fc98c51136d4e.Older evidence, not rerun for this head:
dm-labels.spec.mjspassed 4/4 in both engines; serial cold/warm opening measurements passed 2/2 (24.8s total, cold visible upper bounds 339/345ms including Playwright roundtrip, warm paint 23–34ms Chromium / 38–70ms WebKit). These were local Apple Silicon macOS fixture measurements on the original lifecycle snapshot, not current-head or hosted-network guarantees.Browser coverage rationale: +3 scenarios per engine, no cases removed. Archive proves keyboard/menu/native-modal handoff and focus; Hide proves actual routing and reload visibility without access deletion; Delete proves the separate access-purge/navigation path. Role and failure permutations stay in domain/React tests; Leave uses those lower layers rather than another equivalent full-app journey. Existing grouping keyboard assertions now account for the final lifecycle retry item, without dropping End/Home traversal.
Fail-then-pass evidence: The roster regression first failed the full Vitest run (28 tests across two files plus unhandled errors) after replacing the incorrect two-field fixtures with the actual relay shape. Accepting the optional membership fields restored the full 1,642-test pass while new tests retain rejection before signing/publication for malformed and duplicate members, and prove hints cannot grant admin authority. Relay contract source:
block/buzz70895b355fcea9f99894b426c020052b715bd368,crates/buzz-relay/src/handlers/side_effects.rs:1050–1057; legacy reader:desktop/src-tauri/src/nostr_convert.rs:243–265. No new browser cases were needed for this correction. Earlier implementation evidence: the browser cases rejected an over-strict menu generation guard that prevented native dialogs from mounting; removing that invalid guard restored all six lifecycle executions. Pre-push also caught the unit command-equality assertion crossing a wall-clock second; controllingDate.nowretained the exact timestamp assertion and the hook passed. No retries, sleeps, broadened error allowlists or weakened assertions were used to hide those failures.Deferred: full
just scan/all-browser suite, Node CLI/Rust/native validation, independent review and attended native UI acceptance. This remains a draft, not integration-ready. No live destructive relay writes were performed. There is no matched before/after fixture-performance baseline or hosted CI performance claim.Explicit scope limits: development-broker lifecycle writes only (native/direct-signer capability deferred); direct channel roles only (delegated owner-agent/community-admin authority deferred); no in-app unarchive or DM reopen/unhide; DM visibility refreshes with roster refresh, not a new live cross-device subscription. Cancellation cannot retract an already-sent request. Publication confirmation is bounded and may require an explicit refresh.
Screenshots / demos
Latest lifecycle menu capture; confirmation and grouping captures are unchanged from the preceding update. Dark mode with signed fixture data; narrow crops, no live community content. Real product UI, not mockups or a component showcase.
The existing non-UUID grouping fixture intentionally cannot resolve lifecycle permissions; it demonstrates safe unavailable/Retry copy alongside the new group chooser.