Skip to content

Commit

Permalink
perf(exchanges): better sync with notifications (#1445)
Browse files Browse the repository at this point in the history
  • Loading branch information
douglasduteil authored Jun 16, 2024
1 parent 51f1d3c commit c53ce3c
Show file tree
Hide file tree
Showing 6 changed files with 69 additions and 44 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -15,6 +15,7 @@ import {
Exchange as Icon_Exchange,
LocationRadius,
} from "@1.ui/react/icons";
import { useUpdateEffect } from "@react-hookz/web";
import { useSession } from "next-auth/react";
import Link from "next/link";
import { useParams, useSearchParams } from "next/navigation";
Expand All @@ -29,7 +30,7 @@ export default function Infinite_Exchange_List() {
const params = z
.object({ exchange_id: z.string().optional() })
.parse(useParams(), { path: ["useParams()"] });
const { exchange_id } = params;
const { exchange_id: location_exchange_id } = params;
const info = TRPC_React.exchanges.me.find.useInfiniteQuery(
{ search },
{ getNextPageParam: ({ next_cursor }) => next_cursor },
Expand All @@ -56,15 +57,23 @@ export default function Infinite_Exchange_List() {
{pages
.map((page) => page.data)
.flat()
.map(({ exchange, is_unread }) => (
<li key={exchange.id}>
<Item
exchange_id={exchange.id}
active={exchange.id === exchange_id}
unread={is_unread}
/>
</li>
))}
.map(
({
exchange: { id: exchange_id, updated_at },
last_thread_update,
is_unread,
}) => (
<li key={exchange_id}>
<Item
active={exchange_id === location_exchange_id}
exchange_id={exchange_id}
last_thread_update={last_thread_update}
unread={is_unread}
updated_at={updated_at}
/>
</li>
),
)}
<li className="col-span-full mx-auto">
{isFetchingNextPage ? <Loading /> : null}
</li>
Expand All @@ -87,17 +96,27 @@ export default function Infinite_Exchange_List() {
function Item({
active,
exchange_id,
last_thread_update,
unread,
updated_at,
}: {
active: boolean;
exchange_id: string;
last_thread_update: Date;
unread: boolean;
updated_at: Date;
}) {
const utils = TRPC_React.useUtils();
const info = TRPC_React.exchanges.by_id.useQuery(exchange_id);
const { data: session } = useSession();
const searchParams = useSearchParams();
const profile_id = session?.profile.id ?? PROFILE_UNKNOWN.id;

useUpdateEffect(() => {
info.refetch();
utils.exchanges.me.inbox.by_exchange_id.invalidate({ exchange_id });
}, [exchange_id, Number(updated_at), Number(last_thread_update)]);

//

if (info.status !== "success") {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,7 @@ import type { Params } from ":pipes/exchange_by_id";
import { TRPC_React } from ":trpc/client";
import { Deal_Status_Schema, type Deal } from "@1.modules/exchange.domain";
import { handshake_format } from "@1.modules/exchange.domain/handshake_format";
import type { Inbox, Message } from "@1.modules/inbox.domain";
import type { Inbox } from "@1.modules/inbox.domain";
import { thread_recipient } from "@1.modules/inbox.domain/select";
import { Thread_InfiniteList } from "@1.modules/inbox.ui/thread/InfiniteList";
import { Thread_AsyncItem } from "@1.modules/inbox.ui/thread/Thread_AsyncItem";
Expand Down Expand Up @@ -67,21 +67,18 @@ function UserThread_Item({

useUpdateEffect(() => {
info.refetch();
}, [thread_id, updated_at]);
}, [thread_id, Number(updated_at)]);

return (
<Thread_AsyncItem info={info}>
{({ inbox }) => {
const { thread, deal, last_seen_date } = inbox as Inbox & {
deal: Deal;
};
const last_message =
thread.messages.at(0) ??
({
content: "...",
created_at: new Date(),
updated_at: new Date(),
} satisfies Omit<Message, "author" | "id">);
const last_message = thread.messages.at(0);
const last_message_content = last_message?.content
? handshake_format(last_message.content)
: "...";

const participant = thread_recipient({
participants: thread.participants,
Expand All @@ -101,7 +98,7 @@ function UserThread_Item({
}}
>
<Thread_Item
last_update={last_message.updated_at}
last_update={thread.updated_at}
variants={{
active: is_active,
unread,
Expand All @@ -112,7 +109,7 @@ function UserThread_Item({
</Thread_Item.Avatar>
<Thread_Item.Body>
<Indicator className="float-right" status={deal.status} />
{handshake_format(last_message.content)}
{last_message_content}
</Thread_Item.Body>
</Thread_Item>
</Link>
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -2,14 +2,15 @@

import { ProfileAvatarMedia } from ":components/avatar";
import { TRPC_React } from ":trpc/client";
import type { Inbox, Message } from "@1.modules/inbox.domain";
import type { Inbox } from "@1.modules/inbox.domain";
import { thread_recipient } from "@1.modules/inbox.domain/select";
import { Thread_InfiniteList } from "@1.modules/inbox.ui/thread/InfiniteList";
import { Thread_AsyncItem } from "@1.modules/inbox.ui/thread/Thread_AsyncItem";
import { Thread_Item } from "@1.modules/inbox.ui/thread/Thread_Item";
import { PROFILE_UNKNOWN } from "@1.modules/profile.domain";
import { Circle } from "@1.ui/react/icons";
import { Frame } from "@1.ui/react/motion/Frame";
import { useUpdateEffect } from "@react-hookz/web";
import type { UseQueryResult } from "@tanstack/react-query";
import { isAfter } from "date-fns";
import { m, type Transition, type Variants } from "framer-motion";
Expand Down Expand Up @@ -49,9 +50,9 @@ function Infinite_Thread_List() {

return (
<Thread_InfiniteList info={query_info}>
{({ id, thread }) => (
{({ id, thread: { id: thread_id, updated_at } }) => (
<MotionOutlet key={id} id={id}>
<UserThread_Item thread_id={thread.id} />
<UserThread_Item thread_id={thread_id} updated_at={updated_at} />
</MotionOutlet>
)}
</Thread_InfiniteList>
Expand Down Expand Up @@ -85,7 +86,13 @@ function MotionOutlet({
);
}

function UserThread_Item({ thread_id }: { thread_id: string }) {
function UserThread_Item({
thread_id,
updated_at,
}: {
thread_id: string;
updated_at: Date;
}) {
const { data: session } = useSession();
const search_params = useSearchParams();
const pathname = usePathname();
Expand All @@ -94,17 +101,15 @@ function UserThread_Item({ thread_id }: { thread_id: string }) {
thread_id,
) as UseQueryResult<Inbox>;

useUpdateEffect(() => {
info.refetch();
}, [thread_id, Number(updated_at)]);

return (
<Thread_AsyncItem info={info}>
{({ inbox }) => {
const { thread, last_seen_date } = inbox;
const last_message =
thread.messages.at(0) ??
({
content: "...",
created_at: new Date(),
updated_at: new Date(),
} satisfies Omit<Message, "author" | "id">);
const last_message = thread.messages.at(0)?.content ?? "...";

const participant = thread_recipient({
participants: thread.participants,
Expand All @@ -114,7 +119,7 @@ function UserThread_Item({ thread_id }: { thread_id: string }) {
const href = `/@~/inbox/${thread.id}`;
const is_active = pathname === href;
const unread = !is_active
? isAfter(last_message.created_at, last_seen_date)
? isAfter(thread.updated_at, last_seen_date)
: false;
const { indicator } = item({ unread });

Expand All @@ -127,7 +132,7 @@ function UserThread_Item({ thread_id }: { thread_id: string }) {
key={thread.id}
>
<Thread_Item
last_update={last_message.created_at}
last_update={thread.updated_at}
last_seen_date={last_seen_date}
variants={{
active: is_active,
Expand All @@ -141,7 +146,7 @@ function UserThread_Item({ thread_id }: { thread_id: string }) {
<div className={indicator()}>
<Circle className="size-4 text-[#FF5F5F]" />
</div>
{last_message.content}
{last_message}
</Thread_Item.Body>
</Thread_Item>
</Link>
Expand Down
2 changes: 1 addition & 1 deletion apps/www/app/layout.client.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -48,7 +48,7 @@ function ReactQueryClientProvider({ children }: PropsWithChildren) {
...options,
queries: {
...options.queries,
staleTime: 1_000 * 30, // 30 seconds
staleTime: 1_000 * 60, // 1 minute
},
},
}),
Expand Down
18 changes: 10 additions & 8 deletions apps/www/components/navbar/notification_indicator.client.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -33,13 +33,14 @@ export function Notification_DotIndicator() {

export function MessageNews_DotIndicator() {
const utils = TRPC_React.useUtils();
const { data: count_unread } = TRPC_React.notification.count_unread.useQuery({
type: "INBOX_NEW_MESSAGE",
});
const { data: count_unread, dataUpdatedAt } =
TRPC_React.notification.count_unread.useQuery({
type: "INBOX_NEW_MESSAGE",
});

useUpdateEffect(() => {
utils.inbox.find.invalidate();
}, [count_unread]);
}, [dataUpdatedAt]);

if (!count_unread) return null;
if (count_unread <= 0) return null;
Expand All @@ -49,13 +50,14 @@ export function MessageNews_DotIndicator() {

export function ExchangeNews_DotIndicator() {
const utils = TRPC_React.useUtils();
const { data: count_unread } = TRPC_React.notification.count_unread.useQuery({
type: "EXCHANGE",
});
const { data: count_unread, dataUpdatedAt } =
TRPC_React.notification.count_unread.useQuery({
type: "EXCHANGE",
});

useUpdateEffect(() => {
utils.exchanges.me.find.invalidate();
}, [count_unread]);
}, [dataUpdatedAt]);

if (!count_unread) return null;
if (count_unread <= 0) return null;
Expand Down
2 changes: 2 additions & 0 deletions packages/@1/modules/exchange/api/src/me/find.ts
Original file line number Diff line number Diff line change
Expand Up @@ -69,6 +69,7 @@ export const find = next_auth_procedure
},
take: 1,
where: { owner_id: student_id },
orderBy: { thread: { updated_at: "desc" } },
},
},
take: limit + 1,
Expand All @@ -90,6 +91,7 @@ export const find = next_auth_procedure
} = exchange_threads[0]!;
return {
exchange: parent,
last_thread_update: updated_at,
is_unread: isAfter(updated_at, last_seen_date),
};
});
Expand Down

0 comments on commit c53ce3c

Please sign in to comment.