feat(auth): block disabled user accounts at the subscription guard
RequireActiveTenantSubscription now optionally takes an AuthRepository and rejects the request with 40311/user_disabled when the actor's user row is anything other than active. Wire the repo through the tenant router, surface the new error code in admin-web's membershipBlockedErrors set, persist a "disabled" membership status when markStoredMembershipBlocked sees user_disabled, and add localized copy on the blocked screen and shell membership banner. Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
This commit is contained in:
@@ -25,6 +25,11 @@ const authStore = useAuthStore();
|
||||
const { locale, t } = useI18n();
|
||||
|
||||
const isMembershipBlocked = computed(() => authStore.isMembershipBlocked);
|
||||
const membershipBlockedMessage = computed(() => (
|
||||
authStore.membership?.blocked_reason === "user_disabled"
|
||||
? t("membershipBlocked.userDisabledMessage")
|
||||
: t("membershipBlocked.expiredMessage")
|
||||
));
|
||||
|
||||
const quotaQuery = useQuery({
|
||||
queryKey: ["workspace", "quota-summary", "shell"],
|
||||
@@ -358,7 +363,7 @@ async function handleLogout(): Promise<void> {
|
||||
aria-live="polite"
|
||||
>
|
||||
<div class="membership-expired-logo" :aria-label="t('app.name')">GEO</div>
|
||||
<p>{{ t("membershipBlocked.expiredMessage") }}</p>
|
||||
<p>{{ membershipBlockedMessage }}</p>
|
||||
</section>
|
||||
<router-view v-else />
|
||||
</a-layout-content>
|
||||
|
||||
Reference in New Issue
Block a user