Add admin session management functionality via new API integration
- Implemented `adminListSessions` function to fetch paginated session data for admin monitoring. - Updated `useAdmin` hook to include session statistics and new API call. - Enhanced `DashboardStats` to display total session count. - Added types for `/api/v1/admin/sessions` endpoint responses, errors, and request parameters.
This commit is contained in:
@@ -3,7 +3,7 @@
|
|||||||
|
|
||||||
import { type Client, type Options as Options2, type TDataShape, urlSearchParamsBodySerializer } from './client';
|
import { type Client, type Options as Options2, type TDataShape, urlSearchParamsBodySerializer } from './client';
|
||||||
import { client } from './client.gen';
|
import { client } from './client.gen';
|
||||||
import type { AdminActivateUserData, AdminActivateUserErrors, AdminActivateUserResponses, AdminAddOrganizationMemberData, AdminAddOrganizationMemberErrors, AdminAddOrganizationMemberResponses, AdminBulkUserActionData, AdminBulkUserActionErrors, AdminBulkUserActionResponses, AdminCreateOrganizationData, AdminCreateOrganizationErrors, AdminCreateOrganizationResponses, AdminCreateUserData, AdminCreateUserErrors, AdminCreateUserResponses, AdminDeactivateUserData, AdminDeactivateUserErrors, AdminDeactivateUserResponses, AdminDeleteOrganizationData, AdminDeleteOrganizationErrors, AdminDeleteOrganizationResponses, AdminDeleteUserData, AdminDeleteUserErrors, AdminDeleteUserResponses, AdminGetOrganizationData, AdminGetOrganizationErrors, AdminGetOrganizationResponses, AdminGetUserData, AdminGetUserErrors, AdminGetUserResponses, AdminListOrganizationMembersData, AdminListOrganizationMembersErrors, AdminListOrganizationMembersResponses, AdminListOrganizationsData, AdminListOrganizationsErrors, AdminListOrganizationsResponses, AdminListUsersData, AdminListUsersErrors, AdminListUsersResponses, AdminRemoveOrganizationMemberData, AdminRemoveOrganizationMemberErrors, AdminRemoveOrganizationMemberResponses, AdminUpdateOrganizationData, AdminUpdateOrganizationErrors, AdminUpdateOrganizationResponses, AdminUpdateUserData, AdminUpdateUserErrors, AdminUpdateUserResponses, ChangeCurrentUserPasswordData, ChangeCurrentUserPasswordErrors, ChangeCurrentUserPasswordResponses, CleanupExpiredSessionsData, CleanupExpiredSessionsResponses, ConfirmPasswordResetData, ConfirmPasswordResetErrors, ConfirmPasswordResetResponses, DeleteUserData, DeleteUserErrors, DeleteUserResponses, GetCurrentUserProfileData, GetCurrentUserProfileResponses, GetMyOrganizationsData, GetMyOrganizationsErrors, GetMyOrganizationsResponses, GetOrganizationData, GetOrganizationErrors, GetOrganizationMembersData, GetOrganizationMembersErrors, GetOrganizationMembersResponses, GetOrganizationResponses, GetUserByIdData, GetUserByIdErrors, GetUserByIdResponses, HealthCheckData, HealthCheckResponses, ListMySessionsData, ListMySessionsResponses, ListUsersData, ListUsersErrors, ListUsersResponses, LoginData, LoginErrors, LoginOauthData, LoginOauthErrors, LoginOauthResponses, LoginResponses, LogoutAllData, LogoutAllResponses, LogoutData, LogoutErrors, LogoutResponses, RefreshTokenData, RefreshTokenErrors, RefreshTokenResponses, RegisterData, RegisterErrors, RegisterResponses, RequestPasswordResetData, RequestPasswordResetErrors, RequestPasswordResetResponses, RevokeSessionData, RevokeSessionErrors, RevokeSessionResponses, RootGetData, RootGetResponses, UpdateCurrentUserData, UpdateCurrentUserErrors, UpdateCurrentUserResponses, UpdateOrganizationData, UpdateOrganizationErrors, UpdateOrganizationResponses, UpdateUserData, UpdateUserErrors, UpdateUserResponses } from './types.gen';
|
import type { AdminActivateUserData, AdminActivateUserErrors, AdminActivateUserResponses, AdminAddOrganizationMemberData, AdminAddOrganizationMemberErrors, AdminAddOrganizationMemberResponses, AdminBulkUserActionData, AdminBulkUserActionErrors, AdminBulkUserActionResponses, AdminCreateOrganizationData, AdminCreateOrganizationErrors, AdminCreateOrganizationResponses, AdminCreateUserData, AdminCreateUserErrors, AdminCreateUserResponses, AdminDeactivateUserData, AdminDeactivateUserErrors, AdminDeactivateUserResponses, AdminDeleteOrganizationData, AdminDeleteOrganizationErrors, AdminDeleteOrganizationResponses, AdminDeleteUserData, AdminDeleteUserErrors, AdminDeleteUserResponses, AdminGetOrganizationData, AdminGetOrganizationErrors, AdminGetOrganizationResponses, AdminGetUserData, AdminGetUserErrors, AdminGetUserResponses, AdminListOrganizationMembersData, AdminListOrganizationMembersErrors, AdminListOrganizationMembersResponses, AdminListOrganizationsData, AdminListOrganizationsErrors, AdminListOrganizationsResponses, AdminListSessionsData, AdminListSessionsErrors, AdminListSessionsResponses, AdminListUsersData, AdminListUsersErrors, AdminListUsersResponses, AdminRemoveOrganizationMemberData, AdminRemoveOrganizationMemberErrors, AdminRemoveOrganizationMemberResponses, AdminUpdateOrganizationData, AdminUpdateOrganizationErrors, AdminUpdateOrganizationResponses, AdminUpdateUserData, AdminUpdateUserErrors, AdminUpdateUserResponses, ChangeCurrentUserPasswordData, ChangeCurrentUserPasswordErrors, ChangeCurrentUserPasswordResponses, CleanupExpiredSessionsData, CleanupExpiredSessionsResponses, ConfirmPasswordResetData, ConfirmPasswordResetErrors, ConfirmPasswordResetResponses, DeleteUserData, DeleteUserErrors, DeleteUserResponses, GetCurrentUserProfileData, GetCurrentUserProfileResponses, GetMyOrganizationsData, GetMyOrganizationsErrors, GetMyOrganizationsResponses, GetOrganizationData, GetOrganizationErrors, GetOrganizationMembersData, GetOrganizationMembersErrors, GetOrganizationMembersResponses, GetOrganizationResponses, GetUserByIdData, GetUserByIdErrors, GetUserByIdResponses, HealthCheckData, HealthCheckResponses, ListMySessionsData, ListMySessionsResponses, ListUsersData, ListUsersErrors, ListUsersResponses, LoginData, LoginErrors, LoginOauthData, LoginOauthErrors, LoginOauthResponses, LoginResponses, LogoutAllData, LogoutAllResponses, LogoutData, LogoutErrors, LogoutResponses, RefreshTokenData, RefreshTokenErrors, RefreshTokenResponses, RegisterData, RegisterErrors, RegisterResponses, RequestPasswordResetData, RequestPasswordResetErrors, RequestPasswordResetResponses, RevokeSessionData, RevokeSessionErrors, RevokeSessionResponses, RootGetData, RootGetResponses, UpdateCurrentUserData, UpdateCurrentUserErrors, UpdateCurrentUserResponses, UpdateOrganizationData, UpdateOrganizationErrors, UpdateOrganizationResponses, UpdateUserData, UpdateUserErrors, UpdateUserResponses } from './types.gen';
|
||||||
|
|
||||||
export type Options<TData extends TDataShape = TDataShape, ThrowOnError extends boolean = boolean> = Options2<TData, ThrowOnError> & {
|
export type Options<TData extends TDataShape = TDataShape, ThrowOnError extends boolean = boolean> = Options2<TData, ThrowOnError> & {
|
||||||
/**
|
/**
|
||||||
@@ -812,6 +812,28 @@ export const adminRemoveOrganizationMember = <ThrowOnError extends boolean = fal
|
|||||||
});
|
});
|
||||||
};
|
};
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Admin: List All Sessions
|
||||||
|
*
|
||||||
|
* List all sessions across all users (admin only).
|
||||||
|
*
|
||||||
|
* Returns paginated list of sessions with user information.
|
||||||
|
* Useful for admin dashboard statistics and session monitoring.
|
||||||
|
*/
|
||||||
|
export const adminListSessions = <ThrowOnError extends boolean = false>(options?: Options<AdminListSessionsData, ThrowOnError>) => {
|
||||||
|
return (options?.client ?? client).get<AdminListSessionsResponses, AdminListSessionsErrors, ThrowOnError>({
|
||||||
|
responseType: 'json',
|
||||||
|
security: [
|
||||||
|
{
|
||||||
|
scheme: 'bearer',
|
||||||
|
type: 'http'
|
||||||
|
}
|
||||||
|
],
|
||||||
|
url: '/api/v1/admin/sessions',
|
||||||
|
...options
|
||||||
|
});
|
||||||
|
};
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Get My Organizations
|
* Get My Organizations
|
||||||
*
|
*
|
||||||
|
|||||||
@@ -23,6 +23,76 @@ export type AddMemberRequest = {
|
|||||||
role?: OrganizationRole;
|
role?: OrganizationRole;
|
||||||
};
|
};
|
||||||
|
|
||||||
|
/**
|
||||||
|
* AdminSessionResponse
|
||||||
|
*
|
||||||
|
* Schema for session responses in admin panel.
|
||||||
|
*
|
||||||
|
* Includes user information for admin to see who owns each session.
|
||||||
|
*/
|
||||||
|
export type AdminSessionResponse = {
|
||||||
|
/**
|
||||||
|
* Device Name
|
||||||
|
*
|
||||||
|
* Friendly device name
|
||||||
|
*/
|
||||||
|
device_name?: string | null;
|
||||||
|
/**
|
||||||
|
* Device Id
|
||||||
|
*
|
||||||
|
* Persistent device identifier
|
||||||
|
*/
|
||||||
|
device_id?: string | null;
|
||||||
|
/**
|
||||||
|
* Id
|
||||||
|
*/
|
||||||
|
id: string;
|
||||||
|
/**
|
||||||
|
* User Id
|
||||||
|
*/
|
||||||
|
user_id: string;
|
||||||
|
/**
|
||||||
|
* User Email
|
||||||
|
*
|
||||||
|
* Email of the user who owns this session
|
||||||
|
*/
|
||||||
|
user_email: string;
|
||||||
|
/**
|
||||||
|
* User Full Name
|
||||||
|
*
|
||||||
|
* Full name of the user
|
||||||
|
*/
|
||||||
|
user_full_name?: string | null;
|
||||||
|
/**
|
||||||
|
* Ip Address
|
||||||
|
*/
|
||||||
|
ip_address?: string | null;
|
||||||
|
/**
|
||||||
|
* Location City
|
||||||
|
*/
|
||||||
|
location_city?: string | null;
|
||||||
|
/**
|
||||||
|
* Location Country
|
||||||
|
*/
|
||||||
|
location_country?: string | null;
|
||||||
|
/**
|
||||||
|
* Last Used At
|
||||||
|
*/
|
||||||
|
last_used_at: string;
|
||||||
|
/**
|
||||||
|
* Created At
|
||||||
|
*/
|
||||||
|
created_at: string;
|
||||||
|
/**
|
||||||
|
* Expires At
|
||||||
|
*/
|
||||||
|
expires_at: string;
|
||||||
|
/**
|
||||||
|
* Is Active
|
||||||
|
*/
|
||||||
|
is_active: boolean;
|
||||||
|
};
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Body_login_oauth
|
* Body_login_oauth
|
||||||
*/
|
*/
|
||||||
@@ -312,6 +382,22 @@ export type OrganizationUpdate = {
|
|||||||
} | null;
|
} | null;
|
||||||
};
|
};
|
||||||
|
|
||||||
|
/**
|
||||||
|
* PaginatedResponse[AdminSessionResponse]
|
||||||
|
*/
|
||||||
|
export type PaginatedResponseAdminSessionResponse = {
|
||||||
|
/**
|
||||||
|
* Data
|
||||||
|
*
|
||||||
|
* List of items
|
||||||
|
*/
|
||||||
|
data: Array<AdminSessionResponse>;
|
||||||
|
/**
|
||||||
|
* Pagination metadata
|
||||||
|
*/
|
||||||
|
pagination: PaginationMeta;
|
||||||
|
};
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* PaginatedResponse[OrganizationMemberResponse]
|
* PaginatedResponse[OrganizationMemberResponse]
|
||||||
*/
|
*/
|
||||||
@@ -1711,6 +1797,46 @@ export type AdminRemoveOrganizationMemberResponses = {
|
|||||||
|
|
||||||
export type AdminRemoveOrganizationMemberResponse = AdminRemoveOrganizationMemberResponses[keyof AdminRemoveOrganizationMemberResponses];
|
export type AdminRemoveOrganizationMemberResponse = AdminRemoveOrganizationMemberResponses[keyof AdminRemoveOrganizationMemberResponses];
|
||||||
|
|
||||||
|
export type AdminListSessionsData = {
|
||||||
|
body?: never;
|
||||||
|
path?: never;
|
||||||
|
query?: {
|
||||||
|
/**
|
||||||
|
* Is Active
|
||||||
|
*
|
||||||
|
* Filter by active status
|
||||||
|
*/
|
||||||
|
is_active?: boolean | null;
|
||||||
|
/**
|
||||||
|
* Page
|
||||||
|
*/
|
||||||
|
page?: number;
|
||||||
|
/**
|
||||||
|
* Limit
|
||||||
|
*/
|
||||||
|
limit?: number;
|
||||||
|
};
|
||||||
|
url: '/api/v1/admin/sessions';
|
||||||
|
};
|
||||||
|
|
||||||
|
export type AdminListSessionsErrors = {
|
||||||
|
/**
|
||||||
|
* Validation Error
|
||||||
|
*/
|
||||||
|
422: HttpValidationError;
|
||||||
|
};
|
||||||
|
|
||||||
|
export type AdminListSessionsError = AdminListSessionsErrors[keyof AdminListSessionsErrors];
|
||||||
|
|
||||||
|
export type AdminListSessionsResponses = {
|
||||||
|
/**
|
||||||
|
* Successful Response
|
||||||
|
*/
|
||||||
|
200: PaginatedResponseAdminSessionResponse;
|
||||||
|
};
|
||||||
|
|
||||||
|
export type AdminListSessionsResponse = AdminListSessionsResponses[keyof AdminListSessionsResponses];
|
||||||
|
|
||||||
export type GetMyOrganizationsData = {
|
export type GetMyOrganizationsData = {
|
||||||
body?: never;
|
body?: never;
|
||||||
path?: never;
|
path?: never;
|
||||||
|
|||||||
@@ -11,31 +11,31 @@
|
|||||||
|
|
||||||
'use client';
|
'use client';
|
||||||
|
|
||||||
import { useQuery, useMutation, useQueryClient } from '@tanstack/react-query';
|
import {useMutation, useQuery, useQueryClient} from '@tanstack/react-query';
|
||||||
import {
|
import {
|
||||||
adminListUsers,
|
type AddMemberRequest,
|
||||||
adminListOrganizations,
|
adminActivateUser,
|
||||||
adminCreateUser,
|
adminAddOrganizationMember,
|
||||||
adminGetUser,
|
adminBulkUserAction,
|
||||||
adminUpdateUser,
|
adminCreateOrganization,
|
||||||
adminDeleteUser,
|
adminCreateUser,
|
||||||
adminActivateUser,
|
adminDeactivateUser,
|
||||||
adminDeactivateUser,
|
adminDeleteOrganization,
|
||||||
adminBulkUserAction,
|
adminDeleteUser,
|
||||||
adminCreateOrganization,
|
adminGetOrganization,
|
||||||
adminUpdateOrganization,
|
adminListOrganizationMembers,
|
||||||
adminDeleteOrganization,
|
adminListOrganizations,
|
||||||
adminGetOrganization,
|
adminListSessions,
|
||||||
adminListOrganizationMembers,
|
adminListUsers,
|
||||||
adminAddOrganizationMember,
|
adminRemoveOrganizationMember,
|
||||||
adminRemoveOrganizationMember,
|
adminUpdateOrganization,
|
||||||
type UserCreate,
|
adminUpdateUser,
|
||||||
type UserUpdate,
|
type OrganizationCreate,
|
||||||
type OrganizationCreate,
|
type OrganizationUpdate,
|
||||||
type OrganizationUpdate,
|
type UserCreate,
|
||||||
type AddMemberRequest,
|
type UserUpdate,
|
||||||
} from '@/lib/api/client';
|
} from '@/lib/api/client';
|
||||||
import { useAuth } from '@/lib/auth/AuthContext';
|
import {useAuth} from '@/lib/auth/AuthContext';
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Constants for admin hooks
|
* Constants for admin hooks
|
||||||
@@ -51,7 +51,7 @@ export interface AdminStats {
|
|||||||
totalUsers: number;
|
totalUsers: number;
|
||||||
activeUsers: number;
|
activeUsers: number;
|
||||||
totalOrganizations: number;
|
totalOrganizations: number;
|
||||||
totalSessions: number; // TODO: Requires admin sessions endpoint
|
totalSessions: number;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -103,19 +103,22 @@ export function useAdminStats() {
|
|||||||
const orgsData = (orgsResponse as { data: { pagination: { total: number } } }).data;
|
const orgsData = (orgsResponse as { data: { pagination: { total: number } } }).data;
|
||||||
const totalOrganizations = orgsData?.pagination?.total || 0;
|
const totalOrganizations = orgsData?.pagination?.total || 0;
|
||||||
|
|
||||||
// TODO: Add admin sessions endpoint
|
// Fetch sessions list
|
||||||
// Currently no admin-level endpoint exists to fetch all sessions
|
const sessionsResponse = await adminListSessions({
|
||||||
// across all users. The /api/v1/sessions/me endpoint only returns
|
query: {
|
||||||
// sessions for the current user.
|
page: 1,
|
||||||
//
|
limit: STATS_FETCH_LIMIT,
|
||||||
// Once backend implements /api/v1/admin/sessions, uncomment below:
|
},
|
||||||
// const sessionsResponse = await adminListSessions({
|
throwOnError: false,
|
||||||
// query: { page: 1, limit: 10000 },
|
});
|
||||||
// throwOnError: false,
|
|
||||||
// });
|
|
||||||
// const totalSessions = sessionsResponse.data?.pagination?.total || 0;
|
|
||||||
|
|
||||||
const totalSessions = 0; // Placeholder until admin sessions endpoint exists
|
if ('error' in sessionsResponse) {
|
||||||
|
throw new Error('Failed to fetch sessions');
|
||||||
|
}
|
||||||
|
|
||||||
|
// Type assertion: if no error, response has data
|
||||||
|
const sessionsData = (sessionsResponse as { data: { pagination: { total: number } } }).data;
|
||||||
|
const totalSessions = sessionsData?.pagination?.total || 0;
|
||||||
|
|
||||||
return {
|
return {
|
||||||
totalUsers,
|
totalUsers,
|
||||||
|
|||||||
Reference in New Issue
Block a user