Skip to content

Commit 3236e0c

Browse files
feat: add 2FA status column to organization members table
- Add twoFactorEnabled column to UserListTable with admin-only visibility - Modify backend handler to conditionally include 2FA data for org admins - Set column as hidden by default using initalColumnVisibility - Use Badge component to display enabled/disabled status - Implement proper permission checks using adminOrOwner variable Co-Authored-By: joe@cal.com <j.auyeung419@gmail.com>
1 parent 10fca86 commit 3236e0c

2 files changed

Lines changed: 23 additions & 0 deletions

File tree

packages/features/users/components/UserTable/UserListTable.tsx

Lines changed: 21 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -77,6 +77,7 @@ const initalColumnVisibility = {
7777
teams: true,
7878
createdAt: false,
7979
updatedAt: false,
80+
twoFactorEnabled: false,
8081
actions: true,
8182
};
8283

@@ -416,6 +417,26 @@ function UserListTableContent({ org, attributes, teams, facetedTeamValues }: Use
416417
},
417418
cell: ({ row }) => <div>{row.original.updatedAt || ""}</div>,
418419
},
420+
{
421+
id: "twoFactorEnabled",
422+
accessorKey: "twoFactorEnabled",
423+
header: t("2fa"),
424+
enableHiding: true,
425+
enableSorting: false,
426+
enableColumnFilter: false,
427+
size: 80,
428+
cell: ({ row }) => {
429+
const { twoFactorEnabled } = row.original;
430+
if (!adminOrOwner || twoFactorEnabled === undefined) {
431+
return null;
432+
}
433+
return (
434+
<Badge variant={twoFactorEnabled ? "green" : "gray"}>
435+
{twoFactorEnabled ? t("enabled") : t("disabled")}
436+
</Badge>
437+
);
438+
},
439+
},
419440
{
420441
id: "actions",
421442
enableHiding: false,

packages/trpc/server/routers/viewer/organizations/listMembers.handler.ts

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -225,6 +225,7 @@ export const listMembersHandler = async ({ ctx, input }: GetOptions) => {
225225
disableImpersonation: true,
226226
completedOnboarding: true,
227227
lastActiveAt: true,
228+
...(ctx.user.organization.isOrgAdmin && { twoFactorEnabled: true }),
228229
teams: {
229230
select: {
230231
team: {
@@ -311,6 +312,7 @@ export const listMembersHandler = async ({ ctx, input }: GetOptions) => {
311312
.toLowerCase()
312313
: null,
313314
avatarUrl: user.avatarUrl,
315+
...(ctx.user.organization.isOrgAdmin && { twoFactorEnabled: user.twoFactorEnabled }),
314316
teams: user.teams
315317
.filter((team) => team.team.id !== organizationId) // In this context we dont want to return the org team
316318
.map((team) => {

0 commit comments

Comments
 (0)