@turtleclub/hooks 0.4.0-beta.5 → 0.4.0-beta.7

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/index.cjs CHANGED
@@ -20,6 +20,7 @@ var __toCommonJS = (mod) => __copyProps(__defProp({}, "__esModule", { value: tru
20
20
  // src/index.ts
21
21
  var index_exports = {};
22
22
  __export(index_exports, {
23
+ AuthProvider: () => AuthProvider,
23
24
  approveStep: () => approveStep,
24
25
  asset: () => asset,
25
26
  assetData: () => assetData,
@@ -70,6 +71,7 @@ __export(index_exports, {
70
71
  stepTx: () => stepTx,
71
72
  swapSubstep: () => swapSubstep,
72
73
  tokenSchema: () => tokenSchema,
74
+ useAuthToken: () => useAuthToken,
73
75
  useCheckMembership: () => useCheckMembership,
74
76
  useConfig: () => useConfig,
75
77
  useCreateMembership: () => useCreateMembership,
@@ -101,6 +103,7 @@ __export(index_exports, {
101
103
  useSignup: () => useSignup,
102
104
  useTokenBalance: () => useTokenBalance,
103
105
  useUpdateProduct: () => useUpdateProduct,
106
+ useUploadProductLogo: () => useUploadProductLogo,
104
107
  useWidgetOpportunities: () => useWidgetOpportunities,
105
108
  vaultConfigSchema: () => vaultConfigSchema,
106
109
  walletBalanceSchema: () => walletBalanceSchema,
@@ -1071,110 +1074,219 @@ var earnDepositsQueries = (0, import_query_key_factory5.createQueryKeys)("earnDe
1071
1074
  // src/v2/products/queries.ts
1072
1075
  var import_query_key_factory6 = require("@lukemorales/query-key-factory");
1073
1076
 
1077
+ // src/v2/lib/authenticated-api-client.ts
1078
+ async function authenticatedApiClient(endpoint, options, token = null) {
1079
+ return apiClient(endpoint, {
1080
+ ...options,
1081
+ headers: {
1082
+ ...token && { Authorization: `Bearer ${token}` },
1083
+ ...options?.headers
1084
+ }
1085
+ });
1086
+ }
1087
+
1074
1088
  // src/v2/products/schema.ts
1075
1089
  var import_zod7 = require("zod");
1076
- var productsResponseSchema = import_zod7.z.object({
1077
- products: import_zod7.z.array(productSchema),
1078
- total: import_zod7.z.number().optional()
1090
+ var ProductTypeSchema = import_zod7.z.enum(["deal", "campaign"]);
1091
+ var ProductStatusSchema = import_zod7.z.enum(["active", "paused", "ended"]);
1092
+ var TurtleOrganizationSchema = import_zod7.z.object({
1093
+ id: import_zod7.z.string().uuid(),
1094
+ name: import_zod7.z.string(),
1095
+ iconUrl: import_zod7.z.string(),
1096
+ landingUrl: import_zod7.z.string()
1079
1097
  });
1080
- var productCreateInputSchema = import_zod7.z.object({
1098
+ var ProductSchema = import_zod7.z.object({
1099
+ id: import_zod7.z.string().uuid(),
1081
1100
  name: import_zod7.z.string(),
1082
- title: import_zod7.z.string().optional().nullable(),
1083
- subtitle: import_zod7.z.string().optional().nullable(),
1084
- description: import_zod7.z.string().optional().nullable(),
1085
- logoUrl: import_zod7.z.string().optional().nullable(),
1086
- productUrl: import_zod7.z.string().optional().nullable(),
1101
+ title: import_zod7.z.string(),
1102
+ subtitle: import_zod7.z.string(),
1103
+ description: import_zod7.z.string(),
1104
+ logoUrl: import_zod7.z.string(),
1105
+ productUrl: import_zod7.z.string(),
1087
1106
  startedAt: import_zod7.z.string().optional().nullable(),
1088
- status: import_zod7.z.string().optional().nullable(),
1089
- productType: import_zod7.z.string().optional().nullable(),
1090
- // Relations
1107
+ endedAt: import_zod7.z.string().optional().nullable(),
1108
+ status: ProductStatusSchema,
1109
+ productType: ProductTypeSchema,
1110
+ organization: TurtleOrganizationSchema.nullable(),
1111
+ createdAt: import_zod7.z.string()
1112
+ });
1113
+ var CreateProductInputSchema = import_zod7.z.object({
1114
+ product: ProductSchema.omit({
1115
+ id: true,
1116
+ createdAt: true,
1117
+ organization: true
1118
+ }),
1091
1119
  organizationId: import_zod7.z.string().uuid()
1092
1120
  });
1093
- var productUpdateInputSchema = productCreateInputSchema.extend({
1121
+ var UpdateProductInputSchema = import_zod7.z.object({
1122
+ product: ProductSchema.partial().omit({
1123
+ organization: true
1124
+ })
1125
+ // organizationId: z.string().uuid(),
1126
+ });
1127
+ var ProductsResponseSchema = import_zod7.z.object({
1128
+ products: import_zod7.z.array(ProductSchema),
1129
+ total: import_zod7.z.number().optional()
1130
+ });
1131
+ var ProductResponseSchema = import_zod7.z.object({
1132
+ product: ProductSchema
1133
+ });
1134
+ var CreateProductResponseSchema = import_zod7.z.object({
1094
1135
  id: import_zod7.z.string().uuid()
1095
1136
  });
1137
+ var UpdateProductResponseSchema = import_zod7.z.object({
1138
+ success: import_zod7.z.boolean()
1139
+ });
1140
+ var fileSchema = import_zod7.z.any().refine((value) => {
1141
+ if (!value) return false;
1142
+ if (!(value instanceof File)) return false;
1143
+ if (value.size > 10 * 1024 * 1024) return false;
1144
+ return true;
1145
+ }, "Invalid file");
1146
+ var UploadProductLogoRequestSchema = import_zod7.z.object({
1147
+ // Form data - file upload (required)
1148
+ file: fileSchema,
1149
+ // Form data - optional filename override
1150
+ filename: import_zod7.z.string().optional()
1151
+ });
1152
+ var UploadProductLogoResponseSchema = import_zod7.z.object({
1153
+ url: import_zod7.z.string().url(),
1154
+ error: import_zod7.z.string().optional()
1155
+ });
1156
+ var ProductFiltersSchema = import_zod7.z.object({
1157
+ organizationId: import_zod7.z.string().uuid().optional()
1158
+ });
1096
1159
 
1097
1160
  // src/v2/products/api.ts
1098
- async function getProducts(options) {
1161
+ async function getProducts(filters, token) {
1099
1162
  const params = new URLSearchParams();
1163
+ if (filters?.organizationId) params.append("organizationId", filters.organizationId);
1100
1164
  const queryString = params.toString();
1101
1165
  const endpoint = `/admin/products${queryString ? `?${queryString}` : ""}`;
1102
- const data = await apiClient(endpoint, {
1103
- method: "GET",
1104
- debug: options?.debug
1105
- });
1106
- const result = productsResponseSchema.safeParse(data);
1166
+ console.log("endpoint", endpoint, filters);
1167
+ const data = await authenticatedApiClient(
1168
+ endpoint,
1169
+ {
1170
+ method: "GET"
1171
+ },
1172
+ token
1173
+ );
1174
+ const result = ProductsResponseSchema.safeParse(data);
1107
1175
  if (result.success === false) {
1108
1176
  console.log("[ZOD ERROR]", result.error);
1109
1177
  throw new Error(`Failed to parse products: ${result.error.message}`);
1110
1178
  }
1111
1179
  return result.data;
1112
1180
  }
1113
- async function createProduct(input, options) {
1181
+ async function getProduct(id, token) {
1182
+ const endpoint = `/admin/products/${id}`;
1183
+ const data = await authenticatedApiClient(
1184
+ endpoint,
1185
+ {
1186
+ method: "GET"
1187
+ },
1188
+ token
1189
+ );
1190
+ console.log(data);
1191
+ const result = ProductResponseSchema.safeParse(data);
1192
+ if (result.success === false) {
1193
+ console.log("[ZOD ERROR]", result.error);
1194
+ throw new Error(`Failed to parse product: ${result.error.message}`);
1195
+ }
1196
+ return result.data;
1197
+ }
1198
+ async function createProduct(input, token) {
1114
1199
  const endpoint = `/admin/products`;
1115
- const data = await apiClient(endpoint, {
1116
- method: "POST",
1117
- body: JSON.stringify(input),
1118
- headers: {
1119
- "Content-Type": "application/json"
1200
+ const data = await authenticatedApiClient(
1201
+ endpoint,
1202
+ {
1203
+ method: "POST",
1204
+ body: JSON.stringify(input),
1205
+ headers: {
1206
+ "Content-Type": "application/json"
1207
+ }
1120
1208
  },
1121
- debug: options?.debug
1122
- });
1123
- const result = productSchema.safeParse(data);
1209
+ token
1210
+ );
1211
+ const result = CreateProductResponseSchema.safeParse(data);
1124
1212
  if (result.success === false) {
1125
1213
  console.log("[ZOD ERROR]", result.error);
1126
1214
  throw new Error(`Failed to create product: ${result.error.message}`);
1127
1215
  }
1128
1216
  return result.data;
1129
1217
  }
1130
- async function updateProduct(input, options) {
1131
- const endpoint = `/admin/products/${input.id}`;
1132
- const data = await apiClient(endpoint, {
1133
- method: "PUT",
1134
- body: JSON.stringify(input),
1135
- headers: {
1136
- "Content-Type": "application/json"
1218
+ async function updateProduct(input, token) {
1219
+ const endpoint = `/admin/products/${input.product.id}`;
1220
+ const data = await authenticatedApiClient(
1221
+ endpoint,
1222
+ {
1223
+ method: "PUT",
1224
+ body: JSON.stringify(input),
1225
+ headers: {
1226
+ "Content-Type": "application/json"
1227
+ }
1137
1228
  },
1138
- debug: options?.debug
1139
- });
1140
- const result = productSchema.safeParse(data);
1229
+ token
1230
+ );
1231
+ const result = UpdateProductResponseSchema.safeParse(data);
1141
1232
  if (result.success === false) {
1142
1233
  console.log("[ZOD ERROR]", result.error);
1143
1234
  throw new Error(`Failed to update product: ${result.error.message}`);
1144
1235
  }
1145
1236
  return result.data;
1146
1237
  }
1147
- async function deleteProduct(id, options) {
1238
+ async function deleteProduct(id, token) {
1148
1239
  const endpoint = `/admin/products/${id}`;
1149
- const data = await apiClient(endpoint, {
1150
- method: "DELETE",
1151
- headers: {
1152
- "Content-Type": "application/json"
1240
+ const data = await authenticatedApiClient(
1241
+ endpoint,
1242
+ {
1243
+ method: "DELETE",
1244
+ headers: {
1245
+ "Content-Type": "application/json"
1246
+ }
1153
1247
  },
1154
- debug: options?.debug
1155
- });
1156
- const result = productSchema.safeParse(data);
1248
+ token
1249
+ );
1250
+ const result = ProductResponseSchema.safeParse(data);
1157
1251
  if (result.success === false) {
1158
1252
  console.log("[ZOD ERROR]", result.error);
1159
1253
  throw new Error(`Failed to delete product: ${result.error.message}`);
1160
1254
  }
1161
1255
  }
1256
+ async function uploadProductLogo({ file, filename }, token) {
1257
+ const endpoint = `/admin/products/upload-logo`;
1258
+ const formData = new FormData();
1259
+ formData.append("file", file, filename || file.name);
1260
+ const data = await authenticatedApiClient(
1261
+ endpoint,
1262
+ {
1263
+ method: "POST",
1264
+ body: formData
1265
+ },
1266
+ token
1267
+ );
1268
+ const result = UploadProductLogoResponseSchema.safeParse(data);
1269
+ if (result.success === false) {
1270
+ console.log("[ZOD ERROR]", result.error);
1271
+ throw new Error(`Failed to upload product logo: ${result.error.message}`);
1272
+ }
1273
+ return result.data;
1274
+ }
1162
1275
 
1163
1276
  // src/v2/products/queries.ts
1164
1277
  var productsQueries = (0, import_query_key_factory6.createQueryKeys)("products", {
1165
1278
  // Get all products (no filters)
1166
- all: {
1167
- queryKey: null,
1168
- queryFn: () => getProducts()
1169
- },
1170
- // Get single product by ID
1171
- byId: (id) => ({
1279
+ all: (token) => ({
1280
+ queryKey: ["all"],
1281
+ queryFn: () => getProducts(void 0, token)
1282
+ }),
1283
+ list: (filters, token) => ({
1284
+ queryKey: [{ filters }],
1285
+ queryFn: () => getProducts(filters, token)
1286
+ }),
1287
+ byId: (id, token) => ({
1172
1288
  queryKey: [id],
1173
- // Replace by true query then
1174
- queryFn: async () => {
1175
- const products = await getProducts();
1176
- return products.products.find((product) => product.id === id);
1177
- }
1289
+ queryFn: () => getProduct(id, token)
1178
1290
  })
1179
1291
  });
1180
1292
 
@@ -1413,38 +1525,84 @@ function useOpportunity({ id, ...options }) {
1413
1525
 
1414
1526
  // src/v2/products/hooks.ts
1415
1527
  var import_react_query23 = require("@tanstack/react-query");
1416
- function useProducts(options) {
1417
- return (0, import_react_query23.useQuery)({ ...productsQueries.all, ...queryDefaults });
1528
+
1529
+ // src/v2/lib/auth-provider.tsx
1530
+ var import_react2 = require("react");
1531
+ var import_jsx_runtime = require("react/jsx-runtime");
1532
+ var AuthContext = (0, import_react2.createContext)(null);
1533
+ function AuthProvider({ getToken, children }) {
1534
+ return /* @__PURE__ */ (0, import_jsx_runtime.jsx)(AuthContext.Provider, { value: { getToken }, children });
1418
1535
  }
1419
- function useProduct({ id, ...options }) {
1420
- return (0, import_react_query23.useQuery)({ ...productsQueries.byId(id), ...queryDefaults });
1536
+ function useAuthToken() {
1537
+ const context = (0, import_react2.useContext)(AuthContext);
1538
+ if (!context) {
1539
+ throw new Error("useAuthToken must be used within AuthProvider");
1540
+ }
1541
+ return context;
1421
1542
  }
1422
- function useCreateProduct({ ...options }) {
1423
- return (0, import_react_query23.useMutation)({ mutationFn: createProduct });
1543
+
1544
+ // src/v2/products/hooks.ts
1545
+ function useProducts({ filters, enabled = true }) {
1546
+ const { getToken } = useAuthToken();
1547
+ return (0, import_react_query23.useQuery)({
1548
+ ...productsQueries.list(filters, getToken()),
1549
+ ...queryDefaults,
1550
+ enabled
1551
+ });
1424
1552
  }
1425
- function useUpdateProduct({ ...options }) {
1426
- return (0, import_react_query23.useMutation)({ mutationFn: updateProduct });
1553
+ function useProduct({ id, enabled = true }) {
1554
+ const { getToken } = useAuthToken();
1555
+ return (0, import_react_query23.useQuery)({
1556
+ ...productsQueries.byId(id, getToken()),
1557
+ ...queryDefaults,
1558
+ enabled
1559
+ });
1427
1560
  }
1428
- function useDeleteProduct({ ...options }) {
1429
- return (0, import_react_query23.useMutation)({ mutationFn: deleteProduct });
1561
+ function useCreateProduct(options) {
1562
+ const { getToken } = useAuthToken();
1563
+ return (0, import_react_query23.useMutation)({
1564
+ mutationFn: (input) => createProduct(input, getToken()),
1565
+ ...options
1566
+ });
1567
+ }
1568
+ function useUpdateProduct(options) {
1569
+ const { getToken } = useAuthToken();
1570
+ return (0, import_react_query23.useMutation)({
1571
+ mutationFn: (input) => updateProduct(input, getToken()),
1572
+ ...options
1573
+ });
1574
+ }
1575
+ function useDeleteProduct(options) {
1576
+ const { getToken } = useAuthToken();
1577
+ return (0, import_react_query23.useMutation)({
1578
+ mutationFn: (id) => deleteProduct(id, getToken()),
1579
+ ...options
1580
+ });
1581
+ }
1582
+ function useUploadProductLogo(options) {
1583
+ const { getToken } = useAuthToken();
1584
+ return (0, import_react_query23.useMutation)({
1585
+ mutationFn: (request) => uploadProductLogo(request, getToken()),
1586
+ ...options
1587
+ });
1430
1588
  }
1431
1589
 
1432
1590
  // src/v2/balance/useTokenBalance.ts
1433
- var import_react2 = require("react");
1591
+ var import_react3 = require("react");
1434
1592
  var import_viem = require("viem");
1435
1593
  var import_utils2 = require("@turtleclub/utils");
1436
1594
  function useTokenBalance({ token, amount, setAmount }) {
1437
- const usdValue = (0, import_react2.useMemo)(() => (0, import_utils2.calculateUsdValue)(amount, token?.price), [amount, token?.price]);
1438
- const hasInsufficientBalance = (0, import_react2.useMemo)(
1595
+ const usdValue = (0, import_react3.useMemo)(() => (0, import_utils2.calculateUsdValue)(amount, token?.price), [amount, token?.price]);
1596
+ const hasInsufficientBalance = (0, import_react3.useMemo)(
1439
1597
  () => (0, import_utils2.checkInsufficientBalance)(token, amount),
1440
1598
  [token, amount]
1441
1599
  );
1442
- const handleMaxClick = (0, import_react2.useCallback)(() => {
1600
+ const handleMaxClick = (0, import_react3.useCallback)(() => {
1443
1601
  if (!token) return;
1444
1602
  const maxAmount = (0, import_utils2.calculateMaxAmount)(token.balance, token.decimals);
1445
1603
  setAmount(maxAmount);
1446
1604
  }, [token, setAmount]);
1447
- const amountBigInt = (0, import_react2.useMemo)(() => {
1605
+ const amountBigInt = (0, import_react3.useMemo)(() => {
1448
1606
  if (!token || !amount) return void 0;
1449
1607
  try {
1450
1608
  return (0, import_viem.parseUnits)(amount, token.decimals);
@@ -1492,6 +1650,7 @@ var queries = (0, import_query_key_factory9.mergeQueryKeys)(
1492
1650
  );
1493
1651
  // Annotate the CommonJS export names for ESM import in node:
1494
1652
  0 && (module.exports = {
1653
+ AuthProvider,
1495
1654
  approveStep,
1496
1655
  asset,
1497
1656
  assetData,
@@ -1542,6 +1701,7 @@ var queries = (0, import_query_key_factory9.mergeQueryKeys)(
1542
1701
  stepTx,
1543
1702
  swapSubstep,
1544
1703
  tokenSchema,
1704
+ useAuthToken,
1545
1705
  useCheckMembership,
1546
1706
  useConfig,
1547
1707
  useCreateMembership,
@@ -1573,6 +1733,7 @@ var queries = (0, import_query_key_factory9.mergeQueryKeys)(
1573
1733
  useSignup,
1574
1734
  useTokenBalance,
1575
1735
  useUpdateProduct,
1736
+ useUploadProductLogo,
1576
1737
  useWidgetOpportunities,
1577
1738
  vaultConfigSchema,
1578
1739
  walletBalanceSchema,