@spotsdev/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.
- package/dist/api/client.d.ts +12 -0
- package/dist/api/client.js +68 -0
- package/dist/api/mutations/clubs.d.ts +47 -0
- package/dist/api/mutations/clubs.js +95 -0
- package/dist/api/mutations/conversations.d.ts +45 -0
- package/dist/api/mutations/conversations.js +110 -0
- package/dist/api/mutations/index.d.ts +13 -0
- package/dist/api/mutations/index.js +38 -0
- package/dist/api/mutations/notifications.d.ts +38 -0
- package/dist/api/mutations/notifications.js +64 -0
- package/dist/api/mutations/orders.d.ts +73 -0
- package/dist/api/mutations/orders.js +116 -0
- package/dist/api/mutations/posts.d.ts +123 -0
- package/dist/api/mutations/posts.js +229 -0
- package/dist/api/mutations/products.d.ts +81 -0
- package/dist/api/mutations/products.js +102 -0
- package/dist/api/mutations/spots.d.ts +59 -0
- package/dist/api/mutations/spots.js +129 -0
- package/dist/api/mutations/users.d.ts +71 -0
- package/dist/api/mutations/users.js +173 -0
- package/dist/api/queries/auth.d.ts +37 -0
- package/dist/api/queries/auth.js +61 -0
- package/dist/api/queries/clubs.d.ts +52 -0
- package/dist/api/queries/clubs.js +116 -0
- package/dist/api/queries/conversations.d.ts +52 -0
- package/dist/api/queries/conversations.js +83 -0
- package/dist/api/queries/index.d.ts +26 -0
- package/dist/api/queries/index.js +65 -0
- package/dist/api/queries/misc.d.ts +54 -0
- package/dist/api/queries/misc.js +129 -0
- package/dist/api/queries/notifications.d.ts +34 -0
- package/dist/api/queries/notifications.js +62 -0
- package/dist/api/queries/orders.d.ts +45 -0
- package/dist/api/queries/orders.js +93 -0
- package/dist/api/queries/posts.d.ts +55 -0
- package/dist/api/queries/posts.js +130 -0
- package/dist/api/queries/products.d.ts +52 -0
- package/dist/api/queries/products.js +89 -0
- package/dist/api/queries/spots.d.ts +78 -0
- package/dist/api/queries/spots.js +168 -0
- package/dist/api/queries/templates.d.ts +42 -0
- package/dist/api/queries/templates.js +86 -0
- package/dist/api/queries/users.d.ts +90 -0
- package/dist/api/queries/users.js +187 -0
- package/dist/api/services/index.d.ts +2 -0
- package/dist/api/services/index.js +8 -0
- package/dist/api/services/marketplace.d.ts +129 -0
- package/dist/api/services/marketplace.js +168 -0
- package/dist/api/types.d.ts +54 -0
- package/dist/api/types.js +34 -0
- package/dist/index.d.ts +38 -0
- package/dist/index.js +73 -0
- package/package.json +57 -0
- package/src/api/client.ts +78 -0
- package/src/api/mutations/clubs.ts +107 -0
- package/src/api/mutations/conversations.ts +124 -0
- package/src/api/mutations/index.ts +29 -0
- package/src/api/mutations/notifications.ts +70 -0
- package/src/api/mutations/orders.ts +174 -0
- package/src/api/mutations/posts.ts +278 -0
- package/src/api/mutations/products.ts +160 -0
- package/src/api/mutations/spots.ts +146 -0
- package/src/api/mutations/users.ts +197 -0
- package/src/api/queries/auth.ts +67 -0
- package/src/api/queries/clubs.ts +135 -0
- package/src/api/queries/conversations.ts +94 -0
- package/src/api/queries/index.ts +48 -0
- package/src/api/queries/misc.ts +140 -0
- package/src/api/queries/notifications.ts +66 -0
- package/src/api/queries/orders.ts +119 -0
- package/src/api/queries/posts.ts +142 -0
- package/src/api/queries/products.ts +123 -0
- package/src/api/queries/spots.ts +201 -0
- package/src/api/queries/templates.ts +95 -0
- package/src/api/queries/users.ts +206 -0
- package/src/api/services/index.ts +6 -0
- package/src/api/services/marketplace.ts +265 -0
- package/src/api/types.ts +144 -0
- package/src/index.ts +63 -0
|
@@ -0,0 +1,54 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Spots SDK Types
|
|
3
|
+
*
|
|
4
|
+
* Type sources:
|
|
5
|
+
* - Entity types (User, Spot, Post, etc.) → import from @prisma/client
|
|
6
|
+
* - DTO types (CreatePostDto, etc.) → import from @spotsdev/types
|
|
7
|
+
*
|
|
8
|
+
* This file provides type aliases for SDK convenience while maintaining
|
|
9
|
+
* single sources of truth:
|
|
10
|
+
* - Prisma schema for entities
|
|
11
|
+
* - OpenAPI spec for DTOs
|
|
12
|
+
*/
|
|
13
|
+
/**
|
|
14
|
+
* Standard API response wrapper from ResponseInterceptor
|
|
15
|
+
* All API responses are wrapped in this format
|
|
16
|
+
*/
|
|
17
|
+
export interface ApiResponse<T> {
|
|
18
|
+
success: boolean;
|
|
19
|
+
data: T;
|
|
20
|
+
timestamp: string;
|
|
21
|
+
}
|
|
22
|
+
/**
|
|
23
|
+
* Paginated response for list endpoints
|
|
24
|
+
* Used inside ApiResponse.data for paginated queries
|
|
25
|
+
*/
|
|
26
|
+
export interface PaginatedResponse<T> {
|
|
27
|
+
data: T[];
|
|
28
|
+
meta: {
|
|
29
|
+
total: number;
|
|
30
|
+
page: number;
|
|
31
|
+
limit: number;
|
|
32
|
+
totalPages: number;
|
|
33
|
+
hasNextPage: boolean;
|
|
34
|
+
hasPreviousPage: boolean;
|
|
35
|
+
};
|
|
36
|
+
}
|
|
37
|
+
export * from '@spotsdev/types';
|
|
38
|
+
export type { User, Spot, SpotPost, PostReply, PostResponse, PostUpvote, PostReport, Club, ClubMember, Conversation, Message, Notification, PostTemplate, Vibe, Interest, Intention, LifeSituation, FavoriteSpot, SpotImage, SpotVibe, SpotIntention, SpotClaim, SpotSubscription, City, Product, Order, OrderItem, Payment, InventoryLog, StripeConnectAccount, SpotType, SpotPostType, AccountStatus, ClaimStatus, ResponseStatus, ReportReason, ReportStatus, NotificationType, ProductType, ProductStatus, OrderStatus, PaymentProvider, PaymentStatus, FulfillmentType, InventoryChangeReason, } from '@prisma/client';
|
|
39
|
+
import type { SendOtpDto, VerifyOtpDto, CreatePostDto, CreateReplyDto, CreateResponseDto, UpdateResponseDto, UpdateUserDto, UpvoteResponseDto, VerifyOtpWrappedResponseDto, CreateConversationDto, CreateMessageDto, ClaimSpotDto } from '@spotsdev/types';
|
|
40
|
+
import type { SpotPost, PostTemplate } from '@prisma/client';
|
|
41
|
+
export type SendOtpRequest = SendOtpDto;
|
|
42
|
+
export type VerifyOtpRequest = VerifyOtpDto;
|
|
43
|
+
export type CreatePostRequest = CreatePostDto;
|
|
44
|
+
export type CreateReplyRequest = CreateReplyDto;
|
|
45
|
+
export type RespondToPostRequest = CreateResponseDto;
|
|
46
|
+
export type UpdateResponseRequest = UpdateResponseDto;
|
|
47
|
+
export type UpdateProfileRequest = UpdateUserDto;
|
|
48
|
+
export type CreateConversationRequest = CreateConversationDto;
|
|
49
|
+
export type SendMessageRequest = CreateMessageDto;
|
|
50
|
+
export type ClaimSpotRequest = ClaimSpotDto;
|
|
51
|
+
export type UpvoteResponse = UpvoteResponseDto;
|
|
52
|
+
export type AuthResponse = VerifyOtpWrappedResponseDto;
|
|
53
|
+
export type Post = SpotPost;
|
|
54
|
+
export type Template = PostTemplate;
|
|
@@ -0,0 +1,34 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
/**
|
|
3
|
+
* Spots SDK Types
|
|
4
|
+
*
|
|
5
|
+
* Type sources:
|
|
6
|
+
* - Entity types (User, Spot, Post, etc.) → import from @prisma/client
|
|
7
|
+
* - DTO types (CreatePostDto, etc.) → import from @spotsdev/types
|
|
8
|
+
*
|
|
9
|
+
* This file provides type aliases for SDK convenience while maintaining
|
|
10
|
+
* single sources of truth:
|
|
11
|
+
* - Prisma schema for entities
|
|
12
|
+
* - OpenAPI spec for DTOs
|
|
13
|
+
*/
|
|
14
|
+
var __createBinding = (this && this.__createBinding) || (Object.create ? (function(o, m, k, k2) {
|
|
15
|
+
if (k2 === undefined) k2 = k;
|
|
16
|
+
var desc = Object.getOwnPropertyDescriptor(m, k);
|
|
17
|
+
if (!desc || ("get" in desc ? !m.__esModule : desc.writable || desc.configurable)) {
|
|
18
|
+
desc = { enumerable: true, get: function() { return m[k]; } };
|
|
19
|
+
}
|
|
20
|
+
Object.defineProperty(o, k2, desc);
|
|
21
|
+
}) : (function(o, m, k, k2) {
|
|
22
|
+
if (k2 === undefined) k2 = k;
|
|
23
|
+
o[k2] = m[k];
|
|
24
|
+
}));
|
|
25
|
+
var __exportStar = (this && this.__exportStar) || function(m, exports) {
|
|
26
|
+
for (var p in m) if (p !== "default" && !Object.prototype.hasOwnProperty.call(exports, p)) __createBinding(exports, m, p);
|
|
27
|
+
};
|
|
28
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
29
|
+
// ============================================================================
|
|
30
|
+
// RE-EXPORTS FROM SOURCES
|
|
31
|
+
// ============================================================================
|
|
32
|
+
// Re-export all DTO types from @spotsdev/types (OpenAPI generated)
|
|
33
|
+
__exportStar(require("@spotsdev/types"), exports);
|
|
34
|
+
//# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoidHlwZXMuanMiLCJzb3VyY2VSb290IjoiIiwic291cmNlcyI6WyIuLi8uLi9zcmMvYXBpL3R5cGVzLnRzIl0sIm5hbWVzIjpbXSwibWFwcGluZ3MiOiI7QUFBQTs7Ozs7Ozs7Ozs7R0FXRzs7Ozs7Ozs7Ozs7Ozs7OztBQWdDSCwrRUFBK0U7QUFDL0UsMEJBQTBCO0FBQzFCLCtFQUErRTtBQUUvRSxtRUFBbUU7QUFDbkUsa0RBQWdDIiwic291cmNlc0NvbnRlbnQiOlsiLyoqXG4gKiBTcG90cyBTREsgVHlwZXNcbiAqXG4gKiBUeXBlIHNvdXJjZXM6XG4gKiAtIEVudGl0eSB0eXBlcyAoVXNlciwgU3BvdCwgUG9zdCwgZXRjLikg4oaSIGltcG9ydCBmcm9tIEBwcmlzbWEvY2xpZW50XG4gKiAtIERUTyB0eXBlcyAoQ3JlYXRlUG9zdER0bywgZXRjLikg4oaSIGltcG9ydCBmcm9tIEBzcG90c2Rldi90eXBlc1xuICpcbiAqIFRoaXMgZmlsZSBwcm92aWRlcyB0eXBlIGFsaWFzZXMgZm9yIFNESyBjb252ZW5pZW5jZSB3aGlsZSBtYWludGFpbmluZ1xuICogc2luZ2xlIHNvdXJjZXMgb2YgdHJ1dGg6XG4gKiAtIFByaXNtYSBzY2hlbWEgZm9yIGVudGl0aWVzXG4gKiAtIE9wZW5BUEkgc3BlYyBmb3IgRFRPc1xuICovXG5cbi8vID09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT1cbi8vIEFQSSBSRVNQT05TRSBUWVBFU1xuLy8gPT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PVxuXG4vKipcbiAqIFN0YW5kYXJkIEFQSSByZXNwb25zZSB3cmFwcGVyIGZyb20gUmVzcG9uc2VJbnRlcmNlcHRvclxuICogQWxsIEFQSSByZXNwb25zZXMgYXJlIHdyYXBwZWQgaW4gdGhpcyBmb3JtYXRcbiAqL1xuZXhwb3J0IGludGVyZmFjZSBBcGlSZXNwb25zZTxUPiB7XG4gIHN1Y2Nlc3M6IGJvb2xlYW47XG4gIGRhdGE6IFQ7XG4gIHRpbWVzdGFtcDogc3RyaW5nO1xufVxuXG4vKipcbiAqIFBhZ2luYXRlZCByZXNwb25zZSBmb3IgbGlzdCBlbmRwb2ludHNcbiAqIFVzZWQgaW5zaWRlIEFwaVJlc3BvbnNlLmRhdGEgZm9yIHBhZ2luYXRlZCBxdWVyaWVzXG4gKi9cbmV4cG9ydCBpbnRlcmZhY2UgUGFnaW5hdGVkUmVzcG9uc2U8VD4ge1xuICBkYXRhOiBUW107XG4gIG1ldGE6IHtcbiAgICB0b3RhbDogbnVtYmVyO1xuICAgIHBhZ2U6IG51bWJlcjtcbiAgICBsaW1pdDogbnVtYmVyO1xuICAgIHRvdGFsUGFnZXM6IG51bWJlcjtcbiAgICBoYXNOZXh0UGFnZTogYm9vbGVhbjtcbiAgICBoYXNQcmV2aW91c1BhZ2U6IGJvb2xlYW47XG4gIH07XG59XG5cbi8vID09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT1cbi8vIFJFLUVYUE9SVFMgRlJPTSBTT1VSQ0VTXG4vLyA9PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09XG5cbi8vIFJlLWV4cG9ydCBhbGwgRFRPIHR5cGVzIGZyb20gQHNwb3RzZGV2L3R5cGVzIChPcGVuQVBJIGdlbmVyYXRlZClcbmV4cG9ydCAqIGZyb20gJ0BzcG90c2Rldi90eXBlcyc7XG5cbi8vIFJlLWV4cG9ydCBlbnRpdHkgdHlwZXMgZnJvbSBAcHJpc21hL2NsaWVudFxuZXhwb3J0IHR5cGUge1xuICAvLyBNb2RlbHNcbiAgVXNlcixcbiAgU3BvdCxcbiAgU3BvdFBvc3QsXG4gIFBvc3RSZXBseSxcbiAgUG9zdFJlc3BvbnNlLFxuICBQb3N0VXB2b3RlLFxuICBQb3N0UmVwb3J0LFxuICBDbHViLFxuICBDbHViTWVtYmVyLFxuICBDb252ZXJzYXRpb24sXG4gIE1lc3NhZ2UsXG4gIE5vdGlmaWNhdGlvbixcbiAgUG9zdFRlbXBsYXRlLFxuICBWaWJlLFxuICBJbnRlcmVzdCxcbiAgSW50ZW50aW9uLFxuICBMaWZlU2l0dWF0aW9uLFxuICBGYXZvcml0ZVNwb3QsXG4gIFNwb3RJbWFnZSxcbiAgU3BvdFZpYmUsXG4gIFNwb3RJbnRlbnRpb24sXG4gIFNwb3RDbGFpbSxcbiAgU3BvdFN1YnNjcmlwdGlvbixcbiAgQ2l0eSxcbiAgLy8gTWFya2V0cGxhY2UgTW9kZWxzXG4gIFByb2R1Y3QsXG4gIE9yZGVyLFxuICBPcmRlckl0ZW0sXG4gIFBheW1lbnQsXG4gIEludmVudG9yeUxvZyxcbiAgU3RyaXBlQ29ubmVjdEFjY291bnQsXG4gIC8vIEVudW1zXG4gIFNwb3RUeXBlLFxuICBTcG90UG9zdFR5cGUsXG4gIEFjY291bnRTdGF0dXMsXG4gIENsYWltU3RhdHVzLFxuICBSZXNwb25zZVN0YXR1cyxcbiAgUmVwb3J0UmVhc29uLFxuICBSZXBvcnRTdGF0dXMsXG4gIE5vdGlmaWNhdGlvblR5cGUsXG4gIC8vIE1hcmtldHBsYWNlIEVudW1zXG4gIFByb2R1Y3RUeXBlLFxuICBQcm9kdWN0U3RhdHVzLFxuICBPcmRlclN0YXR1cyxcbiAgUGF5bWVudFByb3ZpZGVyLFxuICBQYXltZW50U3RhdHVzLFxuICBGdWxmaWxsbWVudFR5cGUsXG4gIEludmVudG9yeUNoYW5nZVJlYXNvbixcbn0gZnJvbSAnQHByaXNtYS9jbGllbnQnO1xuXG4vLyA9PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09XG4vLyBTREsgVFlQRSBBTElBU0VTXG4vLyBUaGVzZSBwcm92aWRlIGNvbnZlbmllbnQgbmFtZXMgdGhhdCBtYXRjaCBTREsgdXNhZ2UgcGF0dGVybnNcbi8vID09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT1cblxuaW1wb3J0IHR5cGUge1xuICBTZW5kT3RwRHRvLFxuICBWZXJpZnlPdHBEdG8sXG4gIENyZWF0ZVBvc3REdG8sXG4gIENyZWF0ZVJlcGx5RHRvLFxuICBDcmVhdGVSZXNwb25zZUR0byxcbiAgVXBkYXRlUmVzcG9uc2VEdG8sXG4gIFVwZGF0ZVVzZXJEdG8sXG4gIFVwdm90ZVJlc3BvbnNlRHRvLFxuICBWZXJpZnlPdHBXcmFwcGVkUmVzcG9uc2VEdG8sXG4gIENyZWF0ZUNvbnZlcnNhdGlvbkR0byxcbiAgQ3JlYXRlTWVzc2FnZUR0byxcbiAgQ2xhaW1TcG90RHRvLFxufSBmcm9tICdAc3BvdHNkZXYvdHlwZXMnO1xuXG5pbXBvcnQgdHlwZSB7IFNwb3RQb3N0LCBQb3N0VGVtcGxhdGUgfSBmcm9tICdAcHJpc21hL2NsaWVudCc7XG5cbi8vIFJlcXVlc3QgdHlwZSBhbGlhc2VzIChtYXAgdG8gRFRPcylcbmV4cG9ydCB0eXBlIFNlbmRPdHBSZXF1ZXN0ID0gU2VuZE90cER0bztcbmV4cG9ydCB0eXBlIFZlcmlmeU90cFJlcXVlc3QgPSBWZXJpZnlPdHBEdG87XG5leHBvcnQgdHlwZSBDcmVhdGVQb3N0UmVxdWVzdCA9IENyZWF0ZVBvc3REdG87XG5leHBvcnQgdHlwZSBDcmVhdGVSZXBseVJlcXVlc3QgPSBDcmVhdGVSZXBseUR0bztcbmV4cG9ydCB0eXBlIFJlc3BvbmRUb1Bvc3RSZXF1ZXN0ID0gQ3JlYXRlUmVzcG9uc2VEdG87XG5leHBvcnQgdHlwZSBVcGRhdGVSZXNwb25zZVJlcXVlc3QgPSBVcGRhdGVSZXNwb25zZUR0bztcbmV4cG9ydCB0eXBlIFVwZGF0ZVByb2ZpbGVSZXF1ZXN0ID0gVXBkYXRlVXNlckR0bztcbmV4cG9ydCB0eXBlIENyZWF0ZUNvbnZlcnNhdGlvblJlcXVlc3QgPSBDcmVhdGVDb252ZXJzYXRpb25EdG87XG5leHBvcnQgdHlwZSBTZW5kTWVzc2FnZVJlcXVlc3QgPSBDcmVhdGVNZXNzYWdlRHRvO1xuZXhwb3J0IHR5cGUgQ2xhaW1TcG90UmVxdWVzdCA9IENsYWltU3BvdER0bztcblxuLy8gUmVzcG9uc2UgdHlwZSBhbGlhc2VzXG5leHBvcnQgdHlwZSBVcHZvdGVSZXNwb25zZSA9IFVwdm90ZVJlc3BvbnNlRHRvO1xuZXhwb3J0IHR5cGUgQXV0aFJlc3BvbnNlID0gVmVyaWZ5T3RwV3JhcHBlZFJlc3BvbnNlRHRvO1xuXG4vLyBFbnRpdHkgdHlwZSBhbGlhc2VzIChmb3IgYmFja3dhcmQgY29tcGF0aWJpbGl0eSlcbmV4cG9ydCB0eXBlIFBvc3QgPSBTcG90UG9zdDtcbmV4cG9ydCB0eXBlIFRlbXBsYXRlID0gUG9zdFRlbXBsYXRlO1xuIl19
|
package/dist/index.d.ts
ADDED
|
@@ -0,0 +1,38 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Spots SDK
|
|
3
|
+
*
|
|
4
|
+
* TypeScript SDK for the Spots API with TanStack Query hooks.
|
|
5
|
+
*
|
|
6
|
+
* @example
|
|
7
|
+
* ```tsx
|
|
8
|
+
* import { configureSDK, useCurrentUser, useSpots, useCreatePost } from '@spots/sdk';
|
|
9
|
+
*
|
|
10
|
+
* // Configure SDK with your API base URL and token management
|
|
11
|
+
* configureSDK({
|
|
12
|
+
* baseURL: 'https://spots-api-psi.vercel.app',
|
|
13
|
+
* getAccessToken: () => localStorage.getItem('accessToken'),
|
|
14
|
+
* refreshAccessToken: async () => {
|
|
15
|
+
* // Your token refresh logic
|
|
16
|
+
* return newAccessToken;
|
|
17
|
+
* },
|
|
18
|
+
* onUnauthorized: () => {
|
|
19
|
+
* // Handle unauthorized access
|
|
20
|
+
* window.location.href = '/login';
|
|
21
|
+
* },
|
|
22
|
+
* });
|
|
23
|
+
*
|
|
24
|
+
* // Use hooks in your components
|
|
25
|
+
* function App() {
|
|
26
|
+
* const { data: user } = useCurrentUser();
|
|
27
|
+
* const { data: spots } = useSpots();
|
|
28
|
+
* const { mutate: createPost } = useCreatePost();
|
|
29
|
+
* // ...
|
|
30
|
+
* }
|
|
31
|
+
* ```
|
|
32
|
+
*/
|
|
33
|
+
export { configureSDK, getApiClient, getConfig } from './api/client';
|
|
34
|
+
export type { SDKConfig } from './api/client';
|
|
35
|
+
export * from './api/types';
|
|
36
|
+
export * from './api/queries';
|
|
37
|
+
export * from './api/mutations';
|
|
38
|
+
export * from './api/services';
|
package/dist/index.js
ADDED
|
@@ -0,0 +1,73 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
/**
|
|
3
|
+
* Spots SDK
|
|
4
|
+
*
|
|
5
|
+
* TypeScript SDK for the Spots API with TanStack Query hooks.
|
|
6
|
+
*
|
|
7
|
+
* @example
|
|
8
|
+
* ```tsx
|
|
9
|
+
* import { configureSDK, useCurrentUser, useSpots, useCreatePost } from '@spots/sdk';
|
|
10
|
+
*
|
|
11
|
+
* // Configure SDK with your API base URL and token management
|
|
12
|
+
* configureSDK({
|
|
13
|
+
* baseURL: 'https://spots-api-psi.vercel.app',
|
|
14
|
+
* getAccessToken: () => localStorage.getItem('accessToken'),
|
|
15
|
+
* refreshAccessToken: async () => {
|
|
16
|
+
* // Your token refresh logic
|
|
17
|
+
* return newAccessToken;
|
|
18
|
+
* },
|
|
19
|
+
* onUnauthorized: () => {
|
|
20
|
+
* // Handle unauthorized access
|
|
21
|
+
* window.location.href = '/login';
|
|
22
|
+
* },
|
|
23
|
+
* });
|
|
24
|
+
*
|
|
25
|
+
* // Use hooks in your components
|
|
26
|
+
* function App() {
|
|
27
|
+
* const { data: user } = useCurrentUser();
|
|
28
|
+
* const { data: spots } = useSpots();
|
|
29
|
+
* const { mutate: createPost } = useCreatePost();
|
|
30
|
+
* // ...
|
|
31
|
+
* }
|
|
32
|
+
* ```
|
|
33
|
+
*/
|
|
34
|
+
var __createBinding = (this && this.__createBinding) || (Object.create ? (function(o, m, k, k2) {
|
|
35
|
+
if (k2 === undefined) k2 = k;
|
|
36
|
+
var desc = Object.getOwnPropertyDescriptor(m, k);
|
|
37
|
+
if (!desc || ("get" in desc ? !m.__esModule : desc.writable || desc.configurable)) {
|
|
38
|
+
desc = { enumerable: true, get: function() { return m[k]; } };
|
|
39
|
+
}
|
|
40
|
+
Object.defineProperty(o, k2, desc);
|
|
41
|
+
}) : (function(o, m, k, k2) {
|
|
42
|
+
if (k2 === undefined) k2 = k;
|
|
43
|
+
o[k2] = m[k];
|
|
44
|
+
}));
|
|
45
|
+
var __exportStar = (this && this.__exportStar) || function(m, exports) {
|
|
46
|
+
for (var p in m) if (p !== "default" && !Object.prototype.hasOwnProperty.call(exports, p)) __createBinding(exports, m, p);
|
|
47
|
+
};
|
|
48
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
49
|
+
exports.getConfig = exports.getApiClient = exports.configureSDK = void 0;
|
|
50
|
+
// ============================================================================
|
|
51
|
+
// API CLIENT
|
|
52
|
+
// ============================================================================
|
|
53
|
+
var client_1 = require("./api/client");
|
|
54
|
+
Object.defineProperty(exports, "configureSDK", { enumerable: true, get: function () { return client_1.configureSDK; } });
|
|
55
|
+
Object.defineProperty(exports, "getApiClient", { enumerable: true, get: function () { return client_1.getApiClient; } });
|
|
56
|
+
Object.defineProperty(exports, "getConfig", { enumerable: true, get: function () { return client_1.getConfig; } });
|
|
57
|
+
// ============================================================================
|
|
58
|
+
// TYPES
|
|
59
|
+
// ============================================================================
|
|
60
|
+
__exportStar(require("./api/types"), exports);
|
|
61
|
+
// ============================================================================
|
|
62
|
+
// QUERY HOOKS
|
|
63
|
+
// ============================================================================
|
|
64
|
+
__exportStar(require("./api/queries"), exports);
|
|
65
|
+
// ============================================================================
|
|
66
|
+
// MUTATION HOOKS
|
|
67
|
+
// ============================================================================
|
|
68
|
+
__exportStar(require("./api/mutations"), exports);
|
|
69
|
+
// ============================================================================
|
|
70
|
+
// SERVICES (Plain async functions for testing/non-React)
|
|
71
|
+
// ============================================================================
|
|
72
|
+
__exportStar(require("./api/services"), exports);
|
|
73
|
+
//# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoiaW5kZXguanMiLCJzb3VyY2VSb290IjoiIiwic291cmNlcyI6WyIuLi9zcmMvaW5kZXgudHMiXSwibmFtZXMiOltdLCJtYXBwaW5ncyI6IjtBQUFBOzs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7Ozs7O0dBK0JHOzs7Ozs7Ozs7Ozs7Ozs7OztBQUVILCtFQUErRTtBQUMvRSxhQUFhO0FBQ2IsK0VBQStFO0FBRS9FLHVDQUFxRTtBQUE1RCxzR0FBQSxZQUFZLE9BQUE7QUFBRSxzR0FBQSxZQUFZLE9BQUE7QUFBRSxtR0FBQSxTQUFTLE9BQUE7QUFHOUMsK0VBQStFO0FBQy9FLFFBQVE7QUFDUiwrRUFBK0U7QUFFL0UsOENBQTRCO0FBRTVCLCtFQUErRTtBQUMvRSxjQUFjO0FBQ2QsK0VBQStFO0FBRS9FLGdEQUE4QjtBQUU5QiwrRUFBK0U7QUFDL0UsaUJBQWlCO0FBQ2pCLCtFQUErRTtBQUUvRSxrREFBZ0M7QUFFaEMsK0VBQStFO0FBQy9FLHlEQUF5RDtBQUN6RCwrRUFBK0U7QUFFL0UsaURBQStCIiwic291cmNlc0NvbnRlbnQiOlsiLyoqXG4gKiBTcG90cyBTREtcbiAqXG4gKiBUeXBlU2NyaXB0IFNESyBmb3IgdGhlIFNwb3RzIEFQSSB3aXRoIFRhblN0YWNrIFF1ZXJ5IGhvb2tzLlxuICpcbiAqIEBleGFtcGxlXG4gKiBgYGB0c3hcbiAqIGltcG9ydCB7IGNvbmZpZ3VyZVNESywgdXNlQ3VycmVudFVzZXIsIHVzZVNwb3RzLCB1c2VDcmVhdGVQb3N0IH0gZnJvbSAnQHNwb3RzL3Nkayc7XG4gKlxuICogLy8gQ29uZmlndXJlIFNESyB3aXRoIHlvdXIgQVBJIGJhc2UgVVJMIGFuZCB0b2tlbiBtYW5hZ2VtZW50XG4gKiBjb25maWd1cmVTREsoe1xuICogICBiYXNlVVJMOiAnaHR0cHM6Ly9zcG90cy1hcGktcHNpLnZlcmNlbC5hcHAnLFxuICogICBnZXRBY2Nlc3NUb2tlbjogKCkgPT4gbG9jYWxTdG9yYWdlLmdldEl0ZW0oJ2FjY2Vzc1Rva2VuJyksXG4gKiAgIHJlZnJlc2hBY2Nlc3NUb2tlbjogYXN5bmMgKCkgPT4ge1xuICogICAgIC8vIFlvdXIgdG9rZW4gcmVmcmVzaCBsb2dpY1xuICogICAgIHJldHVybiBuZXdBY2Nlc3NUb2tlbjtcbiAqICAgfSxcbiAqICAgb25VbmF1dGhvcml6ZWQ6ICgpID0+IHtcbiAqICAgICAvLyBIYW5kbGUgdW5hdXRob3JpemVkIGFjY2Vzc1xuICogICAgIHdpbmRvdy5sb2NhdGlvbi5ocmVmID0gJy9sb2dpbic7XG4gKiAgIH0sXG4gKiB9KTtcbiAqXG4gKiAvLyBVc2UgaG9va3MgaW4geW91ciBjb21wb25lbnRzXG4gKiBmdW5jdGlvbiBBcHAoKSB7XG4gKiAgIGNvbnN0IHsgZGF0YTogdXNlciB9ID0gdXNlQ3VycmVudFVzZXIoKTtcbiAqICAgY29uc3QgeyBkYXRhOiBzcG90cyB9ID0gdXNlU3BvdHMoKTtcbiAqICAgY29uc3QgeyBtdXRhdGU6IGNyZWF0ZVBvc3QgfSA9IHVzZUNyZWF0ZVBvc3QoKTtcbiAqICAgLy8gLi4uXG4gKiB9XG4gKiBgYGBcbiAqL1xuXG4vLyA9PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09XG4vLyBBUEkgQ0xJRU5UXG4vLyA9PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09XG5cbmV4cG9ydCB7IGNvbmZpZ3VyZVNESywgZ2V0QXBpQ2xpZW50LCBnZXRDb25maWcgfSBmcm9tICcuL2FwaS9jbGllbnQnO1xuZXhwb3J0IHR5cGUgeyBTREtDb25maWcgfSBmcm9tICcuL2FwaS9jbGllbnQnO1xuXG4vLyA9PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09XG4vLyBUWVBFU1xuLy8gPT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PVxuXG5leHBvcnQgKiBmcm9tICcuL2FwaS90eXBlcyc7XG5cbi8vID09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT1cbi8vIFFVRVJZIEhPT0tTXG4vLyA9PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09XG5cbmV4cG9ydCAqIGZyb20gJy4vYXBpL3F1ZXJpZXMnO1xuXG4vLyA9PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09XG4vLyBNVVRBVElPTiBIT09LU1xuLy8gPT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PVxuXG5leHBvcnQgKiBmcm9tICcuL2FwaS9tdXRhdGlvbnMnO1xuXG4vLyA9PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09XG4vLyBTRVJWSUNFUyAoUGxhaW4gYXN5bmMgZnVuY3Rpb25zIGZvciB0ZXN0aW5nL25vbi1SZWFjdClcbi8vID09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT09PT1cblxuZXhwb3J0ICogZnJvbSAnLi9hcGkvc2VydmljZXMnO1xuIl19
|
package/package.json
ADDED
|
@@ -0,0 +1,57 @@
|
|
|
1
|
+
{
|
|
2
|
+
"name": "@spotsdev/sdk",
|
|
3
|
+
"version": "1.0.0",
|
|
4
|
+
"description": "Shared TypeScript SDK for Spots API - TanStack Query hooks, API client, and utilities",
|
|
5
|
+
"main": "dist/index.js",
|
|
6
|
+
"types": "dist/index.d.ts",
|
|
7
|
+
"exports": {
|
|
8
|
+
".": {
|
|
9
|
+
"types": "./dist/index.d.ts",
|
|
10
|
+
"default": "./dist/index.js"
|
|
11
|
+
}
|
|
12
|
+
},
|
|
13
|
+
"files": [
|
|
14
|
+
"dist",
|
|
15
|
+
"src"
|
|
16
|
+
],
|
|
17
|
+
"scripts": {
|
|
18
|
+
"build": "tsc",
|
|
19
|
+
"build:watch": "tsc --watch",
|
|
20
|
+
"type-check": "tsc --noEmit",
|
|
21
|
+
"lint": "eslint src --ext .ts",
|
|
22
|
+
"generate": "prisma generate --schema=../spots-api/prisma/schema.prisma",
|
|
23
|
+
"prepublishOnly": "npm run build"
|
|
24
|
+
},
|
|
25
|
+
"keywords": [
|
|
26
|
+
"spots",
|
|
27
|
+
"api",
|
|
28
|
+
"sdk",
|
|
29
|
+
"tanstack-query",
|
|
30
|
+
"react-query",
|
|
31
|
+
"typescript"
|
|
32
|
+
],
|
|
33
|
+
"author": "SoulToSoul",
|
|
34
|
+
"license": "MIT",
|
|
35
|
+
"publishConfig": {
|
|
36
|
+
"access": "public"
|
|
37
|
+
},
|
|
38
|
+
"peerDependencies": {
|
|
39
|
+
"@tanstack/react-query": "^5.0.0",
|
|
40
|
+
"axios": "^1.6.0",
|
|
41
|
+
"react": ">=18.0.0",
|
|
42
|
+
"zod": "^3.0.0"
|
|
43
|
+
},
|
|
44
|
+
"dependencies": {
|
|
45
|
+
"@spotsdev/types": "^1.0.0"
|
|
46
|
+
},
|
|
47
|
+
"devDependencies": {
|
|
48
|
+
"@spotsdev/types": "^1.0.0",
|
|
49
|
+
"@tanstack/react-query": "^5.0.0",
|
|
50
|
+
"@types/node": "^20.0.0",
|
|
51
|
+
"@types/react": "^18.0.0",
|
|
52
|
+
"axios": "^1.6.0",
|
|
53
|
+
"react": "^18.0.0",
|
|
54
|
+
"typescript": "^5.9.3",
|
|
55
|
+
"zod": "^3.0.0"
|
|
56
|
+
}
|
|
57
|
+
}
|
|
@@ -0,0 +1,78 @@
|
|
|
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
|
+
export function getConfig(): SDKConfig {
|
|
26
|
+
if (!config) {
|
|
27
|
+
throw new Error('SDK not configured. Call configureSDK() first.');
|
|
28
|
+
}
|
|
29
|
+
return config;
|
|
30
|
+
}
|
|
31
|
+
|
|
32
|
+
function createApiClient(sdkConfig: SDKConfig): AxiosInstance {
|
|
33
|
+
const client = axios.create({
|
|
34
|
+
baseURL: sdkConfig.baseURL,
|
|
35
|
+
headers: {
|
|
36
|
+
'Content-Type': 'application/json',
|
|
37
|
+
},
|
|
38
|
+
});
|
|
39
|
+
|
|
40
|
+
// Request interceptor - add auth token
|
|
41
|
+
client.interceptors.request.use(
|
|
42
|
+
async (requestConfig: InternalAxiosRequestConfig) => {
|
|
43
|
+
const token = await sdkConfig.getAccessToken();
|
|
44
|
+
if (token) {
|
|
45
|
+
requestConfig.headers.Authorization = `Bearer ${token}`;
|
|
46
|
+
}
|
|
47
|
+
return requestConfig;
|
|
48
|
+
},
|
|
49
|
+
(error) => Promise.reject(error)
|
|
50
|
+
);
|
|
51
|
+
|
|
52
|
+
// Response interceptor - handle 401
|
|
53
|
+
client.interceptors.response.use(
|
|
54
|
+
(response) => response,
|
|
55
|
+
async (error: AxiosError) => {
|
|
56
|
+
if (error.response?.status === 401) {
|
|
57
|
+
if (sdkConfig.refreshAccessToken) {
|
|
58
|
+
try {
|
|
59
|
+
const newToken = await sdkConfig.refreshAccessToken();
|
|
60
|
+
if (newToken && error.config) {
|
|
61
|
+
error.config.headers.Authorization = `Bearer ${newToken}`;
|
|
62
|
+
return client.request(error.config);
|
|
63
|
+
}
|
|
64
|
+
} catch {
|
|
65
|
+
sdkConfig.onUnauthorized?.();
|
|
66
|
+
}
|
|
67
|
+
} else {
|
|
68
|
+
sdkConfig.onUnauthorized?.();
|
|
69
|
+
}
|
|
70
|
+
}
|
|
71
|
+
return Promise.reject(error);
|
|
72
|
+
}
|
|
73
|
+
);
|
|
74
|
+
|
|
75
|
+
return client;
|
|
76
|
+
}
|
|
77
|
+
|
|
78
|
+
export { apiClient };
|
|
@@ -0,0 +1,107 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Clubs Mutation Hooks
|
|
3
|
+
*
|
|
4
|
+
* TanStack Query hooks for club mutation operations.
|
|
5
|
+
*/
|
|
6
|
+
|
|
7
|
+
import { useMutation, useQueryClient, UseMutationOptions, UseMutationResult } from '@tanstack/react-query';
|
|
8
|
+
import { getApiClient } from '../client';
|
|
9
|
+
import { clubKeys } from '../queries/clubs';
|
|
10
|
+
import { userKeys } from '../queries/users';
|
|
11
|
+
import type { Club, ApiResponse } from '../types';
|
|
12
|
+
|
|
13
|
+
// ============================================================================
|
|
14
|
+
// MUTATION HOOKS
|
|
15
|
+
// ============================================================================
|
|
16
|
+
|
|
17
|
+
/**
|
|
18
|
+
* Create a new club
|
|
19
|
+
*
|
|
20
|
+
* @endpoint POST /api/v1/clubs
|
|
21
|
+
*/
|
|
22
|
+
export function useCreateClub(
|
|
23
|
+
options?: Omit<UseMutationOptions<Club, Error, { spotId: string; name: string; description?: string }>, 'mutationFn'>
|
|
24
|
+
): UseMutationResult<Club, Error, { spotId: string; name: string; description?: string }> {
|
|
25
|
+
const queryClient = useQueryClient();
|
|
26
|
+
|
|
27
|
+
return useMutation({
|
|
28
|
+
mutationFn: async (data): Promise<Club> => {
|
|
29
|
+
const client = getApiClient();
|
|
30
|
+
const response = await client.post<ApiResponse<Club>>('/api/v1/clubs', data);
|
|
31
|
+
return response.data.data;
|
|
32
|
+
},
|
|
33
|
+
onSuccess: (_, variables) => {
|
|
34
|
+
queryClient.invalidateQueries({ queryKey: clubKeys.bySpot(variables.spotId) });
|
|
35
|
+
},
|
|
36
|
+
...options,
|
|
37
|
+
});
|
|
38
|
+
}
|
|
39
|
+
|
|
40
|
+
/**
|
|
41
|
+
* Update a club
|
|
42
|
+
*
|
|
43
|
+
* @endpoint PUT /api/v1/clubs/{id}
|
|
44
|
+
*/
|
|
45
|
+
export function useUpdateClub(
|
|
46
|
+
options?: Omit<UseMutationOptions<Club, Error, { clubId: string; name?: string; description?: string }>, 'mutationFn'>
|
|
47
|
+
): UseMutationResult<Club, Error, { clubId: string; name?: string; description?: string }> {
|
|
48
|
+
const queryClient = useQueryClient();
|
|
49
|
+
|
|
50
|
+
return useMutation({
|
|
51
|
+
mutationFn: async ({ clubId, ...data }): Promise<Club> => {
|
|
52
|
+
const client = getApiClient();
|
|
53
|
+
const response = await client.put<ApiResponse<Club>>(`/api/v1/clubs/${clubId}`, data);
|
|
54
|
+
return response.data.data;
|
|
55
|
+
},
|
|
56
|
+
onSuccess: (data, variables) => {
|
|
57
|
+
queryClient.setQueryData(clubKeys.detail(variables.clubId), data);
|
|
58
|
+
},
|
|
59
|
+
...options,
|
|
60
|
+
});
|
|
61
|
+
}
|
|
62
|
+
|
|
63
|
+
/**
|
|
64
|
+
* Join a club
|
|
65
|
+
*
|
|
66
|
+
* @endpoint POST /api/v1/clubs/{id}/join
|
|
67
|
+
*/
|
|
68
|
+
export function useJoinClub(
|
|
69
|
+
options?: Omit<UseMutationOptions<void, Error, string>, 'mutationFn'>
|
|
70
|
+
): UseMutationResult<void, Error, string> {
|
|
71
|
+
const queryClient = useQueryClient();
|
|
72
|
+
|
|
73
|
+
return useMutation({
|
|
74
|
+
mutationFn: async (clubId: string): Promise<void> => {
|
|
75
|
+
const client = getApiClient();
|
|
76
|
+
await client.post(`/api/v1/clubs/${clubId}/join`);
|
|
77
|
+
},
|
|
78
|
+
onSuccess: (_, clubId) => {
|
|
79
|
+
queryClient.invalidateQueries({ queryKey: clubKeys.detail(clubId) });
|
|
80
|
+
queryClient.invalidateQueries({ queryKey: userKeys.clubs() });
|
|
81
|
+
},
|
|
82
|
+
...options,
|
|
83
|
+
});
|
|
84
|
+
}
|
|
85
|
+
|
|
86
|
+
/**
|
|
87
|
+
* Leave a club
|
|
88
|
+
*
|
|
89
|
+
* @endpoint POST /api/v1/clubs/{id}/leave
|
|
90
|
+
*/
|
|
91
|
+
export function useLeaveClub(
|
|
92
|
+
options?: Omit<UseMutationOptions<void, Error, string>, 'mutationFn'>
|
|
93
|
+
): UseMutationResult<void, Error, string> {
|
|
94
|
+
const queryClient = useQueryClient();
|
|
95
|
+
|
|
96
|
+
return useMutation({
|
|
97
|
+
mutationFn: async (clubId: string): Promise<void> => {
|
|
98
|
+
const client = getApiClient();
|
|
99
|
+
await client.post(`/api/v1/clubs/${clubId}/leave`);
|
|
100
|
+
},
|
|
101
|
+
onSuccess: (_, clubId) => {
|
|
102
|
+
queryClient.invalidateQueries({ queryKey: clubKeys.detail(clubId) });
|
|
103
|
+
queryClient.invalidateQueries({ queryKey: userKeys.clubs() });
|
|
104
|
+
},
|
|
105
|
+
...options,
|
|
106
|
+
});
|
|
107
|
+
}
|
|
@@ -0,0 +1,124 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Conversations Mutation Hooks
|
|
3
|
+
*
|
|
4
|
+
* TanStack Query hooks for conversation/messaging mutation operations.
|
|
5
|
+
*/
|
|
6
|
+
|
|
7
|
+
import { useMutation, useQueryClient, UseMutationOptions, UseMutationResult } from '@tanstack/react-query';
|
|
8
|
+
import { getApiClient } from '../client';
|
|
9
|
+
import { conversationKeys } from '../queries/conversations';
|
|
10
|
+
import type { Conversation, Message, CreateConversationRequest, SendMessageRequest, ApiResponse } from '../types';
|
|
11
|
+
|
|
12
|
+
// ============================================================================
|
|
13
|
+
// MUTATION HOOKS
|
|
14
|
+
// ============================================================================
|
|
15
|
+
|
|
16
|
+
/**
|
|
17
|
+
* Create a new conversation
|
|
18
|
+
*
|
|
19
|
+
* @endpoint POST /api/v1/conversations
|
|
20
|
+
*/
|
|
21
|
+
export function useCreateConversation(
|
|
22
|
+
options?: Omit<UseMutationOptions<Conversation, Error, CreateConversationRequest>, 'mutationFn'>
|
|
23
|
+
): UseMutationResult<Conversation, Error, CreateConversationRequest> {
|
|
24
|
+
const queryClient = useQueryClient();
|
|
25
|
+
|
|
26
|
+
return useMutation({
|
|
27
|
+
mutationFn: async (data: CreateConversationRequest): Promise<Conversation> => {
|
|
28
|
+
const client = getApiClient();
|
|
29
|
+
const response = await client.post<ApiResponse<Conversation>>('/api/v1/conversations', data);
|
|
30
|
+
return response.data.data;
|
|
31
|
+
},
|
|
32
|
+
onSuccess: () => {
|
|
33
|
+
queryClient.invalidateQueries({ queryKey: conversationKeys.lists() });
|
|
34
|
+
},
|
|
35
|
+
...options,
|
|
36
|
+
});
|
|
37
|
+
}
|
|
38
|
+
|
|
39
|
+
/**
|
|
40
|
+
* Create or get direct conversation with a user
|
|
41
|
+
*
|
|
42
|
+
* @endpoint POST /api/v1/conversations/direct
|
|
43
|
+
*/
|
|
44
|
+
export function useCreateDirectConversation(
|
|
45
|
+
options?: Omit<UseMutationOptions<Conversation, Error, { userId: string }>, 'mutationFn'>
|
|
46
|
+
): UseMutationResult<Conversation, Error, { userId: string }> {
|
|
47
|
+
const queryClient = useQueryClient();
|
|
48
|
+
|
|
49
|
+
return useMutation({
|
|
50
|
+
mutationFn: async (data: { userId: string }): Promise<Conversation> => {
|
|
51
|
+
const client = getApiClient();
|
|
52
|
+
const response = await client.post<ApiResponse<Conversation>>('/api/v1/conversations/direct', data);
|
|
53
|
+
return response.data.data;
|
|
54
|
+
},
|
|
55
|
+
onSuccess: () => {
|
|
56
|
+
queryClient.invalidateQueries({ queryKey: conversationKeys.lists() });
|
|
57
|
+
},
|
|
58
|
+
...options,
|
|
59
|
+
});
|
|
60
|
+
}
|
|
61
|
+
|
|
62
|
+
/**
|
|
63
|
+
* Send a message in a conversation
|
|
64
|
+
*
|
|
65
|
+
* @endpoint POST /api/v1/conversations/{id}/messages
|
|
66
|
+
*/
|
|
67
|
+
export function useSendMessage(
|
|
68
|
+
options?: Omit<UseMutationOptions<Message, Error, { conversationId: string } & SendMessageRequest>, 'mutationFn'>
|
|
69
|
+
): UseMutationResult<Message, Error, { conversationId: string } & SendMessageRequest> {
|
|
70
|
+
const queryClient = useQueryClient();
|
|
71
|
+
|
|
72
|
+
return useMutation({
|
|
73
|
+
mutationFn: async ({ conversationId, ...data }): Promise<Message> => {
|
|
74
|
+
const client = getApiClient();
|
|
75
|
+
const response = await client.post<ApiResponse<Message>>(`/api/v1/conversations/${conversationId}/messages`, data);
|
|
76
|
+
return response.data.data;
|
|
77
|
+
},
|
|
78
|
+
onSuccess: (_, variables) => {
|
|
79
|
+
queryClient.invalidateQueries({ queryKey: conversationKeys.messages(variables.conversationId) });
|
|
80
|
+
queryClient.invalidateQueries({ queryKey: conversationKeys.lists() });
|
|
81
|
+
},
|
|
82
|
+
...options,
|
|
83
|
+
});
|
|
84
|
+
}
|
|
85
|
+
|
|
86
|
+
/**
|
|
87
|
+
* Mark conversation as read
|
|
88
|
+
*
|
|
89
|
+
* @endpoint PUT /api/v1/conversations/{id}/read
|
|
90
|
+
*/
|
|
91
|
+
export function useMarkConversationAsRead(
|
|
92
|
+
options?: Omit<UseMutationOptions<void, Error, string>, 'mutationFn'>
|
|
93
|
+
): UseMutationResult<void, Error, string> {
|
|
94
|
+
const queryClient = useQueryClient();
|
|
95
|
+
|
|
96
|
+
return useMutation({
|
|
97
|
+
mutationFn: async (conversationId: string): Promise<void> => {
|
|
98
|
+
const client = getApiClient();
|
|
99
|
+
await client.put(`/api/v1/conversations/${conversationId}/read`);
|
|
100
|
+
},
|
|
101
|
+
onSuccess: (_, conversationId) => {
|
|
102
|
+
queryClient.invalidateQueries({ queryKey: conversationKeys.detail(conversationId) });
|
|
103
|
+
queryClient.invalidateQueries({ queryKey: conversationKeys.lists() });
|
|
104
|
+
},
|
|
105
|
+
...options,
|
|
106
|
+
});
|
|
107
|
+
}
|
|
108
|
+
|
|
109
|
+
/**
|
|
110
|
+
* Send typing indicator
|
|
111
|
+
*
|
|
112
|
+
* @endpoint POST /api/v1/conversations/{id}/typing
|
|
113
|
+
*/
|
|
114
|
+
export function useSendTypingIndicator(
|
|
115
|
+
options?: Omit<UseMutationOptions<void, Error, string>, 'mutationFn'>
|
|
116
|
+
): UseMutationResult<void, Error, string> {
|
|
117
|
+
return useMutation({
|
|
118
|
+
mutationFn: async (conversationId: string): Promise<void> => {
|
|
119
|
+
const client = getApiClient();
|
|
120
|
+
await client.post(`/api/v1/conversations/${conversationId}/typing`);
|
|
121
|
+
},
|
|
122
|
+
...options,
|
|
123
|
+
});
|
|
124
|
+
}
|
|
@@ -0,0 +1,29 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Spots SDK Mutation Hooks Index
|
|
3
|
+
*
|
|
4
|
+
* Re-exports all mutation hooks.
|
|
5
|
+
*/
|
|
6
|
+
|
|
7
|
+
// Users
|
|
8
|
+
export * from './users';
|
|
9
|
+
|
|
10
|
+
// Posts
|
|
11
|
+
export * from './posts';
|
|
12
|
+
|
|
13
|
+
// Spots
|
|
14
|
+
export * from './spots';
|
|
15
|
+
|
|
16
|
+
// Conversations
|
|
17
|
+
export * from './conversations';
|
|
18
|
+
|
|
19
|
+
// Clubs
|
|
20
|
+
export * from './clubs';
|
|
21
|
+
|
|
22
|
+
// Notifications
|
|
23
|
+
export * from './notifications';
|
|
24
|
+
|
|
25
|
+
// Products (marketplace)
|
|
26
|
+
export * from './products';
|
|
27
|
+
|
|
28
|
+
// Orders (marketplace)
|
|
29
|
+
export * from './orders';
|