235 lines
10 KiB
TypeScript
235 lines
10 KiB
TypeScript
import api from './client'
|
|
import type {
|
|
DashboardMetrics,
|
|
ActivityEntry,
|
|
AdminUserListResponse,
|
|
AdminAccountListResponse,
|
|
AuditLogListResponse,
|
|
PlanLimitConfig,
|
|
AccountOverrideResponse,
|
|
AccountOverrideCreate,
|
|
FeatureFlagResponse,
|
|
FeatureFlagCreate,
|
|
PlanDefaultUpdate,
|
|
AccountFeatureOverrideResponse,
|
|
AccountFeatureOverrideCreate,
|
|
AdminCategory,
|
|
GlobalCategoryCreate,
|
|
InviteCodeResponse,
|
|
InviteCodeCreateRequest,
|
|
UserDetailResponse,
|
|
AdminUserCreate,
|
|
AdminUserCreateResponse,
|
|
} from '@/types/admin'
|
|
|
|
export interface SurveyInviteResponse {
|
|
id: string
|
|
token: string
|
|
recipient_name: string
|
|
recipient_email: string | null
|
|
status: string
|
|
email_sent: boolean
|
|
created_at: string
|
|
completed_at: string | null
|
|
survey_url: string
|
|
}
|
|
|
|
export interface SurveyResponseDetail {
|
|
id: string
|
|
respondent_name: string | null
|
|
responses: Record<string, string | string[]>
|
|
source: 'invite' | 'direct'
|
|
invite_name: string | null
|
|
is_read: boolean
|
|
archived_at: string | null
|
|
created_at: string
|
|
}
|
|
|
|
export interface SurveyResponseListResponse {
|
|
responses: SurveyResponseDetail[]
|
|
total: number
|
|
this_week: number
|
|
unread: number
|
|
}
|
|
|
|
export interface GalleryFlowItem {
|
|
id: string
|
|
name: string
|
|
tree_type: string
|
|
is_gallery_featured: boolean
|
|
gallery_sort_order: number
|
|
visibility: string
|
|
}
|
|
|
|
export interface GalleryScriptItem {
|
|
id: string
|
|
name: string
|
|
is_gallery_featured: boolean
|
|
gallery_sort_order: number
|
|
is_active: boolean
|
|
}
|
|
|
|
export const adminApi = {
|
|
// Dashboard
|
|
getDashboardMetrics: () =>
|
|
api.get<DashboardMetrics>('/admin/dashboard/metrics').then(r => r.data),
|
|
getDashboardActivity: () =>
|
|
api.get<ActivityEntry[]>('/admin/dashboard/activity').then(r => r.data),
|
|
|
|
// Users
|
|
createUser: (data: AdminUserCreate) =>
|
|
api.post<AdminUserCreateResponse>('/admin/users', data).then(r => r.data),
|
|
listUsers: (params?: Record<string, unknown>) =>
|
|
api.get<AdminUserListResponse>('/admin/users', { params }).then(r => r.data),
|
|
listAccounts: (params?: Record<string, unknown>) =>
|
|
api.get<AdminAccountListResponse>('/admin/accounts', { params }).then(r => r.data),
|
|
getUser: (id: string) =>
|
|
api.get(`/admin/users/${id}`).then(r => r.data),
|
|
updateUserRole: (id: string, role: string) =>
|
|
api.put(`/admin/users/${id}/role`, { role }).then(r => r.data),
|
|
updateAccountRole: (id: string, account_role: string) =>
|
|
api.put(`/admin/users/${id}/account-role`, { account_role }).then(r => r.data),
|
|
updateSuperAdminStatus: (id: string, is_super_admin: boolean) =>
|
|
api.put(`/admin/users/${id}/super-admin`, { is_super_admin }).then(r => r.data),
|
|
deactivateUser: (id: string) =>
|
|
api.put(`/admin/users/${id}/deactivate`).then(r => r.data),
|
|
activateUser: (id: string) =>
|
|
api.put(`/admin/users/${id}/activate`).then(r => r.data),
|
|
moveUserAccount: (id: string, display_code: string) =>
|
|
api.put(`/admin/users/${id}/move-account`, { display_code }).then(r => r.data),
|
|
|
|
// Users - archive & delete
|
|
archiveUser: (id: string) =>
|
|
api.put(`/admin/users/${id}/archive`).then(r => r.data),
|
|
restoreUser: (id: string) =>
|
|
api.put(`/admin/users/${id}/restore`).then(r => r.data),
|
|
hardDeleteCheck: (id: string) =>
|
|
api.get<{ can_delete: boolean; blockers: Record<string, number> }>(`/admin/users/${id}/hard-delete-check`).then(r => r.data),
|
|
hardDeleteUser: (id: string) =>
|
|
api.delete(`/admin/users/${id}/hard-delete`),
|
|
|
|
// Users - quick invite
|
|
createInvite: (data: { email: string; account_display_code: string; role: string }) =>
|
|
api.post<{ id: string; email: string; code: string; role: string; account_display_code: string; email_sent: boolean }>('/admin/invites', data).then(r => r.data),
|
|
|
|
// Users - password reset
|
|
adminResetPassword: (id: string, mode: 'email_link' | 'temp_password') =>
|
|
api.post<{ message: string; temporary_password?: string; email_sent: boolean }>(`/admin/users/${id}/password-reset`, { mode }).then(r => r.data),
|
|
|
|
// Users - detail + subscription
|
|
getUserDetail: (id: string) =>
|
|
api.get<UserDetailResponse>(`/admin/users/${id}`).then(r => r.data),
|
|
updateUserSubscriptionPlan: (id: string, plan: string) =>
|
|
api.put(`/admin/users/${id}/subscription/plan`, { plan }).then(r => r.data),
|
|
extendUserTrial: (id: string, days: number) =>
|
|
api.put(`/admin/users/${id}/subscription/extend-trial`, { days }).then(r => r.data),
|
|
|
|
// Invite Codes
|
|
listInviteCodes: (params?: Record<string, unknown>) =>
|
|
api.get<InviteCodeResponse[]>('/invites', { params }).then(r => r.data),
|
|
createInviteCode: (data: InviteCodeCreateRequest = {}) =>
|
|
api.post<InviteCodeResponse>('/invites', data).then(r => r.data),
|
|
deleteInviteCode: (code: string) =>
|
|
api.delete(`/invites/${code}`),
|
|
resendInviteCode: (code: string) =>
|
|
api.post<InviteCodeResponse>(`/invites/${code}/resend`).then(r => r.data),
|
|
|
|
// Audit Logs
|
|
listAuditLogs: (params?: Record<string, unknown>) =>
|
|
api.get<AuditLogListResponse>('/admin/audit-logs', { params }).then(r => r.data),
|
|
exportAuditLogs: (params?: Record<string, string>) =>
|
|
api.get('/admin/audit-logs/export', { params, responseType: 'blob' }),
|
|
|
|
// Plan Limits
|
|
listPlanLimits: () =>
|
|
api.get<PlanLimitConfig[]>('/admin/plan-limits').then(r => r.data),
|
|
updatePlanLimits: (data: PlanLimitConfig) =>
|
|
api.put<PlanLimitConfig>('/admin/plan-limits', data).then(r => r.data),
|
|
|
|
// Account Overrides
|
|
listAccountOverrides: () =>
|
|
api.get<AccountOverrideResponse[]>('/admin/account-overrides').then(r => r.data),
|
|
createAccountOverride: (data: AccountOverrideCreate) =>
|
|
api.post<AccountOverrideResponse>('/admin/account-overrides', data).then(r => r.data),
|
|
updateAccountOverride: (id: string, data: Partial<AccountOverrideCreate>) =>
|
|
api.put<AccountOverrideResponse>(`/admin/account-overrides/${id}`, data).then(r => r.data),
|
|
deleteAccountOverride: (id: string) =>
|
|
api.delete(`/admin/account-overrides/${id}`),
|
|
|
|
// Feature Flags
|
|
listFeatureFlags: () =>
|
|
api.get<FeatureFlagResponse[]>('/admin/feature-flags').then(r => r.data),
|
|
createFeatureFlag: (data: FeatureFlagCreate) =>
|
|
api.post<FeatureFlagResponse>('/admin/feature-flags', data).then(r => r.data),
|
|
updateFeatureFlag: (id: string, data: Partial<FeatureFlagCreate>) =>
|
|
api.put<FeatureFlagResponse>(`/admin/feature-flags/${id}`, data).then(r => r.data),
|
|
deleteFeatureFlag: (id: string) =>
|
|
api.delete(`/admin/feature-flags/${id}`),
|
|
updatePlanDefault: (data: PlanDefaultUpdate) =>
|
|
api.put('/admin/feature-flags/plan-defaults', data).then(r => r.data),
|
|
|
|
// Feature Flag Account Overrides
|
|
listFeatureFlagOverrides: () =>
|
|
api.get<AccountFeatureOverrideResponse[]>('/admin/feature-flags/account-overrides').then(r => r.data),
|
|
createFeatureFlagOverride: (data: AccountFeatureOverrideCreate) =>
|
|
api.post<AccountFeatureOverrideResponse>('/admin/feature-flags/account-overrides', data).then(r => r.data),
|
|
deleteFeatureFlagOverride: (id: string) =>
|
|
api.delete(`/admin/feature-flags/account-overrides/${id}`),
|
|
|
|
// Platform Settings
|
|
listSettings: () =>
|
|
api.get<{ settings: Record<string, unknown> }>('/admin/settings').then(r => r.data),
|
|
updateSettings: (settings: Record<string, unknown>) =>
|
|
api.put<{ settings: Record<string, unknown> }>('/admin/settings', { settings }).then(r => r.data),
|
|
|
|
// Global Categories
|
|
listGlobalCategories: () =>
|
|
api.get<AdminCategory[]>('/admin/categories/global').then(r => r.data),
|
|
createGlobalCategory: (data: GlobalCategoryCreate) =>
|
|
api.post<AdminCategory>('/admin/categories/global', data).then(r => r.data),
|
|
updateGlobalCategory: (id: string, data: Partial<GlobalCategoryCreate>) =>
|
|
api.put<AdminCategory>(`/admin/categories/global/${id}`, data).then(r => r.data),
|
|
deleteGlobalCategory: (id: string) =>
|
|
api.delete(`/admin/categories/global/${id}`),
|
|
|
|
// Survey Invites
|
|
listSurveyInvites: () =>
|
|
api.get<SurveyInviteResponse[]>('/admin/survey-invites').then(r => r.data),
|
|
createSurveyInvite: (data: { recipient_name: string; recipient_email?: string; send_email?: boolean }) =>
|
|
api.post<SurveyInviteResponse>('/admin/survey-invites', data).then(r => r.data),
|
|
|
|
// Survey Responses
|
|
listSurveyResponses: (includeArchived = false) =>
|
|
api.get<SurveyResponseListResponse>('/admin/survey-responses', { params: { include_archived: includeArchived } }).then(r => r.data),
|
|
exportSurveyResponsesCsv: () =>
|
|
api.get('/admin/survey-responses/export', { responseType: 'blob' }).then(r => r.data),
|
|
markResponseRead: (id: string) =>
|
|
api.put(`/admin/survey-responses/${id}/read`).then(r => r.data),
|
|
markResponseUnread: (id: string) =>
|
|
api.put(`/admin/survey-responses/${id}/unread`).then(r => r.data),
|
|
archiveResponse: (id: string) =>
|
|
api.put(`/admin/survey-responses/${id}/archive`).then(r => r.data),
|
|
unarchiveResponse: (id: string) =>
|
|
api.put(`/admin/survey-responses/${id}/unarchive`).then(r => r.data),
|
|
deleteResponse: (id: string) =>
|
|
api.delete(`/admin/survey-responses/${id}`),
|
|
bulkActionResponses: (action: string, ids: string[]) =>
|
|
api.post('/admin/survey-responses/bulk', { action, ids }).then(r => r.data),
|
|
|
|
// Gallery Curation
|
|
getGalleryFeatured: () =>
|
|
api.get<{ flows: GalleryFlowItem[]; scripts: GalleryScriptItem[] }>('/admin/gallery/featured').then(r => r.data),
|
|
getGalleryAllItems: () =>
|
|
api.get<{ flows: GalleryFlowItem[]; scripts: GalleryScriptItem[] }>('/admin/gallery/items').then(r => r.data),
|
|
toggleFlowFeatured: (id: string, is_gallery_featured: boolean) =>
|
|
api.patch<GalleryFlowItem>(`/admin/gallery/flows/${id}/feature`, { is_gallery_featured }).then(r => r.data),
|
|
updateFlowSortOrder: (id: string, gallery_sort_order: number) =>
|
|
api.patch<GalleryFlowItem>(`/admin/gallery/flows/${id}/sort-order`, { gallery_sort_order }).then(r => r.data),
|
|
toggleScriptFeatured: (id: string, is_gallery_featured: boolean) =>
|
|
api.patch<GalleryScriptItem>(`/admin/gallery/scripts/${id}/feature`, { is_gallery_featured }).then(r => r.data),
|
|
updateScriptSortOrder: (id: string, gallery_sort_order: number) =>
|
|
api.patch<GalleryScriptItem>(`/admin/gallery/scripts/${id}/sort-order`, { gallery_sort_order }).then(r => r.data),
|
|
}
|
|
|
|
export default adminApi
|