@growsober/sdk 1.0.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (129) hide show
  1. package/README.md +276 -0
  2. package/dist/__tests__/e2e.test.d.ts +7 -0
  3. package/dist/__tests__/e2e.test.js +472 -0
  4. package/dist/api/client.d.ts +11 -0
  5. package/dist/api/client.js +61 -0
  6. package/dist/api/mutations/admin.d.ts +167 -0
  7. package/dist/api/mutations/admin.js +326 -0
  8. package/dist/api/mutations/ambassadors.d.ts +52 -0
  9. package/dist/api/mutations/ambassadors.js +148 -0
  10. package/dist/api/mutations/auth.d.ts +267 -0
  11. package/dist/api/mutations/auth.js +332 -0
  12. package/dist/api/mutations/bookings.d.ts +59 -0
  13. package/dist/api/mutations/bookings.js +143 -0
  14. package/dist/api/mutations/event-chat.d.ts +35 -0
  15. package/dist/api/mutations/event-chat.js +147 -0
  16. package/dist/api/mutations/events.d.ts +87 -0
  17. package/dist/api/mutations/events.js +205 -0
  18. package/dist/api/mutations/grow90.d.ts +36 -0
  19. package/dist/api/mutations/grow90.js +132 -0
  20. package/dist/api/mutations/hubs.d.ts +111 -0
  21. package/dist/api/mutations/hubs.js +240 -0
  22. package/dist/api/mutations/index.d.ts +22 -0
  23. package/dist/api/mutations/index.js +39 -0
  24. package/dist/api/mutations/jack.d.ts +61 -0
  25. package/dist/api/mutations/jack.js +104 -0
  26. package/dist/api/mutations/library.d.ts +67 -0
  27. package/dist/api/mutations/library.js +168 -0
  28. package/dist/api/mutations/map.d.ts +153 -0
  29. package/dist/api/mutations/map.js +181 -0
  30. package/dist/api/mutations/matching.d.ts +130 -0
  31. package/dist/api/mutations/matching.js +204 -0
  32. package/dist/api/mutations/notifications.d.ts +63 -0
  33. package/dist/api/mutations/notifications.js +106 -0
  34. package/dist/api/mutations/offers.d.ts +26 -0
  35. package/dist/api/mutations/offers.js +47 -0
  36. package/dist/api/mutations/subscriptions.d.ts +127 -0
  37. package/dist/api/mutations/subscriptions.js +140 -0
  38. package/dist/api/mutations/support.d.ts +165 -0
  39. package/dist/api/mutations/support.js +307 -0
  40. package/dist/api/mutations/users.d.ts +211 -0
  41. package/dist/api/mutations/users.js +261 -0
  42. package/dist/api/queries/admin.d.ts +257 -0
  43. package/dist/api/queries/admin.js +320 -0
  44. package/dist/api/queries/ambassadors.d.ts +53 -0
  45. package/dist/api/queries/ambassadors.js +98 -0
  46. package/dist/api/queries/auth.d.ts +16 -0
  47. package/dist/api/queries/auth.js +25 -0
  48. package/dist/api/queries/bookings.d.ts +91 -0
  49. package/dist/api/queries/bookings.js +102 -0
  50. package/dist/api/queries/businesses.d.ts +212 -0
  51. package/dist/api/queries/businesses.js +154 -0
  52. package/dist/api/queries/event-chat.d.ts +19 -0
  53. package/dist/api/queries/event-chat.js +75 -0
  54. package/dist/api/queries/events.d.ts +322 -0
  55. package/dist/api/queries/events.js +221 -0
  56. package/dist/api/queries/grow90.d.ts +26 -0
  57. package/dist/api/queries/grow90.js +85 -0
  58. package/dist/api/queries/hubs.d.ts +165 -0
  59. package/dist/api/queries/hubs.js +143 -0
  60. package/dist/api/queries/index.d.ts +23 -0
  61. package/dist/api/queries/index.js +40 -0
  62. package/dist/api/queries/jack.d.ts +63 -0
  63. package/dist/api/queries/jack.js +92 -0
  64. package/dist/api/queries/library.d.ts +132 -0
  65. package/dist/api/queries/library.js +120 -0
  66. package/dist/api/queries/map.d.ts +216 -0
  67. package/dist/api/queries/map.js +278 -0
  68. package/dist/api/queries/matching.d.ts +136 -0
  69. package/dist/api/queries/matching.js +161 -0
  70. package/dist/api/queries/notifications.d.ts +78 -0
  71. package/dist/api/queries/notifications.js +88 -0
  72. package/dist/api/queries/offers.d.ts +91 -0
  73. package/dist/api/queries/offers.js +103 -0
  74. package/dist/api/queries/subscriptions.d.ts +56 -0
  75. package/dist/api/queries/subscriptions.js +73 -0
  76. package/dist/api/queries/support.d.ts +106 -0
  77. package/dist/api/queries/support.js +202 -0
  78. package/dist/api/queries/users.d.ts +293 -0
  79. package/dist/api/queries/users.js +370 -0
  80. package/dist/api/types.d.ts +464 -0
  81. package/dist/api/types.js +9 -0
  82. package/dist/hooks/useAuth.d.ts +5 -0
  83. package/dist/hooks/useAuth.js +39 -0
  84. package/dist/hooks/useUser.d.ts +43 -0
  85. package/dist/hooks/useUser.js +44 -0
  86. package/dist/index.d.ts +36 -0
  87. package/dist/index.js +67 -0
  88. package/package.json +62 -0
  89. package/src/__tests__/e2e.test.ts +502 -0
  90. package/src/api/client.ts +71 -0
  91. package/src/api/mutations/admin.ts +531 -0
  92. package/src/api/mutations/ambassadors.ts +185 -0
  93. package/src/api/mutations/auth.ts +350 -0
  94. package/src/api/mutations/bookings.ts +190 -0
  95. package/src/api/mutations/event-chat.ts +177 -0
  96. package/src/api/mutations/events.ts +273 -0
  97. package/src/api/mutations/grow90.ts +169 -0
  98. package/src/api/mutations/hubs.ts +385 -0
  99. package/src/api/mutations/index.ts +23 -0
  100. package/src/api/mutations/jack.ts +130 -0
  101. package/src/api/mutations/library.ts +212 -0
  102. package/src/api/mutations/map.ts +230 -0
  103. package/src/api/mutations/matching.ts +271 -0
  104. package/src/api/mutations/notifications.ts +114 -0
  105. package/src/api/mutations/offers.ts +73 -0
  106. package/src/api/mutations/subscriptions.ts +162 -0
  107. package/src/api/mutations/support.ts +390 -0
  108. package/src/api/mutations/users.ts +271 -0
  109. package/src/api/queries/admin.ts +480 -0
  110. package/src/api/queries/ambassadors.ts +139 -0
  111. package/src/api/queries/auth.ts +24 -0
  112. package/src/api/queries/bookings.ts +135 -0
  113. package/src/api/queries/businesses.ts +203 -0
  114. package/src/api/queries/event-chat.ts +78 -0
  115. package/src/api/queries/events.ts +272 -0
  116. package/src/api/queries/grow90.ts +98 -0
  117. package/src/api/queries/hubs.ts +211 -0
  118. package/src/api/queries/index.ts +24 -0
  119. package/src/api/queries/jack.ts +127 -0
  120. package/src/api/queries/library.ts +166 -0
  121. package/src/api/queries/map.ts +331 -0
  122. package/src/api/queries/matching.ts +238 -0
  123. package/src/api/queries/notifications.ts +103 -0
  124. package/src/api/queries/offers.ts +136 -0
  125. package/src/api/queries/subscriptions.ts +91 -0
  126. package/src/api/queries/support.ts +235 -0
  127. package/src/api/queries/users.ts +393 -0
  128. package/src/api/types.ts +596 -0
  129. package/src/index.ts +57 -0
