mirror of
https://github.com/block/buzz.git
synced 2026-08-18 06:50:31 +02:00
Signed-off-by: Wes <wesbillman@users.noreply.github.com> Co-authored-by: Pinky <44b8e82baa6e0e254e0208d68f335c283c94e7b78dd1fa10d5a49d3f13dd0435@sprout-oss.stage.blox.sqprod.co>
58 lines
2.0 KiB
TypeScript
58 lines
2.0 KiB
TypeScript
import * as React from "react";
|
|
|
|
import type { ThreadActivityItem } from "@/features/channels/useUnreadChannels";
|
|
import { getThreadReference } from "@/features/messages/lib/threading";
|
|
import type { Channel, FeedItem } from "@/shared/api/types";
|
|
|
|
export function buildThreadActivityFeedItems(
|
|
threadActivityItems: ThreadActivityItem[],
|
|
mutedRootIds: ReadonlySet<string>,
|
|
channels: Channel[],
|
|
): FeedItem[] {
|
|
const channelById = new Map(channels.map((channel) => [channel.id, channel]));
|
|
|
|
return threadActivityItems
|
|
.filter((item) => {
|
|
// Defense-in-depth relay-scope fence: only synthesize rows whose channel
|
|
// is present in the active community's channel set. Rows persisted under
|
|
// a different relay's scope key should never reach this function, but
|
|
// this filter is the last line of defense against cross-community leaks.
|
|
if (channelById.get(item.channelId) === undefined) return false;
|
|
const rootId = getThreadReference(item.tags).rootId;
|
|
return !rootId || !mutedRootIds.has(rootId);
|
|
})
|
|
.map((item) => {
|
|
const channel = channelById.get(item.channelId);
|
|
return {
|
|
id: item.id,
|
|
kind: item.kind,
|
|
pubkey: item.pubkey,
|
|
content: item.content,
|
|
createdAt: item.createdAt,
|
|
channelId: item.channelId,
|
|
channelName: item.channelName,
|
|
channelType: channel?.channelType,
|
|
tags: item.tags,
|
|
category: "activity" as const,
|
|
};
|
|
});
|
|
}
|
|
|
|
export function useThreadActivityFeedItems(
|
|
threadActivityItems: ThreadActivityItem[],
|
|
mutedRootIds: ReadonlySet<string>,
|
|
channels: Channel[],
|
|
): FeedItem[] {
|
|
const mutedRootIdsKey = [...mutedRootIds].sort().join("\0");
|
|
|
|
return React.useMemo(() => {
|
|
// mutedRootIds is a mutable Set; this key invalidates when contents change.
|
|
void mutedRootIdsKey;
|
|
return buildThreadActivityFeedItems(
|
|
threadActivityItems,
|
|
mutedRootIds,
|
|
channels,
|
|
);
|
|
}, [channels, mutedRootIds, mutedRootIdsKey, threadActivityItems]);
|
|
}
|