Repository navigation
feat(plugin-auth): multi-org Create User joins the administrator's current organization - #25626
Conversation
📓 Docs Drift CheckThis PR changes 2 package(s): 16 hand-written doc(s) name something this change touched — list omitted above 15 rows. Re-derive on the tree named below: ⛔ 11 release-owned page(s) also affected — read-only, see AGENTS.md Documentation Guardrails. What this run could not see
Coarse fallback — 149 page(s) merely mention a changed package (the pre-#9192 predicate, kept for the deliberately-wide backstop): Which tree this was computed onThis run read A worktree cut from an older # while this PR is open — GitHub drops the merge commit once it closes
git fetch origin 415030e3de41c9989e21ff8c013113d7a0d04d09 && git checkout 415030e3de41c9989e21ff8c013113d7a0d04d09
# afterwards, rebuild it from the two parents, which stay fetchable
git fetch origin 6679644a1a56b552d6864b125900221823ec78b3 366391c7697a07047485df3dd009e907c6b26247 && git checkout -B drift-repro 6679644a1a56b552d6864b125900221823ec78b3 && git merge --no-ff 366391c7697a07047485df3dd009e907c6b26247
node scripts/docs-audit/affected-docs.mjs --json 6679644a1a56b552d6864b125900221823ec78b3
|
…odes The membership callout said Create User writes no membership under a walled posture; it now joins the chosen organization or the administrator's current one, so both pages say so and the create-user section documents organizationId and the join table. Co-authored-by: Claude <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01VEz8GXcBLFWiasohtBhYgR
…tract; reword a docs line The two new engine fakes in admin-user-endpoints.test.ts now open update() with assertEngineUpdateDispatch, as check:engine-double-contract requires, and its pinned ledger records the grown coverage. The authentication page no longer adds role-word occurrences (ADR-0090 D3). Co-authored-by: Claude <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01VEz8GXcBLFWiasohtBhYgR
|
Heads-up from PR #25637 (#24814) is in the merge queue with auto-merge on. It edits the same Generated by Claude Code |
|
Maintainer instruction · 「25626 按当前组织」 · 2026-10-24T16:22:33Z · record on #25625 comment 6386597064 This PR is not approved in its current shape. Rework per the record: multi-org Create User joins the administrator's current organization as Maintainer's words: 「单库多组织的时候,浏览器可以切换组织啊,当前始终会属于一个组织啊,当前组织的管理员增加用户就应该加入这个组织啊,怎么会每次增加的时候要选择。你再想想主流系统是怎么做的」 Generated by Claude Code |
…rrent organization, no picker Reworked per the maintainer's ruling: under a walled posture the new user always joins the calling administrator's current organization as member (better-auth addMember, inside the account's transaction); invite-only still joins; an administrator with no current organization is refused 400 NO_ACTIVE_ORGANIZATION. The Organization picker, the organizationId body parameter, its multiOrgEnabled gated-input row and the four translations are removed; the ADR-0093 D3 amendment, docs and changeset shrink to that one rule. Co-authored-by: Claude <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01VEz8GXcBLFWiasohtBhYgR
…edger; port the flows.screens liveness repoint check:dispatcher-error-vocabulary refused the create-user refusal's code as unregistered: it is now in @objectstack/spec's ledger under @objectstack/plugin-auth, with the generated reference pages regenerated. Spec property liveness was red on main itself (the translation/flows.screens row cites engine.ts, which no longer names the key after the resume-body extraction). The same change as the open fix PR 25751 is ported here so this PR is green; it no-ops once main carries that PR. Co-authored-by: Claude <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01VEz8GXcBLFWiasohtBhYgR
|
CI note: The same push registers Generated by Claude Code |
…e budget fix Test Core (8/8) failed twice on this PR in plugin-pinyin-search's boot-reconcile.integration.test.ts, as it does on other open PRs: the fixture seeds 2,500 rows one awaited create at a time and the suite overruns vitest's 5 s default under CI load. The same change as the open fix PR 25775 is ported here; it no-ops once main carries that PR. Co-authored-by: Claude <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01VEz8GXcBLFWiasohtBhYgR
|
CI note: Generated by Claude Code |
…son-xvcx6q # Conflicts: # packages/spec/liveness/translation.json
Refs #25625 (close it by hand once this merges: the branch name is fixed by the session, so it cannot carry the
claude/issue-N-…claim the closing-target guard reads)What changes for the admin
In multi-org mode, Users → Create User adds the new user to the organization the administrator is working in, so the follow-up Add Member is no longer needed. Mainstream admin consoles behave the same way.
Reworked per the maintainer's ruling 「25626 按当前组织」 (#25625 comment 6386597064, confirmed by the maintainer in session): 「当前组织的管理员增加用户就应该加入这个组织」. The earlier Organization picker, the
organizationIdrequest parameter, itsmultiOrgEnabledgated-input row and the four translations are removed.@objectstack/specand@objectstack/platform-objectsare byte-identical tomain.How
tenancy.isolationActive, the predicate behindfeatures.multiOrgEnabled),POST /api/v1/auth/admin/create-userreads the caller'sactiveOrganizationIdfrom their session before any account exists:400 NO_ACTIVE_ORGANIZATION, nothing created.memberthrough better-auth's ownaddMember(the Add Member act), inside the account's transaction. A refused join returns the vendor's status and code, and no user is created. An existing membership is kept (membershipCreated: false).membershipPolicy: 'invite-only'still joins. Creating a user inside your organization is an explicit act (ADR-0093 D1).501before any account exists.authentication.mdx,tenancy-modes.mdx) are updated. The changeset is BREAKING (narrowing): FROM a member-less account TO400 NO_ACTIVE_ORGANIZATIONfor an administrator with no current organization. The fix is to switch to an organization first.Verification
Unit (
admin-user-endpoints.test.ts) covers:organizationIdchooses nothingThe plugin-auth and platform-objects suites pass.
Dogfood:
create-user-organization-join.dogfood.test.tsruns on a realisolatedstack:sys_userrow exists.The existing create-user, permission-set, reconciler, audit, self-registration and sign-up dogfoods pass (44 tests).
pnpm lint, typecheck,check:i18n,check:adr-0087-registration,check:engine-double-contract,check:role-word,check:doc-authoringandcheck:adr-anchorspass.Landing
This diff touches
docs/adr/**(Tier H). It lands only after an authorized approving review. No AI seat queues it before that.Clause-②: yes (narrowing)
Metadata-protocol: none
Generated by Claude Code