Remove unmanaged groups

This commit is contained in:
Jon Staab
2025-05-27 15:30:39 -07:00
parent c33698c662
commit 4ba6c72459
+57 -81
View File
@@ -15,6 +15,7 @@ import {
memoize, memoize,
addToMapKey, addToMapKey,
identity, identity,
groupBy,
always, always,
} from "@welshman/lib" } from "@welshman/lib"
import {load} from "@welshman/net" import {load} from "@welshman/net"
@@ -474,112 +475,87 @@ export const chatSearch = derived(chats, $chats =>
// Messages // Messages
export const messages = derived( export const messages = deriveEvents(repository, {filters: [{kinds: [MESSAGE]}]})
deriveEvents(repository, {filters: [{kinds: [MESSAGE]}]}),
$events => $events,
)
// Nip29
export const groupMeta = deriveEvents(repository, {filters: [{kinds: [GROUP_META]}]})
export const hasNip29 = (relay?: Relay) =>
relay?.profile?.supported_nips?.map?.(String)?.includes?.("29")
// Channels // Channels
export type ChannelMeta = { export type Channel = {
id: string
url: string
room: string
name: string
event: TrustedEvent
access: "public" | "private" access: "public" | "private"
membership: "open" | "closed" membership: "open" | "closed"
picture?: string picture?: string
about?: string about?: string
} }
export type Channel = { export const makeChannelId = (url: string, room: string) => `${url}'${room}`
url: string
room: string
name: string
meta?: ChannelMeta
}
export const makeChannelId = (url: string, room: string) => `${url}|${room}` export const splitChannelId = (id: string) => id.split("'")
export const splitChannelId = (id: string) => id.split("|") export const hasNip29 = (relay?: Relay) =>
relay?.profile?.supported_nips?.map?.(String)?.includes?.("29")
export const channelsById = withGetter( export const channelEvents = deriveEvents(repository, {filters: [{kinds: [GROUP_META]}]})
derived(
[groupMeta, memberships, messages, getUrlsForEvent],
([$groupMeta, $memberships, $messages, $getUrlsForEvent]) => {
const channelsById = new Map<string, Channel>()
// Add meta using group meta events export const channels = derived(
for (const event of $groupMeta) { [channelEvents, getUrlsForEvent],
const meta = fromPairs(event.tags) ([$channelEvents, $getUrlsForEvent]) => {
const room = meta.d const $channels: Channel[] = []
if (room) { for (const event of $channelEvents) {
for (const url of $getUrlsForEvent(event.id)) { const meta = fromPairs(event.tags)
const id = makeChannelId(url, room) const room = meta.d
channelsById.set(id, { if (room) {
url, for (const url of $getUrlsForEvent(event.id)) {
room,
name: meta.name || room,
meta: {
access: meta.private ? "private" : "public",
membership: meta.closed ? "closed" : "open",
picture: meta.picture,
about: meta.about,
},
})
}
}
}
// Add known rooms based on membership events
for (const membership of $memberships) {
for (const {url, room, name} of getMembershipRooms(membership)) {
const id = makeChannelId(url, room) const id = makeChannelId(url, room)
if (!channelsById.has(id)) { $channels.push({
channelsById.set(id, {url, room, name}) id,
} url,
room,
event,
name: meta.name || room,
access: meta.private ? "private" : "public",
membership: meta.closed ? "closed" : "open",
picture: meta.picture,
about: meta.about,
})
} }
} }
}
// Add rooms based on known messages return $channels
for (const event of $messages) { },
const [_, room] = event.tags.find(nthEq(0, ROOM)) || []
if (room) {
for (const url of $getUrlsForEvent(event.id)) {
const id = makeChannelId(url, room)
if (!channelsById.has(id)) {
channelsById.set(id, {url, room, name: room})
}
}
}
}
return channelsById
},
),
) )
export const deriveChannel = (url: string, room: string) => export const channelsByUrl = derived(channels, $channels => groupBy(c => c.url, $channels))
derived(channelsById, $channelsById => $channelsById.get(makeChannelId(url, room)))
export const channelsByUrl = derived(channelsById, $channelsById => { export const {
const $channelsByUrl = new Map<string, Channel[]>() indexStore: channelsById,
deriveItem: _deriveChannel,
loadItem: _loadChannel,
} = collection({
name: "channels",
store: channels,
getKey: channel => channel.id,
load: async (id: string) => {
const [url, room] = splitChannelId(id)
for (const channel of $channelsById.values()) { await load({
pushToMapKey($channelsByUrl, channel.url, channel) relays: [url],
} filters: [{kinds: [GROUP_META], "#d": [room]}],
})
return $channelsByUrl },
}) })
export const deriveChannel = (url: string, room: string) => _deriveChannel(makeChannelId(url, room))
export const loadChannel = (url: string, room: string) => _loadChannel(makeChannelId(url, room))
export const displayChannel = (url: string, room: string) => export const displayChannel = (url: string, room: string) =>
channelsById.get().get(makeChannelId(url, room))?.name || room channelsById.get().get(makeChannelId(url, room))?.name || room
@@ -587,7 +563,7 @@ export const roomComparator = (url: string) => (room: string) =>
displayChannel(url, room).toLowerCase() displayChannel(url, room).toLowerCase()
export const channelIsLocked = (channel?: Channel) => export const channelIsLocked = (channel?: Channel) =>
channel?.meta?.access === "private" && channel?.meta?.membership === "closed" channel?.access === "private" && channel?.membership === "closed"
// User stuff // User stuff