Skip to content

feat(members): offer the observer role on invite and role change - #2549

Open
Makisuo wants to merge 1 commit into
observer/agentsfrom
observer/members
Open

Makisuo wants to merge 1 commit into
observer/agentsfrom
observer/members

Conversation

@Makisuo

@Makisuo Makisuo commented Nov 12, 2026 •

Copy link
Copy Markdown
Collaborator

Fourth layer of the Observer role, on top of #2547. The Members page now offers it.

What changed

  • Observer joins the roles the Members page assigns, lowest first. The invite picker, the role picker on each row and the role change prompt all read that list, so they pick it up without page changes.
  • Member stays the default role for a new invite.
  • A role key the page does not know now shows as Observer, the same way the API reads it. It showed as Member.

Screenshots

Role picker, before and after:

Before After
before after

The confirm strip says what the role is for:

confirm

Verified

  • packages/domain: policy tests, 16 passed.
  • apps/web: org-membership.test.ts and the members page tests, 17 passed. New cases: an unknown role key shows as Observer, root still shows as Member, and the role change prompt names the observer role.
  • The /lab/members page driven in a headless browser for the screenshots above.
  • The development auth instance now has org:observer in its default role set, created through the provider's API.

Before merge

Create org:observer (name "Observer", no system permissions, in the default role set) on the production auth instance. Until it exists, assigning Observer there fails. Also confirm production has no role keys beyond admin, member and engineer: any other key now reads as observer.


Autofix with [code]smith
Open in [code]smith · Need help on this PR? Tag @codesmith-bot with what you need.

Observer joins the roles the Members page assigns, so the invite and role pickers offer it and the role change prompt says what it can do. Member stays the default for a new invite.

A role key the page does not know now shows as Observer, matching how the API reads it. The role has to exist on the auth instance before it can be assigned.
@coderabbitai

coderabbitai Bot commented Nov 12, 2026

Copy link
Copy Markdown

Important

Review skipped

Auto reviews are disabled on base/target branches other than the default branch.

Please check the settings in the CodeRabbit UI or the .coderabbit.yaml file in this repository. To trigger a single review, invoke the @coderabbitai review command.

Run configuration

  • Source mode: Auto
  • Repository: Unavailable
  • Branch: Unavailable
  • File: No configuration file from this repository applied
  • Commit: Unavailable
  • Layers: defaults
  • Review profile: CHILL
  • Plan: Advanced
  • Run ID: ac14d004-11e0-4f60-9c67-bdf392d79366

You can disable this status message by setting the reviews.review_status to false in the CodeRabbit configuration file.

Use the checkbox below for a quick retry:

  • Trigger review
  • Autofix · Keep fixing CodeRabbit findings and required CI, and resolving merge conflicts

Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out.

Share

@maple-review-bot

maple-review-bot Bot commented Nov 12, 2026 •

Copy link
Copy Markdown

Maple review

🟢 Confidence 10/10 · safe to merge. Only an info note on a positional lookup; the role list, picker and prompt text are pinned by new tests.
1 note · tests covered · risk medium

Moves the observer role into Policy.assignableRoles so the Members page offers it in the invite picker, the row picker and the role-change prompt, and makes an unknown Clerk role key display as Observer. Safe to merge once the Clerk role exists in production.

  • observer joins assignableRoles lowest first; clerkRoles is gone
  • toOrgRole now maps an unknown key to org:observer
  • Invite default stays org:member

Before merge

  • Manual · Create org:observer (name "Observer", no system permissions, in the default role set) on the production Clerk instance
  • Manual · Confirm production has no Clerk role keys beyond admin, member and engineer: any other key now reads, and resends, as observer

Findings

🔵 Note · F1 · memberEntry is looked up by array position, not by role

maintainability · apps/web/src/page/settings/kit/org-membership.ts:11

Policy.assignableRoles[1] hard-codes member as second in a list the same module defines as rank-ordered; this change already shifted every role down one. A role inserted between observer and member would make a root membership read as that role, and its row picker would then write it.

`const memberEntry = Arr.findFirst(Policy.assignableRoles, (entry) => entry.role === "member")`, and return `Option.getOrThrow(memberEntry)` from `entryOf`'s fallback.
🤖 Prompt to fix this finding with an AI agent
Findings from an automated review of commit cfd972575f21565ece2c93e536c3cd189b0a7d5f. Verify each one against the current code before changing anything, fix only those that still apply, and keep each fix to the lines it names.

---

F1 · Note · maintainability · apps/web/src/page/settings/kit/org-membership.ts:11
`memberEntry` is looked up by array position, not by role
`Policy.assignableRoles[1]` hard-codes member as second in a list the same module defines as rank-ordered; this change already shifted every role down one. A role inserted between observer and member would make a `root` membership read as that role, and its row picker would then write it.
Suggested fix: `const memberEntry = Arr.findFirst(Policy.assignableRoles, (entry) => entry.role === "member")`, and return `Option.getOrThrow(memberEntry)` from `entryOf`'s fallback.

cfd9725 · What was checked, coverage and telemetry details are on the Maple / review check. Reply "won't fix" to dismiss a finding, or mention @maple-review-bot to ask about one.

This branch has not been deployed

No deployments
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant