Skip to content

Commit 2a250bf

Browse files
committed
Adding metadata and proper gating
1 parent a684306 commit 2a250bf

8 files changed

Lines changed: 140 additions & 89 deletions

File tree

.env

Lines changed: 9 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -1,3 +1,9 @@
1-
NEXT_PUBLIC_PHOTOS_HOST=https://imagedelivery.net/dqFoxiedZNoncKJ9uqxz0g
2-
PHOTOS_HOST=https://imagedelivery.net/dqFoxiedZNoncKJ9uqxz0g
3-
PHOTO_API_HOST=https://image-test-importer.jsconf.cl
1+
NEXT_PUBLIC_SANITY_PROJECT_ID=t2zgeg0i
2+
NEXT_PUBLIC_SANITY_DATASET=dev
3+
NEXT_PUBLIC_SANITY_API_VERSION=
4+
NEXT_PUBLIC_SANITY_USE_CDN=True
5+
NEXT_PUBLIC_BASE_URL=https://gallery.jschile.org
6+
# CLERK
7+
NEXT_PUBLIC_CLERK_PUBLISHABLE_KEY='pk_test_ZnVua3ktZ3JpZmZvbi04NC5jbGVyay5hY2NvdW50cy5kZXYk'
8+
CLERK_SECRET_KEY=''
9+
NEXT_PUBLIC_JSCL_API_URL="https://graphql-api.jsconfcl.workers.dev/graphql"

app/import/page.tsx

Lines changed: 4 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,3 +1,4 @@
1+
import { Suspense } from "react";
12
import { Import } from "../../src/features/import";
23
import { API } from "../../src/gql/sanityApi";
34

@@ -7,7 +8,9 @@ export default async function Page() {
78

89
return (
910
<main className="mx-auto max-w-5xl p-4">
10-
<Import communityEvents={communityEvents} />
11+
<Suspense>
12+
<Import communityEvents={communityEvents} />
13+
</Suspense>
1114
</main>
1215
);
1316
}

app/layout.tsx

Lines changed: 35 additions & 32 deletions
Original file line numberDiff line numberDiff line change
@@ -5,6 +5,7 @@ import { Clerk } from "../src/components/Auth/clerk";
55
import { Toaster } from "../src/components/ui/toaster";
66
import { Footer } from "../src/features/footer";
77
import { Metadata } from "next";
8+
import { JSChileApolloProvider } from "../src/components/ApolloProvider";
89

