@htlkg/data 0.0.22 → 0.0.24
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/hooks/index.d.ts +100 -1
- package/dist/hooks/index.js +131 -7
- package/dist/hooks/index.js.map +1 -1
- package/dist/index.d.ts +1 -1
- package/dist/index.js +131 -7
- package/dist/index.js.map +1 -1
- package/package.json +1 -1
- package/src/hooks/contacts/index.ts +2 -0
- package/src/hooks/contacts/useContacts.ts +176 -0
- package/src/hooks/contacts/usePaginatedContacts.ts +261 -0
- package/src/hooks/index.ts +6 -1
package/dist/hooks/index.d.ts
CHANGED
|
@@ -1038,4 +1038,103 @@ interface UseContactsReturn {
|
|
|
1038
1038
|
*/
|
|
1039
1039
|
declare function useContacts(options?: UseContactsOptions): UseContactsReturn;
|
|
1040
1040
|
|
|
1041
|
-
|
|
1041
|
+
/**
|
|
1042
|
+
* Paginated Contacts Hooks
|
|
1043
|
+
*
|
|
1044
|
+
* Vue composables for fetching contacts with server-side pagination.
|
|
1045
|
+
* Provides separate hooks for active and deleted contacts to enable
|
|
1046
|
+
* efficient tab-based filtering in large datasets.
|
|
1047
|
+
*/
|
|
1048
|
+
|
|
1049
|
+
/** Extended Contact type with computed fields */
|
|
1050
|
+
type ContactWithRelations = Contact & {
|
|
1051
|
+
brandName?: string;
|
|
1052
|
+
name?: string;
|
|
1053
|
+
deletedAt?: string;
|
|
1054
|
+
deletedBy?: string;
|
|
1055
|
+
};
|
|
1056
|
+
interface UsePaginatedContactsOptions extends PaginatedHookOptions {
|
|
1057
|
+
/** Filter by brand ID */
|
|
1058
|
+
brandId?: string;
|
|
1059
|
+
/** Search query (searches email, firstName, lastName) */
|
|
1060
|
+
search?: string;
|
|
1061
|
+
/** Filter by GDPR consent */
|
|
1062
|
+
gdprConsent?: boolean;
|
|
1063
|
+
/** Filter by marketing opt-in */
|
|
1064
|
+
marketingOptIn?: boolean;
|
|
1065
|
+
/** Filter by tags (contact must have at least one of these tags) */
|
|
1066
|
+
tags?: string[];
|
|
1067
|
+
}
|
|
1068
|
+
interface UsePaginatedContactsReturn {
|
|
1069
|
+
/** Reactive array of contacts */
|
|
1070
|
+
contacts: Ref<ContactWithRelations[]>;
|
|
1071
|
+
/** Loading state (true during any fetch) */
|
|
1072
|
+
loading: Ref<boolean>;
|
|
1073
|
+
/** Loading state for initial fetch */
|
|
1074
|
+
initialLoading: Ref<boolean>;
|
|
1075
|
+
/** Loading state for loadMore */
|
|
1076
|
+
loadingMore: Ref<boolean>;
|
|
1077
|
+
/** Error state */
|
|
1078
|
+
error: Ref<Error | null>;
|
|
1079
|
+
/** Pagination state */
|
|
1080
|
+
pagination: Ref<PaginationState>;
|
|
1081
|
+
/** Whether there are more items to load */
|
|
1082
|
+
hasMore: ComputedRef<boolean>;
|
|
1083
|
+
/** Load next page of data */
|
|
1084
|
+
loadMore: () => Promise<void>;
|
|
1085
|
+
/** Refetch data (resets to first page) */
|
|
1086
|
+
refetch: () => Promise<void>;
|
|
1087
|
+
/** Reset data and pagination state */
|
|
1088
|
+
reset: () => void;
|
|
1089
|
+
/** Update search filter and refetch from server (searches ALL data) */
|
|
1090
|
+
setSearchFilter: (filter: any) => Promise<void>;
|
|
1091
|
+
/** Current search filter */
|
|
1092
|
+
searchFilter: Ref<any>;
|
|
1093
|
+
}
|
|
1094
|
+
/**
|
|
1095
|
+
* Composable for fetching active (non-deleted) contacts with pagination
|
|
1096
|
+
*
|
|
1097
|
+
* @example
|
|
1098
|
+
* ```typescript
|
|
1099
|
+
* import { useActiveContacts } from '@htlkg/data/hooks';
|
|
1100
|
+
*
|
|
1101
|
+
* const { contacts, loading, hasMore, loadMore, refetch, setSearchFilter } = useActiveContacts({
|
|
1102
|
+
* pageSize: 25,
|
|
1103
|
+
* });
|
|
1104
|
+
*
|
|
1105
|
+
* // Load more when user scrolls or clicks "Load More"
|
|
1106
|
+
* async function onLoadMore() {
|
|
1107
|
+
* await loadMore();
|
|
1108
|
+
* }
|
|
1109
|
+
*
|
|
1110
|
+
* // Server-side search (searches ALL contacts in database)
|
|
1111
|
+
* async function onSearch(filter: any) {
|
|
1112
|
+
* await setSearchFilter(filter);
|
|
1113
|
+
* }
|
|
1114
|
+
* ```
|
|
1115
|
+
*
|
|
1116
|
+
* @example With filters
|
|
1117
|
+
* ```typescript
|
|
1118
|
+
* const { contacts, loading } = useActiveContacts({
|
|
1119
|
+
* brandId: 'brand-123',
|
|
1120
|
+
* gdprConsent: true,
|
|
1121
|
+
* pageSize: 50
|
|
1122
|
+
* });
|
|
1123
|
+
* ```
|
|
1124
|
+
*/
|
|
1125
|
+
declare function useActiveContacts(options?: UsePaginatedContactsOptions): UsePaginatedContactsReturn;
|
|
1126
|
+
/**
|
|
1127
|
+
* Composable for fetching deleted contacts with pagination
|
|
1128
|
+
*
|
|
1129
|
+
* @example
|
|
1130
|
+
* ```typescript
|
|
1131
|
+
* import { useDeletedContacts } from '@htlkg/data/hooks';
|
|
1132
|
+
*
|
|
1133
|
+
* const { contacts, loading, hasMore, loadMore, refetch } = useDeletedContacts({
|
|
1134
|
+
* pageSize: 25,
|
|
1135
|
+
* });
|
|
1136
|
+
* ```
|
|
1137
|
+
*/
|
|
1138
|
+
declare function useDeletedContacts(options?: UsePaginatedContactsOptions): UsePaginatedContactsReturn;
|
|
1139
|
+
|
|
1140
|
+
export { ACTIVE_FILTER, type AccountWithBrands, type BaseHookOptions, type BrandWithCounts, type ContactWithRelations, type CreateDataHookOptions, type CreatePaginatedDataHookOptions, DELETED_FILTER, type DataHookReturn, type InferHookReturn, type InferPaginatedHookReturn, type AccountWithBrands as PaginatedAccountWithBrands, type PaginatedDataHookReturn, type PaginatedHookOptions, type PaginationState, type ReservationWithRelations, type UseAccountsOptions, type UseAccountsReturn, type UseBrandsOptions, type UseBrandsReturn, type UseContactsOptions, type UseContactsReturn, type UsePaginatedAccountsOptions, type UsePaginatedAccountsReturn, type UsePaginatedBrandsOptions, type UsePaginatedBrandsReturn, type UsePaginatedContactsOptions, type UsePaginatedContactsReturn, type UsePaginatedReservationsOptions, type UsePaginatedReservationsReturn, type UsePaginatedUsersOptions, type UsePaginatedUsersReturn, type UseProductInstancesOptions, type UseProductInstancesReturn, type UseProductsOptions, type UseProductsReturn, type UseReservationsOptions, type UseReservationsReturn, type UseUsersOptions, type UseUsersReturn, type UserWithRelations, createDataHook, createPaginatedDataHook, resetClientInstance, useAccounts, useActiveAccounts, useActiveBrands, useActiveContacts, useActiveReservations, useActiveUsers, useBrands, useContacts, useDeletedAccounts, useDeletedBrands, useDeletedContacts, useDeletedReservations, useDeletedUsers, useProductInstances, useProducts, useReservations, useUsers };
|
package/dist/hooks/index.js
CHANGED
|
@@ -55,7 +55,7 @@ function createDataHook(config) {
|
|
|
55
55
|
defaultLimit,
|
|
56
56
|
selectionSet,
|
|
57
57
|
transform,
|
|
58
|
-
buildFilter:
|
|
58
|
+
buildFilter: buildFilter11,
|
|
59
59
|
computedProperties,
|
|
60
60
|
dataPropertyName = "data"
|
|
61
61
|
} = config;
|
|
@@ -65,8 +65,8 @@ function createDataHook(config) {
|
|
|
65
65
|
const loading = ref(false);
|
|
66
66
|
const error = ref(null);
|
|
67
67
|
const getFilter = () => {
|
|
68
|
-
if (
|
|
69
|
-
return
|
|
68
|
+
if (buildFilter11) {
|
|
69
|
+
return buildFilter11(options);
|
|
70
70
|
}
|
|
71
71
|
return baseFilter && Object.keys(baseFilter).length > 0 ? baseFilter : void 0;
|
|
72
72
|
};
|
|
@@ -140,7 +140,7 @@ function createPaginatedDataHook(config) {
|
|
|
140
140
|
defaultPageSize = 25,
|
|
141
141
|
selectionSet,
|
|
142
142
|
transform,
|
|
143
|
-
buildFilter:
|
|
143
|
+
buildFilter: buildFilter11,
|
|
144
144
|
dataPropertyName = "data",
|
|
145
145
|
baseFilter
|
|
146
146
|
} = config;
|
|
@@ -163,8 +163,8 @@ function createPaginatedDataHook(config) {
|
|
|
163
163
|
if (baseFilter) {
|
|
164
164
|
filters.push(baseFilter);
|
|
165
165
|
}
|
|
166
|
-
if (
|
|
167
|
-
const customFilter =
|
|
166
|
+
if (buildFilter11) {
|
|
167
|
+
const customFilter = buildFilter11(options);
|
|
168
168
|
if (customFilter) {
|
|
169
169
|
filters.push(customFilter);
|
|
170
170
|
}
|
|
@@ -1113,7 +1113,7 @@ function useProductInstances(options = {}) {
|
|
|
1113
1113
|
};
|
|
1114
1114
|
}
|
|
1115
1115
|
|
|
1116
|
-
// src/hooks/useContacts.ts
|
|
1116
|
+
// src/hooks/contacts/useContacts.ts
|
|
1117
1117
|
function buildFilter9(options) {
|
|
1118
1118
|
const conditions = [];
|
|
1119
1119
|
if (options.brandId) {
|
|
@@ -1171,6 +1171,128 @@ function useContacts(options = {}) {
|
|
|
1171
1171
|
refetch: result.refetch
|
|
1172
1172
|
};
|
|
1173
1173
|
}
|
|
1174
|
+
|
|
1175
|
+
// src/hooks/contacts/usePaginatedContacts.ts
|
|
1176
|
+
function buildFilter10(options) {
|
|
1177
|
+
const conditions = [];
|
|
1178
|
+
if (options.brandId) {
|
|
1179
|
+
conditions.push({ brandId: { eq: options.brandId } });
|
|
1180
|
+
}
|
|
1181
|
+
if (options.search) {
|
|
1182
|
+
conditions.push({
|
|
1183
|
+
or: [
|
|
1184
|
+
{ email: { contains: options.search } },
|
|
1185
|
+
{ firstName: { contains: options.search } },
|
|
1186
|
+
{ lastName: { contains: options.search } }
|
|
1187
|
+
]
|
|
1188
|
+
});
|
|
1189
|
+
}
|
|
1190
|
+
if (options.gdprConsent !== void 0) {
|
|
1191
|
+
conditions.push({ gdprConsent: { eq: options.gdprConsent } });
|
|
1192
|
+
}
|
|
1193
|
+
if (options.marketingOptIn !== void 0) {
|
|
1194
|
+
conditions.push({ marketingOptIn: { eq: options.marketingOptIn } });
|
|
1195
|
+
}
|
|
1196
|
+
if (options.tags && options.tags.length > 0) {
|
|
1197
|
+
const tagConditions = options.tags.map((tag) => ({
|
|
1198
|
+
tags: { contains: tag }
|
|
1199
|
+
}));
|
|
1200
|
+
conditions.push({ or: tagConditions });
|
|
1201
|
+
}
|
|
1202
|
+
if (options.filter && Object.keys(options.filter).length > 0) {
|
|
1203
|
+
conditions.push(options.filter);
|
|
1204
|
+
}
|
|
1205
|
+
if (conditions.length === 0) {
|
|
1206
|
+
return void 0;
|
|
1207
|
+
}
|
|
1208
|
+
if (conditions.length === 1) {
|
|
1209
|
+
return conditions[0];
|
|
1210
|
+
}
|
|
1211
|
+
return { and: conditions };
|
|
1212
|
+
}
|
|
1213
|
+
function transformContact(contact) {
|
|
1214
|
+
return {
|
|
1215
|
+
...contact,
|
|
1216
|
+
name: `${contact.firstName || ""} ${contact.lastName || ""}`.trim() || contact.email,
|
|
1217
|
+
brandName: contact.brand?.name || ""
|
|
1218
|
+
};
|
|
1219
|
+
}
|
|
1220
|
+
var CONTACT_SELECTION_SET = [
|
|
1221
|
+
"id",
|
|
1222
|
+
"email",
|
|
1223
|
+
"phone",
|
|
1224
|
+
"firstName",
|
|
1225
|
+
"lastName",
|
|
1226
|
+
"locale",
|
|
1227
|
+
"brandId",
|
|
1228
|
+
"gdprConsent",
|
|
1229
|
+
"gdprConsentDate",
|
|
1230
|
+
"marketingOptIn",
|
|
1231
|
+
"preferences",
|
|
1232
|
+
"tags",
|
|
1233
|
+
"totalVisits",
|
|
1234
|
+
"lastVisitDate",
|
|
1235
|
+
"firstVisitDate",
|
|
1236
|
+
"source",
|
|
1237
|
+
"status",
|
|
1238
|
+
"createdAt",
|
|
1239
|
+
"updatedAt",
|
|
1240
|
+
"deletedAt",
|
|
1241
|
+
"deletedBy",
|
|
1242
|
+
"brand.name"
|
|
1243
|
+
];
|
|
1244
|
+
var useActiveContactsInternal = createPaginatedDataHook({
|
|
1245
|
+
model: "Contact",
|
|
1246
|
+
dataPropertyName: "contacts",
|
|
1247
|
+
defaultPageSize: 25,
|
|
1248
|
+
selectionSet: CONTACT_SELECTION_SET,
|
|
1249
|
+
transform: transformContact,
|
|
1250
|
+
buildFilter: buildFilter10,
|
|
1251
|
+
baseFilter: ACTIVE_FILTER
|
|
1252
|
+
});
|
|
1253
|
+
var useDeletedContactsInternal = createPaginatedDataHook({
|
|
1254
|
+
model: "Contact",
|
|
1255
|
+
dataPropertyName: "contacts",
|
|
1256
|
+
defaultPageSize: 25,
|
|
1257
|
+
selectionSet: CONTACT_SELECTION_SET,
|
|
1258
|
+
transform: transformContact,
|
|
1259
|
+
buildFilter: buildFilter10,
|
|
1260
|
+
baseFilter: DELETED_FILTER
|
|
1261
|
+
});
|
|
1262
|
+
function useActiveContacts(options = {}) {
|
|
1263
|
+
const result = useActiveContactsInternal(options);
|
|
1264
|
+
return {
|
|
1265
|
+
contacts: result.contacts,
|
|
1266
|
+
loading: result.loading,
|
|
1267
|
+
initialLoading: result.initialLoading,
|
|
1268
|
+
loadingMore: result.loadingMore,
|
|
1269
|
+
error: result.error,
|
|
1270
|
+
pagination: result.pagination,
|
|
1271
|
+
hasMore: result.hasMore,
|
|
1272
|
+
loadMore: result.loadMore,
|
|
1273
|
+
refetch: result.refetch,
|
|
1274
|
+
reset: result.reset,
|
|
1275
|
+
setSearchFilter: result.setSearchFilter,
|
|
1276
|
+
searchFilter: result.searchFilter
|
|
1277
|
+
};
|
|
1278
|
+
}
|
|
1279
|
+
function useDeletedContacts(options = {}) {
|
|
1280
|
+
const result = useDeletedContactsInternal(options);
|
|
1281
|
+
return {
|
|
1282
|
+
contacts: result.contacts,
|
|
1283
|
+
loading: result.loading,
|
|
1284
|
+
initialLoading: result.initialLoading,
|
|
1285
|
+
loadingMore: result.loadingMore,
|
|
1286
|
+
error: result.error,
|
|
1287
|
+
pagination: result.pagination,
|
|
1288
|
+
hasMore: result.hasMore,
|
|
1289
|
+
loadMore: result.loadMore,
|
|
1290
|
+
refetch: result.refetch,
|
|
1291
|
+
reset: result.reset,
|
|
1292
|
+
setSearchFilter: result.setSearchFilter,
|
|
1293
|
+
searchFilter: result.searchFilter
|
|
1294
|
+
};
|
|
1295
|
+
}
|
|
1174
1296
|
export {
|
|
1175
1297
|
ACTIVE_FILTER,
|
|
1176
1298
|
DELETED_FILTER,
|
|
@@ -1180,12 +1302,14 @@ export {
|
|
|
1180
1302
|
useAccounts,
|
|
1181
1303
|
useActiveAccounts,
|
|
1182
1304
|
useActiveBrands,
|
|
1305
|
+
useActiveContacts,
|
|
1183
1306
|
useActiveReservations,
|
|
1184
1307
|
useActiveUsers,
|
|
1185
1308
|
useBrands,
|
|
1186
1309
|
useContacts,
|
|
1187
1310
|
useDeletedAccounts,
|
|
1188
1311
|
useDeletedBrands,
|
|
1312
|
+
useDeletedContacts,
|
|
1189
1313
|
useDeletedReservations,
|
|
1190
1314
|
useDeletedUsers,
|
|
1191
1315
|
useProductInstances,
|