General
Admin Panel
Users
Manage users, ban/unban accounts, and view user details in the admin panel.
The Users section of the admin panel allows you to manage all users in your application, including viewing user details, filtering users, banning/unbanning accounts, and exporting user data.
Features
View All Users
The users table displays all registered users with the following information:
- Name and Email - User identification
- Role - User role (user or admin)
- Verification Status - Whether the email is verified
- Ban Status - Whether the user is banned
- Created Date - When the user account was created
Filter Users
You can filter users by multiple criteria:
- Search Query - Search by name or email
- Role - Filter by user role (user, admin)
- Email Verification - Filter by verification status (verified, pending)
- Ban Status - Filter by ban status (banned, active)
- Creation Date - Filter by when the account was created (today, this week, this month, older)
Ban/Unban Users
You can ban users temporarily or permanently:
components/admin/users/ban-user-modal.tsx
import { banUserAdminSchema } from '@/schemas/admin-user-schemas';
// Ban user with optional expiration date
const form = useZodForm({
schema: banUserAdminSchema,
defaultValues: {
reason: '',
expiresAt: null // null = permanent ban
}
});Ban Options:
- Permanent Ban - Set
expiresAttonullfor a permanent ban - Temporary Ban - Set
expiresAtto a future date to automatically unban the user - Ban Reason - Provide a reason for the ban (stored for audit purposes)
Export Users
Export user data to CSV format for analysis or backup:
trpc/routers/admin/admin-user-router.ts
exportSelectedToCsv: protectedAdminProcedure
.input(exportUsersAdminSchema)
.mutation(async ({ input }) => {
const users = await db.query.userTable.findMany({
where: inArray(userTable.id, input.userIds),
});
const Papa = await import('papaparse');
const csv = Papa.unparse(users);
return csv;
}),Using the Admin Users API
List Users
app/admin/users/page.tsx
import { trpc } from '@/trpc/client';
export function UsersTable() {
const { data, isPending } = trpc.admin.user.list.useQuery({
limit: 25,
offset: 0,
query: '', // Optional search query
sortBy: 'name', // 'name' | 'email' | 'role' | 'createdAt'
sortOrder: 'asc', // 'asc' | 'desc'
filters: {
role: ['user'], // Optional role filter
emailVerified: ['verified'], // Optional: 'verified' | 'pending'
banned: ['active'], // Optional: 'active' | 'banned'
createdAt: ['today'] // Optional: 'today' | 'this-week' | 'this-month' | 'older'
}
});
return (
<div>
{data?.users.map((user) => (
<div key={user.id}>
{user.name} - {user.email}
</div>
))}
</div>
);
}Ban a User
components/admin/users/ban-user-modal.tsx
const banUser = trpc.admin.user.ban.useMutation({
onSuccess: () => {
toast.success('User banned successfully');
utils.admin.user.list.invalidate();
}
});
const handleBan = (data: BanUserInput) => {
banUser.mutate({
userId: user.id,
reason: data.reason,
expiresAt: data.expiresAt
});
};Unban a User
components/admin/users/users-table.tsx
const unbanUser = trpc.admin.user.unban.useMutation({
onSuccess: () => {
toast.success('User unbanned successfully');
utils.admin.user.list.invalidate();
}
});
const handleUnban = (userId: string) => {
unbanUser.mutate({ userId });
};User Management Best Practices
When to Ban Users
Ban users when they: - Violate terms of service - Engage in abusive behavior
- Attempt to exploit the system - Show signs of fraudulent activity
Temporary vs Permanent Bans
- Temporary bans - Use for first-time violations or minor infractions - Permanent bans - Use for serious violations or repeat offenders - Always provide a clear reason for the ban
User Data Privacy
- Only export user data when necessary - Ensure compliance with data protection regulations - Store exported data securely - Delete exported files after use
Related Documentation
- Admin UI - Learn how to create admin users
- Permissions and Access Control - Understand user roles and permissions