910
export async function generateMetadata({ params }): Promise<Metadata> {
1011
return {
@@ -45,39 +46,41 @@ export default function RootLayout({
4546
}) {
4647
return (
4748
<Clerk>
48-
<html lang="en">
49-
<head>
50-
<link rel="icon" href="/favicon.ico" />
51-
<meta property="og:type" content="website" />
52-
<meta property="og:site_name" content="https://gallery.jsconf.cl" />
53-
<meta
54-
property="og:description"
55-
content="Explora las mejores fotos de la exitosa Conferencia de JavaScript en Chile de febrero de 2023 y revive los momentos más emocionantes de este evento de tecnología de vanguardia."
56-
/>
57-
<meta property="og:title" content="JSConf Chile 2023 Photos" />
58-
<meta name="twitter:card" content="summary_large_image" />
59-
<meta name="twitter:title" content="JSConf Chile 2023 Photos" />
49+
<JSChileApolloProvider>
50+
<html lang="en">
51+
<head>
52+
<link rel="icon" href="/favicon.ico" />
53+
<meta property="og:type" content="website" />
54+
<meta property="og:site_name" content="https://gallery.jsconf.cl" />
55+
<meta
56+
property="og:description"
57+
content="Explora las mejores fotos de la exitosa Conferencia de JavaScript en Chile de febrero de 2023 y revive los momentos más emocionantes de este evento de tecnología de vanguardia."
58+
/>
59+
<meta property="og:title" content="JSConf Chile 2023 Photos" />
60+
<meta name="twitter:card" content="summary_large_image" />
61+
<meta name="twitter:title" content="JSConf Chile 2023 Photos" />
6062

61-
<meta
62-
name="twitter:description"
63-
content="Revive la JSConf Chile 2023!"
64-
/>
65-
<link rel="preconnect" href="https://fonts.googleapis.com" />
66-
<link rel="preconnect" href="https://fonts.gstatic.com" />
67-
<link
68-
href="https://fonts.googleapis.com/css2?family=Koulen&display=swap"
69-
rel="stylesheet"
70-
/>
71-
</head>
72-
<body className="dark antialiased h-[100dvh] w-[100dvw] flex flex-col overflow-hidden">
73-
<Nav />
74-
<div className="h-full overflow-auto relative">
75-
{children}
76-
<Footer />
77-
</div>
78-
<Toaster />
79-
</body>
80-
</html>
63+
<meta
64+
name="twitter:description"
65+
content="Revive la JSConf Chile 2023!"
66+
/>
67+
<link rel="preconnect" href="https://fonts.googleapis.com" />
68+
<link rel="preconnect" href="https://fonts.gstatic.com" />
69+
<link
70+
href="https://fonts.googleapis.com/css2?family=Koulen&display=swap"
71+
rel="stylesheet"
72+
/>
73+
</head>
74+
<body className="dark antialiased h-[100dvh] w-[100dvw] flex flex-col overflow-hidden">
75+
<Nav />
76+
<div className="h-full overflow-auto relative">
77+
{children}
78+
<Footer />
79+
</div>
80+
<Toaster />
81+
</body>
82+
</html>
83+
</JSChileApolloProvider>
8184
</Clerk>
8285
);
8386
}

src/components/ApolloProvider.tsx

Lines changed: 37 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,37 @@
1+
"use client";
2+
import { ApolloClient, ApolloProvider, InMemoryCache } from "@apollo/client";
3+
import { useEffect, useState } from "react";
4+
import { useRouter } from "next/navigation";
5+
import { useAuth } from "@clerk/clerk-react";
6+
7+
const useGetClient = (token: string) => {
8+
return new ApolloClient({
9+
uri: process.env.NEXT_PUBLIC_JSCL_API_URL,
10+
cache: new InMemoryCache(),
11+
headers: {
12+
authorization: `Bearer ${token}`,
13+
},
14+
});
15+
};
16+
17+
export const JSChileApolloProvider = ({ children }) => {
18+
const { getToken } = useAuth();
19+
const [token, setToken] = useState("");
20+
const client = useGetClient(token);
21+
useEffect(() => {
22+
const start = async () => {
23+
const token = await getToken({
24+
template: "API_AUTH",
25+
});
26+
if (!token) {
27+
return;
28+
}
29+
setToken(token);
30+
};
31+
start().catch((e) => {
32+
console.error(e);
33+
});
34+
}, []);
35+
36+
return <ApolloProvider client={client}>{children}</ApolloProvider>;
37+
};

src/components/Nav/AuthBlock.tsx

Lines changed: 6 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -7,7 +7,7 @@ import {
77
} from "@clerk/clerk-react";
88
import { User2 } from "lucide-react";
99
import { usePathname } from "next/navigation";
10-
import React from "react";
10+
import React, { Suspense } from "react";
1111
import { Button } from "../ui/button";
1212
import {
1313
DropdownMenu,
@@ -18,13 +18,13 @@ import {
1818
DropdownMenuSeparator,
1919
DropdownMenuTrigger,
2020
} from "../ui/dropdown-menu";
21-
import Link from "next/link";
21+
import { ImportImagesLink } from "./ImportImagesLink";
2222

2323
export const AuthBlock = () => {
2424
const pathname = usePathname();
2525

2626
return (
27-
<div>
27+
<div className="w-10">
2828
<SignedIn>
2929
<DropdownMenu>
3030
<DropdownMenuTrigger>
@@ -36,11 +36,9 @@ export const AuthBlock = () => {
3636
<DropdownMenuLabel>Mi Cuenta</DropdownMenuLabel>
3737
<DropdownMenuSeparator />
3838
<DropdownMenuGroup>
39-
<Link href={"/import"} prefetch>
40-
<DropdownMenuItem className="cursor-pointer">
41-
Importar Imágenes
42-
</DropdownMenuItem>
43-
</Link>
39+
<Suspense fallback={null}>
40+
<ImportImagesLink />
41+
</Suspense>
4442
<SignOutButton>
4543
<DropdownMenuItem className="cursor-pointer">
4644
Salir
Lines changed: 20 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,20 @@
1+
"use client";
2+
3+
import React from "react";
4+
import { DropdownMenuItem } from "../ui/dropdown-menu";
5+
import Link from "next/link";
6+
import { useIsSuperAdminSuspenseQuery } from "../../gql/jschileAPI";
7+
8+
export const ImportImagesLink = () => {
9+
const isSuperAdminQuery = useIsSuperAdminSuspenseQuery();
10+
if (!isSuperAdminQuery.data.me.isSuperAdmin) {
11+
return;
12+
}
13+
return (
14+
<Link href={"/import"} prefetch>
15+
<DropdownMenuItem className="cursor-pointer">
16+
Importar Imágenes
17+
</DropdownMenuItem>
18+
</Link>
19+
);
20+
};

src/features/import/importer.tsx

Lines changed: 0 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -46,8 +46,6 @@ export const Importer = ({
4646
}: {
4747
communityEvents: AllEventsQuery["allEventInstance"];
4848
}) => {
49-
const isSuperAdminQuery = useIsSuperAdminSuspenseQuery();
50-
5149
const [hiddenToken, setHiddenToken] = useState("");
5250
const [token, setToken] = useState("");
5351
const [defaultAlbums, setDefaultAlbums] = useState<

src/features/import/index.tsx

Lines changed: 29 additions & 43 deletions
Original file line numberDiff line numberDiff line change
@@ -1,59 +1,45 @@
11
"use client";
2-
import { ApolloClient, ApolloProvider, InMemoryCache } from "@apollo/client";
32
import { Importer } from "./importer";
43
import { Suspense, useEffect, useState } from "react";
54
import { ErrorBoundary } from "./errorBoundary";
65
import { useRouter } from "next/navigation";
7-
import { useAuth } from "@clerk/clerk-react";
6+
import { SignedIn, useAuth } from "@clerk/clerk-react";
87
import { AllEventsQuery } from "../../gql/graphql";
8+
import { useIsSuperAdminSuspenseQuery } from "../../gql/jschileAPI";
99

10-
const useGetClient = (token: string) => {
11-
return new ApolloClient({
12-
uri: process.env.NEXT_PUBLIC_JSCL_API_URL,
13-
cache: new InMemoryCache(),
14-
headers: {
15-
authorization: `Bearer ${token}`,
16-
},
17-
});
18-
};
19-
export const Import = ({
10+
const ImportImpl = ({
2011
communityEvents,
2112
}: {
2213
communityEvents: AllEventsQuery["allEventInstance"];
2314
}) => {
24-
const { getToken } = useAuth();
25-
const [token, setToken] = useState("");
2615
const router = useRouter();
27-
const client = useGetClient(token);
28-
useEffect(() => {
29-
const start = async () => {
30-
const token = await getToken({
31-
template: "API_AUTH",
32-
});
33-
if (!token) {
34-
return;
35-
}
36-
setToken(token);
37-
};
38-
start().catch((e) => {
39-
console.error(e);
40-
});
41-
}, []);
42-
43-
if (!token) {
44-
return;
16+
const superAdminQuery = useIsSuperAdminSuspenseQuery();
17+
const superAdmin = superAdminQuery.data.me.isSuperAdmin;
18+
if (!superAdmin) {
19+
router.push("/");
20+
return null;
4521
}
22+
23+
return (
24+
<Suspense fallback={<div>Loading...</div>}>
25+
<ErrorBoundary
26+
onError={() => {
27+
router.push("/", {});
28+
}}
29+
>
30+
<Importer communityEvents={communityEvents} />
31+
</ErrorBoundary>
32+
</Suspense>
33+
);
34+
};
35+
export const Import = ({
36+
communityEvents,
37+
}: {
38+
communityEvents: AllEventsQuery["allEventInstance"];
39+
}) => {
4640
return (
47-
<ApolloProvider client={client}>
48-
<Suspense fallback={<div>Loading...</div>}>
49-
<ErrorBoundary
50-
onError={() => {
51-
router.push("/", {});
52-
}}
53-
>
54-
<Importer communityEvents={communityEvents} />
55-
</ErrorBoundary>
56-
</Suspense>
57-
</ApolloProvider>
41+
<SignedIn>
42+
<ImportImpl communityEvents={communityEvents} />
43+
</SignedIn>
5844
);
5945
};

0 commit comments

Comments
 (0)