+
| Email |
@@ -434,7 +437,7 @@
Kind |
{/if}
Role |
-
+
Actions
|
|
@@ -443,12 +446,22 @@
{#if filteredUsers && users}
{#each filteredUsers.slice(0, nbDisplayed) as { email, super_admin, devops, login_type, name, username, operator_only, is_workspace_admin, role_source, disabled, workspace_id }, i (email + '::' + (workspace_id ?? ''))}
{@const isServiceAccount = login_type === 'service_account'}
+ {@const groupRole =
+ role_source === 'instance_group' && (super_admin || devops)}
+
+ {@const groupRoleTooltip =
+ 'Role is set by an instance group. Superadmin and Devops can be set here, but demoting to User requires removing the user from the group.'}
+ {@const serviceAccountTooltip =
+ 'Service accounts are always users in the instance. Their workspace role is managed in the workspace user settings.'}
+
-
+
{#if isServiceAccount}
@@ -458,14 +471,6 @@
>{email}
{/if}
- {#if workspace_id}
-
- {truncate(workspace_id, 20)}
-
- {/if}
{#if disabled}
{#if automateUsernameCreation}
-
+
{#if username}
{username}
{:else}
@@ -503,133 +508,157 @@
>
{#if activeOnly}
- {#if is_workspace_admin}
- Admin
- {:else if operator_only}
- Operator only
- {:else}
- Developer
- {/if}
+
+ {#if is_workspace_admin}
+ Admin
+ {:else if operator_only}
+ Operator only
+ {:else}
+ Developer
+ {/if}
+
|
{/if}
- {#if isServiceAccount}
-
+
+
+ {#key `${super_admin}_${devops}_${role_source}`}
+ {
+ if (email == $userStore?.email) {
+ sendUserToast('You cannot demote yourself', true)
+ listUsers(activeOnly)
+ return
+ }
+
+ let role = e.detail
+
+ if (role === 'super_admin') {
+ await UserService.globalUserUpdate({
+ email,
+ requestBody: {
+ is_super_admin: true,
+ is_devops: false
+ }
+ })
+ }
+ if (role === 'devops') {
+ await UserService.globalUserUpdate({
+ email,
+ requestBody: {
+ is_super_admin: false,
+ is_devops: true
+ }
+ })
+ }
+ if (role === 'user') {
+ await UserService.globalUserUpdate({
+ email,
+ requestBody: {
+ is_super_admin: false,
+ is_devops: false
+ }
+ })
+ }
+ sendUserToast('User updated')
+ listUsers(activeOnly)
+ }}
+ >
+ {#snippet children({ item })}
+
+
+
+ {/snippet}
+
+ {/key}
+ {#if isServiceAccount}
{is_workspace_admin
? 'Admin'
: operator_only
? 'Operator'
: 'Developer'}
+ in
+ {#if workspace_id}
+ closeDrawer?.()}
+ >{truncate(workspace_id, 20)}
+ {:else}
+ its workspace
+ {/if}
-
- Service-account role is managed in the workspace user settings.
-
-
- {:else}
-
- {#key `${super_admin}_${devops}_${role_source}`}
- {
- if (email == $userStore?.email) {
- sendUserToast('You cannot demote yourself', true)
- listUsers(activeOnly)
- return
- }
-
- let role = e.detail
-
- if (role === 'super_admin') {
- await UserService.globalUserUpdate({
- email,
- requestBody: {
- is_super_admin: true,
- is_devops: false
- }
- })
- }
- if (role === 'devops') {
- await UserService.globalUserUpdate({
- email,
- requestBody: {
- is_super_admin: false,
- is_devops: true
- }
- })
- }
- if (role === 'user') {
- await UserService.globalUserUpdate({
- email,
- requestBody: {
- is_super_admin: false,
- is_devops: false
- }
- })
- }
- sendUserToast('User updated')
- listUsers(activeOnly)
- }}
- >
- {#snippet children({ item })}
-
-
-
- {/snippet}
-
- {/key}
- {#if role_source === 'instance_group' && (super_admin || devops)}
- closeDrawer?.()}
- >
- Set by instance group
-
- {/if}
-
- {/if}
+ {:else if groupRole}
+ closeDrawer?.()}
+ >
+ Set by instance group
+
+ {/if}
+
|
-
+
{#if isServiceAccount}
{#if workspace_id}
- Manage in workspace
+ closeDrawer?.(),
+ href: `${base}/workspace_settings?tab=users&workspace=${workspace_id}`
+ }
+ ]}
+ />
{/if}
{:else}
| | | | | |
{/each}
+ {#if filteredUsers.length > nbDisplayed}
+ {@const remaining = Math.min(50, filteredUsers.length - nbDisplayed)}
+
+
+
+ {
+ nbDisplayed += 50
+ }}
+ >
+ Load next {remaining} user{remaining !== 1 ? 's' : ''}
+
+ |
+
+ {/if}
{/if}
diff --git a/frontend/src/lib/components/common/toggleButton-v2/ToggleButton.svelte b/frontend/src/lib/components/common/toggleButton-v2/ToggleButton.svelte
index 621e8383d0..2773503df9 100644
--- a/frontend/src/lib/components/common/toggleButton-v2/ToggleButton.svelte
+++ b/frontend/src/lib/components/common/toggleButton-v2/ToggleButton.svelte
@@ -7,6 +7,9 @@
interface Props {
label?: string | undefined
+ /** Shown instead of `label` below the `xl` breakpoint, for groups that must keep
+ * their width inside a narrow table cell. The full label stays the accessible name. */
+ shortLabel?: string | undefined
iconOnly?: boolean
tooltip?: string | undefined
icon?: any | undefined
@@ -30,6 +33,7 @@
let {
label = undefined,
+ shortLabel = undefined,
iconOnly = false,
tooltip = undefined,
icon = undefined,
@@ -68,6 +72,7 @@
{/if}
{#if label && !iconOnly}
- {label}
+ {#if shortLabel}
+
{label}
+
{shortLabel}
+ {:else}
+ {label}
+ {/if}
{/if}
{#if showTooltipIcon}
diff --git a/frontend/src/lib/components/settings/ForkMemberSettings.svelte b/frontend/src/lib/components/settings/ForkMemberSettings.svelte
index 45de0bf3f0..69d911dffc 100644
--- a/frontend/src/lib/components/settings/ForkMemberSettings.svelte
+++ b/frontend/src/lib/components/settings/ForkMemberSettings.svelte
@@ -161,7 +161,7 @@
Email |
Username |
Role |
-
Actions |
+
Actions |
@@ -187,7 +187,7 @@
{is_admin ? 'Admin' : operator ? 'Operator' : 'Developer'}
-
+
| Role |
Enabled |
-
+
Actions
|
@@ -963,7 +963,7 @@
size="xs"
/>
|
-
+ |
{#if user.is_service_account && $userStore?.is_admin}
| Email |
Role |
- Actions |
+ Actions |
@@ -1142,7 +1142,7 @@
-
+
interface Props {
- children?: import('svelte').Snippet;
- headerAction?: import('svelte').Snippet;
+ children?: import('svelte').Snippet
+ headerAction?: import('svelte').Snippet
}
- let { children, headerAction }: Props = $props();
+ let { children, headerAction }: Props = $props()
-
+
+
{@render children?.()}
{@render headerAction?.()}
| | | | | |