@semapps/activitypub-components 0.6.5 → 0.6.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.js +329 -68
- package/dist/index.cjs.js.map +1 -1
- package/dist/index.d.ts +22 -13
- package/dist/index.d.ts.map +1 -1
- package/dist/index.es.js +331 -70
- package/dist/index.es.js.map +1 -1
- package/package.json +5 -5
package/dist/index.cjs.js
CHANGED
|
@@ -27,7 +27,7 @@ function $parcel$interopDefault(a) {
|
|
|
27
27
|
$parcel$export(module.exports, "CommentsField", () => $2e5504cc4159ca8d$export$2e2bcd8739ae039);
|
|
28
28
|
$parcel$export(module.exports, "CollectionList", () => $505d598a33288aad$export$2e2bcd8739ae039);
|
|
29
29
|
$parcel$export(module.exports, "ReferenceCollectionField", () => $b0c94a9bdea99da5$export$2e2bcd8739ae039);
|
|
30
|
-
$parcel$export(module.exports, "useCollection", () => $
|
|
30
|
+
$parcel$export(module.exports, "useCollection", () => $5ca5f7e9fc1c3544$export$2e2bcd8739ae039);
|
|
31
31
|
$parcel$export(module.exports, "useInbox", () => $97664763db3c0a46$export$2e2bcd8739ae039);
|
|
32
32
|
$parcel$export(module.exports, "useNodeinfo", () => $30fd77858150739b$export$2e2bcd8739ae039);
|
|
33
33
|
$parcel$export(module.exports, "useOutbox", () => $decfdd34cc00b80e$export$2e2bcd8739ae039);
|
|
@@ -76,7 +76,7 @@ const $ebea823cebb2f44b$export$1ec8e53e7d982d22 = {
|
|
|
76
76
|
REMOVE: "Remove",
|
|
77
77
|
TENTATIVE_REJECT: "TentativeReject",
|
|
78
78
|
TENTATIVE_ACCEPT: "TentativeAccept",
|
|
79
|
-
|
|
79
|
+
TRAVEL: "Travel",
|
|
80
80
|
UNDO: "Undo",
|
|
81
81
|
UPDATE: "Update",
|
|
82
82
|
VIEW: "View"
|
|
@@ -546,7 +546,8 @@ var $d68cd57b2d06b6d5$export$2e2bcd8739ae039 = $d68cd57b2d06b6d5$var$CommentsLis
|
|
|
546
546
|
|
|
547
547
|
|
|
548
548
|
|
|
549
|
-
|
|
549
|
+
|
|
550
|
+
const $03510abb28fd3d8a$export$e57ff0f701c44363 = (value)=>{
|
|
550
551
|
// If the field is null-ish, we suppose there are no values.
|
|
551
552
|
if (value === null || value === undefined) return [];
|
|
552
553
|
// Return as is.
|
|
@@ -556,30 +557,88 @@ const $3ff23aa25753c478$export$e57ff0f701c44363 = (value)=>{
|
|
|
556
557
|
value
|
|
557
558
|
];
|
|
558
559
|
};
|
|
559
|
-
var $
|
|
560
|
-
arrayOf: $
|
|
560
|
+
var $03510abb28fd3d8a$export$2e2bcd8739ae039 = {
|
|
561
|
+
arrayOf: $03510abb28fd3d8a$export$e57ff0f701c44363
|
|
562
|
+
};
|
|
563
|
+
const $03510abb28fd3d8a$export$34aed805e991a647 = (iterable, predicate)=>{
|
|
564
|
+
const seen = new Set();
|
|
565
|
+
return iterable.filter((item)=>{
|
|
566
|
+
const key = predicate(item);
|
|
567
|
+
if (seen.has(key)) return false;
|
|
568
|
+
seen.add(key);
|
|
569
|
+
return true;
|
|
570
|
+
});
|
|
561
571
|
};
|
|
562
572
|
|
|
563
573
|
|
|
574
|
+
const $2b75a2f49c9ef165$var$useItemsFromPagesAndNotifications = (pages, notifications, dereferenceItems)=>{
|
|
575
|
+
const dataProvider = (0, $583VT$reactadmin.useDataProvider)();
|
|
576
|
+
// Add all items from pages and process notifications (possibly new and deleted items).
|
|
577
|
+
const items = (0, $583VT$react.useMemo)(()=>{
|
|
578
|
+
const addItems = notifications.map((n)=>n.type === "Add").map((n)=>n.object);
|
|
579
|
+
const removeItems = notifications.map((n)=>n.type === "Remove").map((n)=>n.object.id || n.object);
|
|
580
|
+
const currentItems = !pages ? [] : pages.flatMap((p)=>(0, $03510abb28fd3d8a$export$e57ff0f701c44363)(p.orderedItems || p.items));
|
|
581
|
+
const currentAndNew = currentItems.concat(addItems);
|
|
582
|
+
return currentAndNew// Filter out removed items.
|
|
583
|
+
.filter((item)=>!removeItems.some((r)=>(r.id ?? r) === (item.id ?? item)))// Filter duplicates.
|
|
584
|
+
.filter((item)=>currentAndNew.some((i2)=>(i2.id ?? i2) === (item.id ?? item)));
|
|
585
|
+
}, pages, notifications);
|
|
586
|
+
if (!dereferenceItems) return {
|
|
587
|
+
loadedItems: items,
|
|
588
|
+
isLoading: false,
|
|
589
|
+
isFetching: false
|
|
590
|
+
};
|
|
591
|
+
// Dereference all items, if they are not yet.
|
|
592
|
+
const itemQueries = (0, $583VT$reactquery.useQueries)(items.filter((item)=>typeof item === "string").map((itemUri)=>({
|
|
593
|
+
queryKey: [
|
|
594
|
+
"resource",
|
|
595
|
+
itemUri
|
|
596
|
+
],
|
|
597
|
+
queryFn: async ()=>(await dataProvider.fetch(itemUri)).json,
|
|
598
|
+
staleTime: Infinity
|
|
599
|
+
})));
|
|
600
|
+
// Put all loaded items together (might be dereferenced already, so concatenate).
|
|
601
|
+
const loadedItems = items.filter((item)=>typeof item !== "string").concat(itemQueries.flatMap((itemQuery)=>{
|
|
602
|
+
return itemQuery.isSuccess && itemQuery.data || [];
|
|
603
|
+
}));
|
|
604
|
+
console.log("loadedItems", loadedItems.length, "total", items.length);
|
|
605
|
+
const errors = itemQueries.filter((q)=>q.error);
|
|
606
|
+
return {
|
|
607
|
+
loadedItems: loadedItems,
|
|
608
|
+
isLoading: itemQueries.some((q)=>q.isLoading),
|
|
609
|
+
isFetching: itemQueries.some((q)=>q.isFetching),
|
|
610
|
+
errors: errors.length > 0 && errors
|
|
611
|
+
};
|
|
612
|
+
};
|
|
564
613
|
const $2b75a2f49c9ef165$var$useCollection = (predicateOrUrl, options = {})=>{
|
|
565
|
-
const { dereferenceItems: dereferenceItems = false } = options;
|
|
614
|
+
const { dereferenceItems: dereferenceItems = false, liveUpdates: liveUpdates = true } = options;
|
|
566
615
|
const { data: identity } = (0, $583VT$reactadmin.useGetIdentity)();
|
|
567
|
-
const [items, setItems] = (0, $583VT$react.useState)();
|
|
568
616
|
const [totalItems, setTotalItems] = (0, $583VT$react.useState)();
|
|
617
|
+
const [notifications, setNotifications] = (0, $583VT$react.useState)([]);
|
|
618
|
+
const [hasLiveUpdates, setHasLiveUpdates] = (0, $583VT$react.useState)({
|
|
619
|
+
status: "disconnected",
|
|
620
|
+
error: undefined
|
|
621
|
+
});
|
|
569
622
|
const dataProvider = (0, $583VT$reactadmin.useDataProvider)();
|
|
570
|
-
|
|
623
|
+
// Get collectionUrl from webId predicate or URL.
|
|
571
624
|
const collectionUrl = (0, $583VT$react.useMemo)(()=>{
|
|
572
625
|
if (predicateOrUrl) {
|
|
573
626
|
if (predicateOrUrl.startsWith("http")) return predicateOrUrl;
|
|
574
627
|
if (identity?.webIdData) return identity?.webIdData?.[predicateOrUrl];
|
|
575
628
|
}
|
|
629
|
+
return undefined;
|
|
630
|
+
// throw new Error(`No URL available for useCollection: ${predicateOrUrl}.`);
|
|
576
631
|
}, [
|
|
577
632
|
identity,
|
|
578
633
|
predicateOrUrl
|
|
579
634
|
]);
|
|
635
|
+
// Fetch page of collection item references (if pageParam provided)
|
|
636
|
+
// or default to `collectionUrl` (which should give you the first page).
|
|
580
637
|
const fetchCollection = (0, $583VT$react.useCallback)(async ({ pageParam: nextPageUrl })=>{
|
|
638
|
+
// Fetch page or first page (collectionUrl)
|
|
581
639
|
let { json: json } = await dataProvider.fetch(nextPageUrl || collectionUrl);
|
|
582
640
|
if (json.totalItems) setTotalItems(json.totalItems);
|
|
641
|
+
// If first page, handle this here.
|
|
583
642
|
if ((json.type === "OrderedCollection" || json.type === "Collection") && json.first) {
|
|
584
643
|
if (json.first?.items) {
|
|
585
644
|
if (json.first?.items.length === 0 && json.first?.next) // Special case where the first property is an object without items
|
|
@@ -588,17 +647,6 @@ const $2b75a2f49c9ef165$var$useCollection = (predicateOrUrl, options = {})=>{
|
|
|
588
647
|
} else // Fetch the first page
|
|
589
648
|
({ json: json } = await dataProvider.fetch(json.first));
|
|
590
649
|
}
|
|
591
|
-
// Force dereference of items
|
|
592
|
-
if (dereferenceItems) {
|
|
593
|
-
const itemPredicate = json.items ? "items" : "orderedItems";
|
|
594
|
-
json[itemPredicate] = json[itemPredicate] && await Promise.all((0, $3ff23aa25753c478$export$e57ff0f701c44363)(json[itemPredicate]).map(async (item)=>{
|
|
595
|
-
if (typeof item === "string") {
|
|
596
|
-
const { json: json } = await dataProvider.fetch(item);
|
|
597
|
-
return json;
|
|
598
|
-
}
|
|
599
|
-
return item;
|
|
600
|
-
}));
|
|
601
|
-
}
|
|
602
650
|
return json;
|
|
603
651
|
}, [
|
|
604
652
|
dataProvider,
|
|
@@ -606,8 +654,9 @@ const $2b75a2f49c9ef165$var$useCollection = (predicateOrUrl, options = {})=>{
|
|
|
606
654
|
identity,
|
|
607
655
|
setTotalItems
|
|
608
656
|
]);
|
|
609
|
-
|
|
610
|
-
|
|
657
|
+
// Use infiniteQuery to handle pagination, fetching, etc.
|
|
658
|
+
const { data: data, error: collectionError, fetchNextPage: fetchNextPage, refetch: refetch, hasNextPage: hasNextPage, isLoading: isLoadingPage, isFetching: isFetchingPage, isFetchingNextPage: isFetchingNextPage } = (0, $583VT$reactquery.useInfiniteQuery)([
|
|
659
|
+
"collection",
|
|
611
660
|
{
|
|
612
661
|
collectionUrl: collectionUrl
|
|
613
662
|
}
|
|
@@ -616,63 +665,57 @@ const $2b75a2f49c9ef165$var$useCollection = (predicateOrUrl, options = {})=>{
|
|
|
616
665
|
getNextPageParam: (lastPage)=>lastPage.next,
|
|
617
666
|
getPreviousPageParam: (firstPage)=>firstPage.prev
|
|
618
667
|
});
|
|
668
|
+
// Put all items together in a list.
|
|
669
|
+
const { loadedItems: items, isLoading: isLoadingItems, isFetching: isFetchingItems, errors: itemErrors } = $2b75a2f49c9ef165$var$useItemsFromPagesAndNotifications(data?.pages, notifications, dereferenceItems);
|
|
670
|
+
// Notifications have been processed after hook call, so reset.
|
|
671
|
+
// useEffect(() => {
|
|
672
|
+
// setNotifications([]);
|
|
673
|
+
// }, [notifications])
|
|
674
|
+
// Live Updates
|
|
619
675
|
(0, $583VT$react.useEffect)(()=>{
|
|
620
|
-
if (
|
|
621
|
-
|
|
622
|
-
|
|
623
|
-
|
|
624
|
-
|
|
625
|
-
|
|
626
|
-
|
|
627
|
-
|
|
628
|
-
|
|
629
|
-
|
|
630
|
-
|
|
631
|
-
|
|
632
|
-
|
|
633
|
-
|
|
634
|
-
|
|
635
|
-
|
|
636
|
-
|
|
637
|
-
|
|
638
|
-
|
|
639
|
-
|
|
640
|
-
|
|
641
|
-
|
|
642
|
-
|
|
643
|
-
|
|
644
|
-
|
|
645
|
-
const removeItem = (0, $583VT$react.useCallback)((itemId)=>{
|
|
646
|
-
setItems((oldItems)=>oldItems.filter((item)=>typeof item === "string" ? item !== itemId : item.id !== itemId));
|
|
647
|
-
// TODO use queryClient.setQueryData to update items directly in react-query cache
|
|
648
|
-
setTimeout(()=>queryClient.refetchQueries([
|
|
649
|
-
"Collection",
|
|
650
|
-
{
|
|
651
|
-
collectionUrl: collectionUrl
|
|
652
|
-
}
|
|
653
|
-
], {
|
|
654
|
-
active: true,
|
|
655
|
-
exact: true
|
|
656
|
-
}), 2000);
|
|
676
|
+
if (liveUpdates && collectionUrl) // Create ws that listens to collectionUri changes
|
|
677
|
+
(0, $583VT$semappssemanticdataprovider.getOrCreateWsChannel)(dataProvider.fetch, collectionUrl).then((webSocket)=>{
|
|
678
|
+
webSocket.addEventListener("message", (e)=>{
|
|
679
|
+
if (e.data && e.data.type === "Add" || e.data.type === "Remove") setNotifications([
|
|
680
|
+
...notifications,
|
|
681
|
+
e.data
|
|
682
|
+
]);
|
|
683
|
+
});
|
|
684
|
+
webSocket.addEventListener("error", (e)=>{
|
|
685
|
+
setHasLiveUpdates({
|
|
686
|
+
status: "error",
|
|
687
|
+
error: e
|
|
688
|
+
});
|
|
689
|
+
// TODO: Retry after a while
|
|
690
|
+
});
|
|
691
|
+
webSocket.addEventListener("close", (e)=>{
|
|
692
|
+
setHasLiveUpdates({
|
|
693
|
+
...hasLiveUpdates,
|
|
694
|
+
status: "disconnected"
|
|
695
|
+
});
|
|
696
|
+
});
|
|
697
|
+
setHasLiveUpdates({
|
|
698
|
+
status: "connected"
|
|
699
|
+
});
|
|
700
|
+
}).catch(()=>{}); // If it fails, we won't receive live updates. But that's okay.
|
|
657
701
|
}, [
|
|
658
|
-
|
|
659
|
-
|
|
660
|
-
|
|
702
|
+
collectionUrl,
|
|
703
|
+
liveUpdates,
|
|
704
|
+
dataProvider.fetch
|
|
661
705
|
]);
|
|
706
|
+
const allErrors = (0, $03510abb28fd3d8a$export$e57ff0f701c44363)(collectionError).concat((0, $03510abb28fd3d8a$export$e57ff0f701c44363)(itemErrors));
|
|
662
707
|
return {
|
|
663
708
|
items: items,
|
|
664
709
|
totalItems: totalItems,
|
|
665
|
-
error:
|
|
710
|
+
error: allErrors.length > 0 && allErrors,
|
|
666
711
|
refetch: refetch,
|
|
667
712
|
fetchNextPage: fetchNextPage,
|
|
668
713
|
hasNextPage: hasNextPage,
|
|
669
|
-
isLoading:
|
|
670
|
-
isFetching:
|
|
714
|
+
isLoading: isLoadingPage || isLoadingItems,
|
|
715
|
+
isFetching: isFetchingPage || isFetchingItems,
|
|
671
716
|
isFetchingNextPage: isFetchingNextPage,
|
|
672
|
-
|
|
673
|
-
|
|
674
|
-
removeItem: removeItem,
|
|
675
|
-
url: collectionUrl
|
|
717
|
+
url: collectionUrl,
|
|
718
|
+
hasLiveUpdates: hasLiveUpdates
|
|
676
719
|
};
|
|
677
720
|
};
|
|
678
721
|
var $2b75a2f49c9ef165$export$2e2bcd8739ae039 = $2b75a2f49c9ef165$var$useCollection;
|
|
@@ -759,6 +802,224 @@ var $b0c94a9bdea99da5$export$2e2bcd8739ae039 = $b0c94a9bdea99da5$var$ReferenceCo
|
|
|
759
802
|
|
|
760
803
|
|
|
761
804
|
|
|
805
|
+
|
|
806
|
+
const $5ca5f7e9fc1c3544$var$useItemsFromPages = (pages, dereferenceItems)=>{
|
|
807
|
+
const dataProvider = (0, $583VT$reactadmin.useDataProvider)();
|
|
808
|
+
const items = (0, $583VT$react.useMemo)(()=>pages.flatMap((p)=>(0, $03510abb28fd3d8a$export$e57ff0f701c44363)(p.orderedItems || p.items)), [
|
|
809
|
+
pages
|
|
810
|
+
]);
|
|
811
|
+
// We will force dereference, if some items are not URI string references.
|
|
812
|
+
const shouldDereference = (0, $583VT$react.useMemo)(()=>{
|
|
813
|
+
return dereferenceItems || items.some((item)=>typeof item !== "string");
|
|
814
|
+
}, [
|
|
815
|
+
dereferenceItems,
|
|
816
|
+
items
|
|
817
|
+
]);
|
|
818
|
+
// Dereference all items, if necessary (even if shouldDereference is false, the hook needs to be called).
|
|
819
|
+
const itemQueries = (0, $583VT$reactquery.useQueries)(!shouldDereference ? [] : items.filter((item)=>typeof item === "string").map((itemUri)=>({
|
|
820
|
+
queryKey: [
|
|
821
|
+
"resource",
|
|
822
|
+
itemUri
|
|
823
|
+
],
|
|
824
|
+
queryFn: async ()=>(await dataProvider.fetch(itemUri)).json,
|
|
825
|
+
staleTime: Infinity
|
|
826
|
+
})));
|
|
827
|
+
if (!shouldDereference) return {
|
|
828
|
+
loadedItems: items,
|
|
829
|
+
isLoading: false,
|
|
830
|
+
isFetching: false
|
|
831
|
+
};
|
|
832
|
+
// Put all loaded items together (might be dereferenced already, so concatenate).
|
|
833
|
+
const loadedItems = items.filter((item)=>typeof item !== "string").concat(itemQueries.flatMap((itemQuery)=>{
|
|
834
|
+
return itemQuery.isSuccess && itemQuery.data || [];
|
|
835
|
+
}));
|
|
836
|
+
const errors = itemQueries.filter((q)=>q.error);
|
|
837
|
+
return {
|
|
838
|
+
loadedItems: loadedItems,
|
|
839
|
+
isLoading: itemQueries.some((q)=>q.isLoading),
|
|
840
|
+
isFetching: itemQueries.some((q)=>q.isFetching),
|
|
841
|
+
errors: errors.length > 0 ? errors : undefined
|
|
842
|
+
};
|
|
843
|
+
};
|
|
844
|
+
/**
|
|
845
|
+
* Subscribe a collection. Supports pagination.
|
|
846
|
+
* @param predicateOrUrl The collection URI or the predicate to get the collection URI from the identity (webId).
|
|
847
|
+
* @param {UseCollectionOptions} options Defaults to `{ dereferenceItems: false, liveUpdates: true }`
|
|
848
|
+
*/ const $5ca5f7e9fc1c3544$var$useCollection = (predicateOrUrl, options = {})=>{
|
|
849
|
+
const { dereferenceItems: dereferenceItems = false, liveUpdates: liveUpdates = true } = options;
|
|
850
|
+
const { data: identity } = (0, $583VT$reactadmin.useGetIdentity)();
|
|
851
|
+
const [totalItems, setTotalItems] = (0, $583VT$react.useState)();
|
|
852
|
+
const queryClient = (0, $583VT$reactquery.useQueryClient)();
|
|
853
|
+
const [hasLiveUpdates, setHasLiveUpdates] = (0, $583VT$react.useState)({
|
|
854
|
+
status: "connecting"
|
|
855
|
+
});
|
|
856
|
+
const dataProvider = (0, $583VT$reactadmin.useDataProvider)();
|
|
857
|
+
// Get collectionUrl from webId predicate or URL.
|
|
858
|
+
const collectionUrl = (0, $583VT$react.useMemo)(()=>{
|
|
859
|
+
if (predicateOrUrl) {
|
|
860
|
+
if (predicateOrUrl.startsWith("http")) return predicateOrUrl;
|
|
861
|
+
if (identity?.webIdData) return identity?.webIdData?.[predicateOrUrl];
|
|
862
|
+
}
|
|
863
|
+
return undefined;
|
|
864
|
+
// throw new Error(`No URL available for useCollection: ${predicateOrUrl}.`);
|
|
865
|
+
}, [
|
|
866
|
+
identity,
|
|
867
|
+
predicateOrUrl
|
|
868
|
+
]);
|
|
869
|
+
// Fetch page of collection item references (if pageParam provided)
|
|
870
|
+
// or default to `collectionUrl` (which should give you the first page).
|
|
871
|
+
const fetchCollection = (0, $583VT$react.useCallback)(async ({ pageParam: nextPageUrl })=>{
|
|
872
|
+
// Fetch page or first page (collectionUrl)
|
|
873
|
+
let { json: json } = await dataProvider.fetch(nextPageUrl || collectionUrl);
|
|
874
|
+
if (json.totalItems) setTotalItems(json.totalItems);
|
|
875
|
+
// If first page, handle this here.
|
|
876
|
+
if ((json.type === "OrderedCollection" || json.type === "Collection") && json.first) {
|
|
877
|
+
if (json.first?.items) {
|
|
878
|
+
if (json.first?.items.length === 0 && json.first?.next) // Special case where the first property is an object without items
|
|
879
|
+
({ json: json } = await dataProvider.fetch(json.first?.next));
|
|
880
|
+
else json = json.first;
|
|
881
|
+
} else // Fetch the first page
|
|
882
|
+
({ json: json } = await dataProvider.fetch(json.first));
|
|
883
|
+
}
|
|
884
|
+
return json;
|
|
885
|
+
}, [
|
|
886
|
+
dataProvider,
|
|
887
|
+
collectionUrl,
|
|
888
|
+
identity,
|
|
889
|
+
setTotalItems
|
|
890
|
+
]);
|
|
891
|
+
// Use infiniteQuery to handle pagination, fetching, etc.
|
|
892
|
+
const { data: pageData, error: collectionError, fetchNextPage: fetchNextPage, refetch: refetch, hasNextPage: hasNextPage, isLoading: isLoadingPage, isFetching: isFetchingPage, isFetchingNextPage: isFetchingNextPage } = (0, $583VT$reactquery.useInfiniteQuery)([
|
|
893
|
+
"collection",
|
|
894
|
+
{
|
|
895
|
+
collectionUrl: collectionUrl
|
|
896
|
+
}
|
|
897
|
+
], fetchCollection, {
|
|
898
|
+
enabled: !!(collectionUrl && identity?.id),
|
|
899
|
+
getNextPageParam: (lastPage)=>lastPage.next,
|
|
900
|
+
getPreviousPageParam: (firstPage)=>firstPage.prev
|
|
901
|
+
});
|
|
902
|
+
// Put all items together in a list (and dereference, if required).
|
|
903
|
+
const { loadedItems: items, isLoading: isLoadingItems, isFetching: isFetchingItems, errors: itemErrors } = $5ca5f7e9fc1c3544$var$useItemsFromPages(pageData?.pages ?? [], dereferenceItems);
|
|
904
|
+
const allErrors = (0, $03510abb28fd3d8a$export$e57ff0f701c44363)(collectionError).concat((0, $03510abb28fd3d8a$export$e57ff0f701c44363)(itemErrors));
|
|
905
|
+
const addItem = (0, $583VT$react.useCallback)((item, shouldRefetch = true)=>{
|
|
906
|
+
queryClient.setQueryData([
|
|
907
|
+
"collection",
|
|
908
|
+
{
|
|
909
|
+
collectionUrl: collectionUrl
|
|
910
|
+
}
|
|
911
|
+
], (oldData)=>{
|
|
912
|
+
if (!oldData) return oldData;
|
|
913
|
+
setTotalItems(totalItems && totalItems + 1);
|
|
914
|
+
// Destructure, so react knows, it needs to re-render the pages.
|
|
915
|
+
const pages = [
|
|
916
|
+
...oldData.pages
|
|
917
|
+
];
|
|
918
|
+
const firstPageItems = pages?.[0]?.orderedItems || pages?.[0]?.items || [];
|
|
919
|
+
firstPageItems.unshift(item);
|
|
920
|
+
oldData.pages = pages;
|
|
921
|
+
return oldData;
|
|
922
|
+
});
|
|
923
|
+
if (shouldRefetch) setTimeout(()=>queryClient.refetchQueries([
|
|
924
|
+
"collection",
|
|
925
|
+
{
|
|
926
|
+
collectionUrl: collectionUrl
|
|
927
|
+
}
|
|
928
|
+
], {
|
|
929
|
+
active: true,
|
|
930
|
+
exact: true
|
|
931
|
+
}), typeof shouldRefetch === "number" ? shouldRefetch : 2000);
|
|
932
|
+
}, [
|
|
933
|
+
queryClient,
|
|
934
|
+
collectionUrl
|
|
935
|
+
]);
|
|
936
|
+
const removeItem = (0, $583VT$react.useCallback)((item, shouldRefetch = true)=>{
|
|
937
|
+
queryClient.setQueryData([
|
|
938
|
+
"collection",
|
|
939
|
+
{
|
|
940
|
+
collectionUrl: collectionUrl
|
|
941
|
+
}
|
|
942
|
+
], (oldData)=>{
|
|
943
|
+
if (!oldData) return oldData;
|
|
944
|
+
setTotalItems(totalItems && totalItems - 1);
|
|
945
|
+
// Destructure, so react knows, it needs to re-render the pages array.
|
|
946
|
+
const pages = [
|
|
947
|
+
...oldData.pages
|
|
948
|
+
];
|
|
949
|
+
// Find the item in all pages and remove the item to be removed (either item.id or just item)
|
|
950
|
+
pages.forEach((page)=>{
|
|
951
|
+
if (page.orderedItems) page.orderedItems = page.orderedItems.filter((i)=>(i.id || i) !== (item.id || item));
|
|
952
|
+
else if (page.items) page.items = page.items.filter((i)=>(i.id || i) !== (item?.id || item));
|
|
953
|
+
});
|
|
954
|
+
oldData.pages = pages;
|
|
955
|
+
return oldData;
|
|
956
|
+
});
|
|
957
|
+
if (shouldRefetch) setTimeout(()=>queryClient.refetchQueries([
|
|
958
|
+
"collection",
|
|
959
|
+
{
|
|
960
|
+
collectionUrl: collectionUrl
|
|
961
|
+
}
|
|
962
|
+
], {
|
|
963
|
+
active: true,
|
|
964
|
+
exact: true
|
|
965
|
+
}), typeof shouldRefetch === "number" ? shouldRefetch : 2000);
|
|
966
|
+
}, [
|
|
967
|
+
queryClient,
|
|
968
|
+
collectionUrl
|
|
969
|
+
]);
|
|
970
|
+
// Live Updates
|
|
971
|
+
(0, $583VT$react.useEffect)(()=>{
|
|
972
|
+
if (liveUpdates && collectionUrl) // Create ws that listens to collectionUri changes
|
|
973
|
+
(0, $583VT$semappssemanticdataprovider.getOrCreateWsChannel)(dataProvider.fetch, collectionUrl).then((webSocket)=>{
|
|
974
|
+
webSocket.addEventListener("message", (e)=>{
|
|
975
|
+
const data = JSON.parse(e.data);
|
|
976
|
+
if (data && data.type === "Add") addItem(data.object, true);
|
|
977
|
+
else if (data && data.type === "Remove") removeItem(data.object, true);
|
|
978
|
+
});
|
|
979
|
+
webSocket.addEventListener("error", (e)=>{
|
|
980
|
+
setHasLiveUpdates({
|
|
981
|
+
status: "error",
|
|
982
|
+
error: e
|
|
983
|
+
});
|
|
984
|
+
// TODO: Retry after a while
|
|
985
|
+
});
|
|
986
|
+
webSocket.addEventListener("close", (e)=>{
|
|
987
|
+
if (!hasLiveUpdates.error) setHasLiveUpdates({
|
|
988
|
+
...hasLiveUpdates,
|
|
989
|
+
status: "closed"
|
|
990
|
+
});
|
|
991
|
+
});
|
|
992
|
+
setHasLiveUpdates({
|
|
993
|
+
status: "connected"
|
|
994
|
+
});
|
|
995
|
+
}).catch(()=>{}); // If it fails, we won't receive live updates. But that's okay.
|
|
996
|
+
}, [
|
|
997
|
+
collectionUrl,
|
|
998
|
+
liveUpdates,
|
|
999
|
+
dataProvider
|
|
1000
|
+
]);
|
|
1001
|
+
return {
|
|
1002
|
+
items: items,
|
|
1003
|
+
totalItems: totalItems,
|
|
1004
|
+
error: allErrors.length > 0 && allErrors,
|
|
1005
|
+
refetch: refetch,
|
|
1006
|
+
fetchNextPage: fetchNextPage,
|
|
1007
|
+
addItem: addItem,
|
|
1008
|
+
removeItem: removeItem,
|
|
1009
|
+
hasNextPage: hasNextPage,
|
|
1010
|
+
isLoading: isLoadingPage || isLoadingItems,
|
|
1011
|
+
isFetching: isFetchingPage || isFetchingItems,
|
|
1012
|
+
isFetchingNextPage: isFetchingNextPage,
|
|
1013
|
+
url: collectionUrl,
|
|
1014
|
+
hasLiveUpdates: hasLiveUpdates
|
|
1015
|
+
};
|
|
1016
|
+
};
|
|
1017
|
+
var $5ca5f7e9fc1c3544$export$2e2bcd8739ae039 = $5ca5f7e9fc1c3544$var$useCollection;
|
|
1018
|
+
|
|
1019
|
+
|
|
1020
|
+
|
|
1021
|
+
|
|
1022
|
+
|
|
762
1023
|
const $97664763db3c0a46$var$useInbox = ()=>{
|
|
763
1024
|
const { data: identity } = (0, $583VT$reactadmin.useGetIdentity)();
|
|
764
1025
|
const inboxUrl = (0, $583VT$react.useMemo)(()=>{
|