Skip to content

Commit bbd15f6

Browse files
committed
be more aggressive with loading videos
1 parent 3bd35ae commit bbd15f6

File tree

4 files changed

+66
-24
lines changed

4 files changed

+66
-24
lines changed

app/components/dialogs/upload-video-dialog.tsx

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -28,6 +28,7 @@ import { Progress } from "../ui/progress";
2828
import { FFmpeg } from "@ffmpeg/ffmpeg";
2929
import { fetchFile, toBlobURL } from "@ffmpeg/util";
3030
import { RangeSlider } from "../ui/range-slider";
31+
import { toast } from "sonner";
3132

3233
type FormData = {
3334
title: string | null;

app/components/video-card.tsx

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -36,6 +36,12 @@ import { motion } from "framer-motion";
3636
dayjs.extend(utc);
3737
dayjs.extend(relativeTime);
3838

39+
export function VideoCardSkeleton() {
40+
return (
41+
<Skeleton className="relative group/video aspect-video max-w-2xl rounded-lg overflow-hidden border shadow-lg" />
42+
);
43+
}
44+
3945
type VideoCardProps = {
4046
title: string;
4147
views: number;

app/lib/query-utils.ts

Lines changed: 11 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -80,7 +80,17 @@ const fetchVideosData = createServerFn({ method: "GET" })
8080
export const videosQueryOptions = queryOptions({
8181
queryKey: queryKeys.videos,
8282
queryFn: () => fetchVideosData(),
83-
staleTime: 1000 * 60 * 5,
83+
staleTime: ({ state }) => {
84+
if (
85+
state?.data &&
86+
"signedIn" in state.data &&
87+
state.data?.signedIn === false
88+
) {
89+
return 0;
90+
}
91+
92+
return 1000 * 60 * 5;
93+
},
8494
});
8595

8696
export type VideoData = {

app/routes/videos.tsx

Lines changed: 48 additions & 23 deletions
Original file line numberDiff line numberDiff line change
@@ -14,34 +14,19 @@ import { UploadButton } from "../components/upload-button";
1414
import { UploadingVideosContainer } from "../components/uploading-videos-container";
1515
import { VideosBoard } from "../components/videos-board";
1616
import { useQuery } from "@tanstack/react-query";
17-
import { fetchClerkAuth } from "@/server-fns/clerk";
1817
import { seo } from "@/lib/seo";
1918
import { HeroHighlight } from "@/components/ui/hero-highlight";
2019
import { Separator } from "@/components/ui/seperator";
2120
import { Footer } from "@/components/footer";
2221
import { useEffect } from "react";
2322
import { HumanFileSizeMotion } from "@/components/human-file-size-motion";
2423
import { humanFileSize } from "@/lib/utils";
24+
import { useUser } from "@clerk/tanstack-start";
25+
import { VideoCardSkeleton } from "@/components/video-card";
2526

2627
export const Route = createFileRoute("/videos")({
2728
component: RouteComponent,
28-
beforeLoad: async () => {
29-
const { userId } = await fetchClerkAuth();
30-
31-
if (!userId) {
32-
throw redirect({ to: "/sign-in/$" });
33-
}
34-
35-
return {
36-
userId,
37-
};
38-
},
3929
pendingMs: 0,
40-
loader: ({ context }) => {
41-
return {
42-
userId: context.userId,
43-
};
44-
},
4530
head: () => ({
4631
meta: seo({
4732
title: "Your Videos",
@@ -52,12 +37,44 @@ export const Route = createFileRoute("/videos")({
5237
});
5338

5439
function RouteComponent() {
55-
const { userId } = Route.useLoaderData();
56-
const { data: videoData } = useQuery(videosQueryOptions);
40+
const navigate = Route.useNavigate();
41+
const { user } = useUser();
42+
const { data: videoData, isLoading } = useQuery({
43+
...videosQueryOptions,
44+
queryFn: async () => {
45+
try {
46+
// @ts-expect-error
47+
const data = await videosQueryOptions.queryFn!();
48+
49+
return data;
50+
} catch (error) {
51+
if (
52+
typeof error === "object" &&
53+
error !== null &&
54+
"isRedirect" in error &&
55+
error.isRedirect &&
56+
"to" in error &&
57+
typeof error.to === "string"
58+
) {
59+
// @ts-expect-error
60+
navigate(error);
61+
62+
return {
63+
videos: [],
64+
signedIn: false,
65+
};
66+
}
67+
68+
return {
69+
videos: [],
70+
};
71+
}
72+
},
73+
});
5774
const { data: usageData } = useQuery(usageDataQueryOptions);
5875

5976
useEffect(() => {
60-
if (!videoData) {
77+
if (!videoData || !user?.id) {
6178
return;
6279
}
6380

@@ -68,13 +85,13 @@ function RouteComponent() {
6885
isPrivate: video.isPrivate,
6986
videoLengthSeconds: video.videoLengthSeconds,
7087
views: video.views,
71-
authorId: userId,
88+
authorId: user.id,
7289
isProcessing: video.status === "processing",
7390
videoCreatedAt: video.createdAt.toString(),
7491
},
7592
});
7693
});
77-
}, [videoData, userId]);
94+
}, [videoData, user]);
7895

7996
return (
8097
<HeroHighlight className="min-h-screen flex flex-col">
@@ -106,7 +123,15 @@ function RouteComponent() {
106123
<div className="container flex flex-col gap-6">
107124
<div className="grid grid-cols-1 sm:grid-cols-1 md:grid-cols-2 lg:grid-cols-3 gap-6">
108125
<UploadingVideosContainer />
109-
{videoData && <VideosBoard videos={videoData.videos} />}
126+
{isLoading ? (
127+
<>
128+
<VideoCardSkeleton />
129+
<VideoCardSkeleton />
130+
<VideoCardSkeleton />
131+
</>
132+
) : (
133+
videoData && <VideosBoard videos={videoData.videos} />
134+
)}
110135
</div>
111136
</div>
112137
</main>

0 commit comments

Comments
 (0)