@@ -0,0 +1,71 @@
1
+ import axios, { AxiosInstance, AxiosError, InternalAxiosRequestConfig } from 'axios';
2
+
3
+ export interface SDKConfig {
4
+ baseURL: string;
5
+ getAccessToken: () => string | null | Promise<string | null>;
6
+ refreshAccessToken?: () => Promise<string>;
7
+ onUnauthorized?: () => void;
8
+ }
9
+
10
+ let config: SDKConfig | null = null;
11
+ let apiClient: AxiosInstance | null = null;
12
+
13
+ export function configureSDK(sdkConfig: SDKConfig): void {
14
+ config = sdkConfig;
15
+ apiClient = createApiClient(sdkConfig);
16
+ }
17
+
18
+ export function getApiClient(): AxiosInstance {
19
+ if (!apiClient) {
20
+ throw new Error('SDK not configured. Call configureSDK() first.');
21
+ }
22
+ return apiClient;
23
+ }
24
+
25
+ function createApiClient(sdkConfig: SDKConfig): AxiosInstance {
26
+ const client = axios.create({
27
+ baseURL: sdkConfig.baseURL,
28
+ headers: {
29
+ 'Content-Type': 'application/json',
30
+ },
31
+ });
32
+
33
+ // Request interceptor - add auth token
34
+ client.interceptors.request.use(
35
+ async (requestConfig: InternalAxiosRequestConfig) => {
36
+ const token = await sdkConfig.getAccessToken();
37
+ if (token) {
38
+ requestConfig.headers.Authorization = `Bearer ${token}`;
39
+ }
40
+ return requestConfig;
41
+ },
42
+ (error) => Promise.reject(error)
43
+ );
44
+
45
+ // Response interceptor - handle 401
46
+ client.interceptors.response.use(
47
+ (response) => response,
48
+ async (error: AxiosError) => {
49
+ if (error.response?.status === 401) {
50
+ if (sdkConfig.refreshAccessToken) {
51
+ try {
52
+ const newToken = await sdkConfig.refreshAccessToken();
53
+ if (newToken && error.config) {
54
+ error.config.headers.Authorization = `Bearer ${newToken}`;
55
+ return client.request(error.config);
56
+ }
57
+ } catch {
58
+ sdkConfig.onUnauthorized?.();
59
+ }
60
+ } else {
61
+ sdkConfig.onUnauthorized?.();
62
+ }
63
+ }
64
+ return Promise.reject(error);
65
+ }
66
+ );
67
+
68
+ return client;
69
+ }
70
+
71
+ export { apiClient };
@@ -0,0 +1,531 @@
1
+ /**
2
+ * Admin Mutation Hooks
3
+ *
4
+ * TanStack Query mutation hooks for admin-related write operations.
5
+ * These hooks handle admin actions like user management, content moderation,
6
+ * and business verification.
7
+ *
8
+ * @module api/mutations/admin
9
+ */
10
+
11
+ import {
12
+ useMutation,
13
+ UseMutationOptions,
14
+ UseMutationResult,
15
+ useQueryClient,
16
+ } from '@tanstack/react-query';
17
+ import { getApiClient } from '../client';
18
+ import { adminKeys } from '../queries/admin';
19
+ import type {
20
+ UserResponse,
21
+ HubResponse,
22
+ EventResponse,
23
+ BusinessResponse,
24
+ LibraryContentResponse,
25
+ CreateHubRequest,
26
+ UpdateHubRequest,
27
+ UpdateEventRequest,
28
+ } from '../types';
29
+
30
+ // ============================================================================
31
+ // REQUEST TYPES
32
+ // ============================================================================
33
+
34
+ export interface AdminUpdateUserRequest {
35
+ displayName?: string;
36
+ email?: string;
37
+ role?: string;
38
+ isPremium?: boolean;
39
+ isSuspended?: boolean;
40
+ }
41
+
42
+ export interface AdminCreateContentRequest {
43
+ title: string;
44
+ type: string;
45
+ category: string;
46
+ description?: string;
47
+ content?: string;
48
+ mediaUrl?: string;
49
+ thumbnailUrl?: string;
50
+ duration?: number;
51
+ isPremium?: boolean;
52
+ isFeatured?: boolean;
53
+ sortOrder?: number;
54
+ }
55
+
56
+ export interface AdminUpdateContentRequest extends Partial<AdminCreateContentRequest> {}
57
+
58
+ export interface AdminVerifyBusinessRequest {
59
+ isVerified: boolean;
60
+ notes?: string;
61
+ }
62
+
63
+ // ============================================================================
64
+ // RESPONSE TYPES
65
+ // ============================================================================
66
+
67
+ export interface AdminActionResponse {
68
+ success: boolean;
69
+ message: string;
70
+ }
71
+
72
+ // ============================================================================
73
+ // USER MUTATIONS
74
+ // ============================================================================
75
+
76
+ /**
77
+ * Update user (admin)
78
+ *
79
+ * @endpoint PUT /api/v1/admin/users/{id}
80
+ */
81
+ export function useAdminUpdateUser(
82
+ options?: Omit<
83
+ UseMutationOptions<UserResponse, Error, { id: string; data: AdminUpdateUserRequest }>,
84
+ 'mutationFn'
85
+ >
86
+ ): UseMutationResult<UserResponse, Error, { id: string; data: AdminUpdateUserRequest }> {
87
+ const queryClient = useQueryClient();
88
+
89
+ return useMutation({
90
+ mutationFn: async ({
91
+ id,
92
+ data,
93
+ }: {
94
+ id: string;
95
+ data: AdminUpdateUserRequest;
96
+ }): Promise<UserResponse> => {
97
+ const client = getApiClient();
98
+ const response = await client.put<UserResponse>(`/api/v1/admin/users/${id}`, data);
99
+ return response.data;
100
+ },
101
+ onSuccess: (_, variables) => {
102
+ queryClient.invalidateQueries({ queryKey: adminKeys.users.detail(variables.id) });
103
+ queryClient.invalidateQueries({ queryKey: adminKeys.users.list() });
104
+ queryClient.invalidateQueries({ queryKey: adminKeys.dashboard() });
105
+ },
106
+ ...options,
107
+ });
108
+ }
109
+
110
+ /**
111
+ * Suspend user (admin)
112
+ *
113
+ * @endpoint POST /api/v1/admin/users/{id}/suspend
114
+ */
115
+ export function useAdminSuspendUser(
116
+ options?: Omit<
117
+ UseMutationOptions<AdminActionResponse, Error, { id: string; reason?: string }>,
118
+ 'mutationFn'
119
+ >
120
+ ): UseMutationResult<AdminActionResponse, Error, { id: string; reason?: string }> {
121
+ const queryClient = useQueryClient();
122
+
123
+ return useMutation({
124
+ mutationFn: async ({
125
+ id,
126
+ reason,
127
+ }: {
128
+ id: string;
129
+ reason?: string;
130
+ }): Promise<AdminActionResponse> => {
131
+ const client = getApiClient();
132
+ const response = await client.post<AdminActionResponse>(
133
+ `/api/v1/admin/users/${id}/suspend`,
134
+ { reason }
135
+ );
136
+ return response.data;
137
+ },
138
+ onSuccess: (_, variables) => {
139
+ queryClient.invalidateQueries({ queryKey: adminKeys.users.detail(variables.id) });
140
+ queryClient.invalidateQueries({ queryKey: adminKeys.users.list() });
141
+ },
142
+ ...options,
143
+ });
144
+ }
145
+
146
+ /**
147
+ * Activate user (admin)
148
+ *
149
+ * @endpoint POST /api/v1/admin/users/{id}/activate
150
+ */
151
+ export function useAdminActivateUser(
152
+ options?: Omit<UseMutationOptions<AdminActionResponse, Error, string>, 'mutationFn'>
153
+ ): UseMutationResult<AdminActionResponse, Error, string> {
154
+ const queryClient = useQueryClient();
155
+
156
+ return useMutation({
157
+ mutationFn: async (id: string): Promise<AdminActionResponse> => {
158
+ const client = getApiClient();
159
+ const response = await client.post<AdminActionResponse>(
160
+ `/api/v1/admin/users/${id}/activate`
161
+ );
162
+ return response.data;
163
+ },
164
+ onSuccess: (_, id) => {
165
+ queryClient.invalidateQueries({ queryKey: adminKeys.users.detail(id) });
166
+ queryClient.invalidateQueries({ queryKey: adminKeys.users.list() });
167
+ },
168
+ ...options,
169
+ });
170
+ }
171
+
172
+ /**
173
+ * Delete user (admin)
174
+ *
175
+ * @endpoint DELETE /api/v1/admin/users/{id}
176
+ */
177
+ export function useAdminDeleteUser(
178
+ options?: Omit<UseMutationOptions<AdminActionResponse, Error, string>, 'mutationFn'>
179
+ ): UseMutationResult<AdminActionResponse, Error, string> {
180
+ const queryClient = useQueryClient();
181
+
182
+ return useMutation({
183
+ mutationFn: async (id: string): Promise<AdminActionResponse> => {
184
+ const client = getApiClient();
185
+ const response = await client.delete<AdminActionResponse>(`/api/v1/admin/users/${id}`);
186
+ return response.data;
187
+ },
188
+ onSuccess: () => {
189
+ queryClient.invalidateQueries({ queryKey: adminKeys.users.list() });
190
+ queryClient.invalidateQueries({ queryKey: adminKeys.dashboard() });
191
+ },
192
+ ...options,
193
+ });
194
+ }
195
+
196
+ // ============================================================================
197
+ // HUB MUTATIONS
198
+ // ============================================================================
199
+
200
+ /**
201
+ * Create hub (admin)
202
+ *
203
+ * @endpoint POST /api/v1/admin/hubs
204
+ */
205
+ export function useAdminCreateHub(
206
+ options?: Omit<UseMutationOptions<HubResponse, Error, CreateHubRequest>, 'mutationFn'>
207
+ ): UseMutationResult<HubResponse, Error, CreateHubRequest> {
208
+ const queryClient = useQueryClient();
209
+
210
+ return useMutation({
211
+ mutationFn: async (data: CreateHubRequest): Promise<HubResponse> => {
212
+ const client = getApiClient();
213
+ const response = await client.post<HubResponse>('/api/v1/admin/hubs', data);
214
+ return response.data;
215
+ },
216
+ onSuccess: () => {
217
+ queryClient.invalidateQueries({ queryKey: adminKeys.hubs.list() });
218
+ queryClient.invalidateQueries({ queryKey: adminKeys.dashboard() });
219
+ },
220
+ ...options,
221
+ });
222
+ }
223
+
224
+ /**
225
+ * Update hub (admin)
226
+ *
227
+ * @endpoint PUT /api/v1/admin/hubs/{id}
228
+ */
229
+ export function useAdminUpdateHub(
230
+ options?: Omit<
231
+ UseMutationOptions<HubResponse, Error, { id: string; data: UpdateHubRequest }>,
232
+ 'mutationFn'
233
+ >
234
+ ): UseMutationResult<HubResponse, Error, { id: string; data: UpdateHubRequest }> {
235
+ const queryClient = useQueryClient();
236
+
237
+ return useMutation({
238
+ mutationFn: async ({
239
+ id,
240
+ data,
241
+ }: {
242
+ id: string;
243
+ data: UpdateHubRequest;
244
+ }): Promise<HubResponse> => {
245
+ const client = getApiClient();
246
+ const response = await client.put<HubResponse>(`/api/v1/admin/hubs/${id}`, data);
247
+ return response.data;
248
+ },
249
+ onSuccess: (_, variables) => {
250
+ queryClient.invalidateQueries({ queryKey: adminKeys.hubs.detail(variables.id) });
251
+ queryClient.invalidateQueries({ queryKey: adminKeys.hubs.list() });
252
+ },
253
+ ...options,
254
+ });
255
+ }
256
+
257
+ /**
258
+ * Delete hub (admin)
259
+ *
260
+ * @endpoint DELETE /api/v1/admin/hubs/{id}
261
+ */
262
+ export function useAdminDeleteHub(
263
+ options?: Omit<UseMutationOptions<AdminActionResponse, Error, string>, 'mutationFn'>
264
+ ): UseMutationResult<AdminActionResponse, Error, string> {
265
+ const queryClient = useQueryClient();
266
+
267
+ return useMutation({
268
+ mutationFn: async (id: string): Promise<AdminActionResponse> => {
269
+ const client = getApiClient();
270
+ const response = await client.delete<AdminActionResponse>(`/api/v1/admin/hubs/${id}`);
271
+ return response.data;
272
+ },
273
+ onSuccess: () => {
274
+ queryClient.invalidateQueries({ queryKey: adminKeys.hubs.list() });
275
+ queryClient.invalidateQueries({ queryKey: adminKeys.dashboard() });
276
+ },
277
+ ...options,
278
+ });
279
+ }
280
+
281
+ // ============================================================================
282
+ // EVENT MUTATIONS
283
+ // ============================================================================
284
+
285
+ /**
286
+ * Update event (admin)
287
+ *
288
+ * @endpoint PUT /api/v1/admin/events/{id}
289
+ */
290
+ export function useAdminUpdateEvent(
291
+ options?: Omit<
292
+ UseMutationOptions<EventResponse, Error, { id: string; data: UpdateEventRequest }>,
293
+ 'mutationFn'
294
+ >
295
+ ): UseMutationResult<EventResponse, Error, { id: string; data: UpdateEventRequest }> {
296
+ const queryClient = useQueryClient();
297
+
298
+ return useMutation({
299
+ mutationFn: async ({
300
+ id,
301
+ data,
302
+ }: {
303
+ id: string;
304
+ data: UpdateEventRequest;
305
+ }): Promise<EventResponse> => {
306
+ const client = getApiClient();
307
+ const response = await client.put<EventResponse>(`/api/v1/admin/events/${id}`, data);
308
+ return response.data;
309
+ },
310
+ onSuccess: (_, variables) => {
311
+ queryClient.invalidateQueries({ queryKey: adminKeys.events.detail(variables.id) });
312
+ queryClient.invalidateQueries({ queryKey: adminKeys.events.list() });
313
+ },
314
+ ...options,
315
+ });
316
+ }
317
+
318
+ /**
319
+ * Cancel event (admin)
320
+ *
321
+ * @endpoint POST /api/v1/admin/events/{id}/cancel
322
+ */
323
+ export function useAdminCancelEvent(
324
+ options?: Omit<
325
+ UseMutationOptions<AdminActionResponse, Error, { id: string; reason?: string }>,
326
+ 'mutationFn'
327
+ >
328
+ ): UseMutationResult<AdminActionResponse, Error, { id: string; reason?: string }> {
329
+ const queryClient = useQueryClient();
330
+
331
+ return useMutation({
332
+ mutationFn: async ({
333
+ id,
334
+ reason,
335
+ }: {
336
+ id: string;
337
+ reason?: string;
338
+ }): Promise<AdminActionResponse> => {
339
+ const client = getApiClient();
340
+ const response = await client.post<AdminActionResponse>(
341
+ `/api/v1/admin/events/${id}/cancel`,
342
+ { reason }
343
+ );
344
+ return response.data;
345
+ },
346
+ onSuccess: (_, variables) => {
347
+ queryClient.invalidateQueries({ queryKey: adminKeys.events.detail(variables.id) });
348
+ queryClient.invalidateQueries({ queryKey: adminKeys.events.list() });
349
+ },
350
+ ...options,
351
+ });
352
+ }
353
+
354
+ // ============================================================================
355
+ // BUSINESS MUTATIONS
356
+ // ============================================================================
357
+
358
+ /**
359
+ * Verify business (admin)
360
+ *
361
+ * @endpoint POST /api/v1/admin/businesses/{id}/verify
362
+ */
363
+ export function useAdminVerifyBusiness(
364
+ options?: Omit<
365
+ UseMutationOptions<
366
+ BusinessResponse,
367
+ Error,
368
+ { id: string; data: AdminVerifyBusinessRequest }
369
+ >,
370
+ 'mutationFn'
371
+ >
372
+ ): UseMutationResult<
373
+ BusinessResponse,
374
+ Error,
375
+ { id: string; data: AdminVerifyBusinessRequest }
376
+ > {
377
+ const queryClient = useQueryClient();
378
+
379
+ return useMutation({
380
+ mutationFn: async ({
381
+ id,
382
+ data,
383
+ }: {
384
+ id: string;
385
+ data: AdminVerifyBusinessRequest;
386
+ }): Promise<BusinessResponse> => {
387
+ const client = getApiClient();
388
+ const response = await client.post<BusinessResponse>(
389
+ `/api/v1/admin/businesses/${id}/verify`,
390
+ data
391
+ );
392
+ return response.data;
393
+ },
394
+ onSuccess: (_, variables) => {
395
+ queryClient.invalidateQueries({
396
+ queryKey: adminKeys.businesses.detail(variables.id),
397
+ });
398
+ queryClient.invalidateQueries({ queryKey: adminKeys.businesses.list() });
399
+ queryClient.invalidateQueries({ queryKey: adminKeys.dashboard() });
400
+ },
401
+ ...options,
402
+ });
403
+ }
404
+
405
+ /**
406
+ * Delete business (admin)
407
+ *
408
+ * @endpoint DELETE /api/v1/admin/businesses/{id}
409
+ */
410
+ export function useAdminDeleteBusiness(
411
+ options?: Omit<UseMutationOptions<AdminActionResponse, Error, string>, 'mutationFn'>
412
+ ): UseMutationResult<AdminActionResponse, Error, string> {
413
+ const queryClient = useQueryClient();
414
+
415
+ return useMutation({
416
+ mutationFn: async (id: string): Promise<AdminActionResponse> => {
417
+ const client = getApiClient();
418
+ const response = await client.delete<AdminActionResponse>(
419
+ `/api/v1/admin/businesses/${id}`
420
+ );
421
+ return response.data;
422
+ },
423
+ onSuccess: () => {
424
+ queryClient.invalidateQueries({ queryKey: adminKeys.businesses.list() });
425
+ queryClient.invalidateQueries({ queryKey: adminKeys.dashboard() });
426
+ },
427
+ ...options,
428
+ });
429
+ }
430
+
431
+ // ============================================================================
432
+ // CONTENT MUTATIONS
433
+ // ============================================================================
434
+
435
+ /**
436
+ * Create content (admin)
437
+ *
438
+ * @endpoint POST /api/v1/admin/content
439
+ */
440
+ export function useAdminCreateContent(
441
+ options?: Omit<
442
+ UseMutationOptions<LibraryContentResponse, Error, AdminCreateContentRequest>,
443
+ 'mutationFn'
444
+ >
445
+ ): UseMutationResult<LibraryContentResponse, Error, AdminCreateContentRequest> {
446
+ const queryClient = useQueryClient();
447
+
448
+ return useMutation({
449
+ mutationFn: async (data: AdminCreateContentRequest): Promise<LibraryContentResponse> => {
450
+ const client = getApiClient();
451
+ const response = await client.post<LibraryContentResponse>(
452
+ '/api/v1/admin/content',
453
+ data
454
+ );
455
+ return response.data;
456
+ },
457
+ onSuccess: () => {
458
+ queryClient.invalidateQueries({ queryKey: adminKeys.content.list() });
459
+ },
460
+ ...options,
461
+ });
462
+ }
463
+
464
+ /**
465
+ * Update content (admin)
466
+ *
467
+ * @endpoint PUT /api/v1/admin/content/{id}
468
+ */
469
+ export function useAdminUpdateContent(
470
+ options?: Omit<
471
+ UseMutationOptions<
472
+ LibraryContentResponse,
473
+ Error,
474
+ { id: string; data: AdminUpdateContentRequest }
475
+ >,
476
+ 'mutationFn'
477
+ >
478
+ ): UseMutationResult<
479
+ LibraryContentResponse,
480
+ Error,
481
+ { id: string; data: AdminUpdateContentRequest }
482
+ > {
483
+ const queryClient = useQueryClient();
484
+
485
+ return useMutation({
486
+ mutationFn: async ({
487
+ id,
488
+ data,
489
+ }: {
490
+ id: string;
491
+ data: AdminUpdateContentRequest;
492
+ }): Promise<LibraryContentResponse> => {
493
+ const client = getApiClient();
494
+ const response = await client.put<LibraryContentResponse>(
495
+ `/api/v1/admin/content/${id}`,
496
+ data
497
+ );
498
+ return response.data;
499
+ },
500
+ onSuccess: (_, variables) => {
501
+ queryClient.invalidateQueries({ queryKey: adminKeys.content.detail(variables.id) });
502
+ queryClient.invalidateQueries({ queryKey: adminKeys.content.list() });
503
+ },
504
+ ...options,
505
+ });
506
+ }
507
+
508
+ /**
509
+ * Delete content (admin)
510
+ *
511
+ * @endpoint DELETE /api/v1/admin/content/{id}
512
+ */
513
+ export function useAdminDeleteContent(
514
+ options?: Omit<UseMutationOptions<AdminActionResponse, Error, string>, 'mutationFn'>
515
+ ): UseMutationResult<AdminActionResponse, Error, string> {
516
+ const queryClient = useQueryClient();
517
+
518
+ return useMutation({
519
+ mutationFn: async (id: string): Promise<AdminActionResponse> => {
520
+ const client = getApiClient();
521
+ const response = await client.delete<AdminActionResponse>(
522
+ `/api/v1/admin/content/${id}`
523
+ );
524
+ return response.data;
525
+ },
526
+ onSuccess: () => {
527
+ queryClient.invalidateQueries({ queryKey: adminKeys.content.list() });
528
+ },
529
+ ...options,
530
+ });
531
+ }