diff --git a/src/components/Nav/AuthModal/EmailConfirm.tsx b/src/components/Nav/AuthModal/EmailConfirm.tsx index ab23280a..0e062add 100644 --- a/src/components/Nav/AuthModal/EmailConfirm.tsx +++ b/src/components/Nav/AuthModal/EmailConfirm.tsx @@ -1,7 +1,7 @@ import type { ConfirmEmailSearchParams } from './types' import { clsx } from 'clsx' -import { createEffect, createMemo, createSignal, onMount, Show } from 'solid-js' +import { createEffect, createSignal, onMount, Show } from 'solid-js' import { useLocalize } from '../../../context/localize' import { useSession } from '../../../context/session' diff --git a/src/components/Nav/SearchModal/SearchModal.tsx b/src/components/Nav/SearchModal/SearchModal.tsx index bdc12e97..1e9d05a5 100644 --- a/src/components/Nav/SearchModal/SearchModal.tsx +++ b/src/components/Nav/SearchModal/SearchModal.tsx @@ -1,4 +1,4 @@ -import clsx from 'clsx' +import { clsx } from 'clsx' import { useLocalize } from '../../../context/localize' import { Icon } from '../../_shared/Icon' diff --git a/src/components/Views/Inbox.tsx b/src/components/Views/Inbox.tsx index 20047839..3816ddda 100644 --- a/src/components/Views/Inbox.tsx +++ b/src/components/Views/Inbox.tsx @@ -7,7 +7,6 @@ import { For, createSignal, Show, onMount, createEffect, createMemo, on } from ' import { useInbox } from '../../context/inbox' import { useLocalize } from '../../context/localize' import { useSession } from '../../context/session' -import { loadRecipients } from '../../stores/inbox' import { useRouter } from '../../stores/router' import { showModal } from '../../stores/ui' import { Icon } from '../_shared/Icon' @@ -42,7 +41,7 @@ export const InboxView = () => { const { chats, messages, - actions: { loadChats, getMessages, sendMessage, createChat }, + actions: { loadChats, loadRecipients, getMessages, sendMessage, createChat }, } = useInbox() const [recipients, setRecipients] = createSignal([]) diff --git a/src/context/inbox.tsx b/src/context/inbox.tsx index e963eb54..5188e473 100644 --- a/src/context/inbox.tsx +++ b/src/context/inbox.tsx @@ -1,10 +1,10 @@ -import type { Chat, Message, MutationCreate_MessageArgs } from '../graphql/schema/chat.gen' +import type { Chat, Message, MessagesBy, MutationCreate_MessageArgs } from '../graphql/schema/chat.gen' import type { Accessor, JSX } from 'solid-js' -import { createContext, createMemo, createSignal, useContext } from 'solid-js' +import { createContext, createEffect, createSignal, useContext } from 'solid-js' import { inboxClient } from '../graphql/client/chat' -import { loadMessages } from '../stores/inbox' +import { Author } from '../graphql/schema/core.gen' import { SSEMessage, useConnect } from './connect' import { useSession } from './session' @@ -14,8 +14,10 @@ type InboxContextType = { messages?: Accessor actions: { createChat: (members: number[], title: string) => Promise<{ chat: Chat }> - loadChats: () => Promise - getMessages?: (chatId: string) => Promise + loadChats: () => Promise> + loadRecipients: () => Promise> + loadMessages: (by: MessagesBy, limit: number, offset: number) => Promise> + getMessages?: (chatId: string) => Promise> sendMessage?: (args: MutationCreate_MessageArgs) => void } } @@ -29,6 +31,7 @@ export function useInbox() { export const InboxProvider = (props: { children: JSX.Element }) => { const [chats, setChats] = createSignal([]) const [messages, setMessages] = createSignal([]) + const handleMessage = (sseMessage: SSEMessage) => { console.log('[context.inbox]:', sseMessage) @@ -41,50 +44,77 @@ export const InboxProvider = (props: { children: JSX.Element }) => { setChats((prev) => [...prev, relivedChat]) } } - const { - actions: { getToken }, - } = useSession() - const apiClient = createMemo(() => { - const token = getToken() - if (!inboxClient.private) { - inboxClient.connect(token) - return inboxClient - } - }) + const { addHandler } = useConnect() addHandler(handleMessage) + const { + actions: { getToken }, + } = useSession() + + createEffect(() => { + const token = getToken() + if (!inboxClient.private && token) { + inboxClient.connect(token) + } + }) + + const loadRecipients = async (limit = 50, offset = 0): Promise> => { + if (inboxClient.private) { + // TODO: perhaps setMembers(authors) ? + return await inboxClient.loadRecipients({ limit, offset }) + } + return [] + } + + const loadMessages = async ( + by: MessagesBy, + limit: number = 50, + offset: number = 0, + ): Promise> => { + if (inboxClient.private) { + const msgs = await inboxClient.loadChatMessages({ by, limit, offset }) + setMessages((mmm) => [...mmm, ...msgs]) // TODO: check unique + return msgs || [] + } + return [] + } const loadChats = async () => { try { - const client = apiClient() - if (client) { - const newChats = await client.loadChats({ limit: 50, offset: 0 }) + if (inboxClient.private) { + const newChats = await inboxClient.loadChats({ limit: 50, offset: 0 }) setChats(newChats) + return newChats } } catch (error) { console.log('[loadChats] error:', error) } + return [] } const getMessages = async (chatId: string) => { - if (!chatId) return + if (!chatId) return [] try { - const response = await loadMessages({ chat: chatId }) - setMessages(response as unknown as Message[]) + const msgs: Message[] = await loadMessages({ chat: chatId }) + setMessages(msgs) + return msgs || [] } catch (error) { console.error('Error loading messages:', error) } + return [] } const sendMessage = async (args: MutationCreate_MessageArgs) => { try { - const message = await apiClient().createMessage(args) - setMessages((prev) => [...prev, message]) - const currentChat = chats().find((chat) => chat.id === args.chat_id) - setChats((prev) => [ - ...prev.filter((c) => c.id !== currentChat.id), - { ...currentChat, updated_at: message.created_at }, - ]) + if (inboxClient.private) { + const message = await inboxClient.createMessage(args) + setMessages((prev) => [...prev, message]) + const currentChat = chats().find((chat) => chat.id === args.chat_id) + setChats((prev) => [ + ...prev.filter((c) => c.id !== currentChat.id), + { ...currentChat, updated_at: message.created_at }, + ]) + } } catch (error) { console.error('Error sending message:', error) } @@ -92,9 +122,11 @@ export const InboxProvider = (props: { children: JSX.Element }) => { const createChat = async (members: number[], title: string) => { try { - const chat = await inboxClient.createChat({ members, title }) - setChats((prevChats) => [chat, ...prevChats]) - return chat + if (inboxClient.private) { + const chat = await inboxClient.createChat({ members, title }) + setChats((prevChats) => [chat, ...prevChats]) + return chat + } } catch (error) { console.error('Error creating chat:', error) } @@ -103,6 +135,8 @@ export const InboxProvider = (props: { children: JSX.Element }) => { const actions = { createChat, loadChats, + loadMessages, + loadRecipients, getMessages, sendMessage, } diff --git a/src/context/notifications.tsx b/src/context/notifications.tsx index 9dbd05ac..754006d9 100644 --- a/src/context/notifications.tsx +++ b/src/context/notifications.tsx @@ -1,6 +1,6 @@ import type { Accessor, JSX } from 'solid-js' -import { createContext, createMemo, createSignal, onMount, useContext } from 'solid-js' +import { createContext, createEffect, createMemo, createSignal, onMount, useContext } from 'solid-js' import { createStore } from 'solid-js/store' import { Portal } from 'solid-js/web' @@ -44,21 +44,18 @@ export const NotificationsProvider = (props: { children: JSX.Element }) => { actions: { getToken }, } = useSession() - const apiClient = createMemo(() => { + createEffect(() => { const token = getToken() - if (!notifierClient.private) { + if (!notifierClient.private && token) { notifierClient.connect(token) - return notifierClient } }) const { addHandler } = useConnect() const loadNotifications = async (options: { limit?: number; offset?: number }) => { - const client = apiClient() - if (isAuthenticated() && client) { - console.debug(client) - const { notifications, unread, total } = await client.getNotifications(options) + if (isAuthenticated() && notifierClient?.private) { + const { notifications, unread, total } = await notifierClient.getNotifications(options) const newNotificationEntities = notifications.reduce((acc, notification) => { acc[notification.id] = notification return acc @@ -91,18 +88,14 @@ export const NotificationsProvider = (props: { children: JSX.Element }) => { }) const markNotificationAsRead = async (notification: Notification) => { - const client = apiClient() - if (client) { - await client.markNotificationAsRead(notification.id) - } + if (notifierClient.private) await notifierClient.markNotificationAsRead(notification.id) const nnn = new Set([...notification.seen, notification.id]) setNotificationEntities(notification.id, 'seen', [...nnn]) setUnreadNotificationsCount((oldCount) => oldCount - 1) } const markAllNotificationsAsRead = async () => { - const client = apiClient() - if (isAuthenticated() && client) { - await client.markAllNotificationsAsRead() + if (isAuthenticated() && notifierClient.private) { + await notifierClient.markAllNotificationsAsRead() await loadNotifications({ limit: loadedNotificationsCount() }) } } diff --git a/src/context/session.tsx b/src/context/session.tsx index 7b80dd6c..e8ce4ad8 100644 --- a/src/context/session.tsx +++ b/src/context/session.tsx @@ -85,13 +85,13 @@ export const SessionProvider = (props: { const getSession = async (): Promise => { try { const tkn = getToken() - console.debug('[context.session] token before:', tkn) + // console.debug('[context.session] token before:', tkn) const authResult = await authorizer().getSession({ Authorization: tkn, }) if (authResult?.access_token) { mutate(authResult) - console.debug('[context.session] token after:', authResult.access_token) + // console.debug('[context.session] token after:', authResult.access_token) await loadSubscriptions() return authResult } diff --git a/src/stores/inbox.ts b/src/stores/inbox.ts deleted file mode 100644 index cffc4846..00000000 --- a/src/stores/inbox.ts +++ /dev/null @@ -1,11 +0,0 @@ -import type { MessagesBy } from '../graphql/schema/chat.gen' - -import { inboxClient } from '../graphql/client/chat' - -export const loadRecipients = async (by = {}): Promise => { - return await inboxClient.loadRecipients(by) -} - -export const loadMessages = async (by: MessagesBy): Promise => { - return await inboxClient.loadChatMessages({ by, limit: 50, offset: 0 }) -}