[bugfix] allow local clerk to work

This commit is contained in:
2026-05-28 14:42:50 -04:00
parent 47f18348bf
commit ae0f3d6683

View File

@@ -1,7 +1,6 @@
import { clerkMiddleware, createRouteMatcher, clerkClient } from '@clerk/astro/server'; import { clerkMiddleware, createRouteMatcher, clerkClient } from '@clerk/astro/server';
import type { MiddlewareNext } from 'astro';
import 'dotenv/config'; import 'dotenv/config';
declare global { declare global {
namespace App { namespace App {
interface Locals { interface Locals {
@@ -9,19 +8,23 @@ declare global {
} }
} }
} }
const isProtectedRoute = createRouteMatcher(['/pokemon']); const isProtectedRoute = createRouteMatcher(['/pokemon']);
const isAdminRoute = createRouteMatcher(['/admin']); const isAdminRoute = createRouteMatcher(['/admin']);
const TARGET_ORG_ID = "org_3Baav9czkRLLlC7g89oJWqRRulK"; const TARGET_ORG_ID = "org_3Baav9czkRLLlC7g89oJWqRRulK";
const ADMIN_ORG_IDS = new Set([
"org_3Baav9czkRLLlC7g89oJWqRRulK",
"org_3ABdwuK3qD7Saq590ZMQWY7AvVz",
]);
export const onRequest = clerkMiddleware(async (auth, context, next) => { export const onRequest = clerkMiddleware(async (auth, context, next) => {
const { isAuthenticated, userId, redirectToSignIn, has } = auth(); const { isAuthenticated, userId, redirectToSignIn, has } = auth();
if (!isAuthenticated && isProtectedRoute(context.request)) { if (!isAuthenticated && isProtectedRoute(context.request)) {
return redirectToSignIn(); return redirectToSignIn();
} }
// ── Inventory visibility check ────────────────────────────────────────────── // ── Inventory visibility check ──────────────────────────────────────────────
// Resolves to true if the user belongs to the target org OR has the feature // Resolves to true if the user belongs to the target org OR has the feature
const canAddInventory = process.env.INVENTORY_ACCESS === 'true' || const canAddInventory = process.env.INVENTORY_ACCESS === 'true' ||
@@ -33,27 +36,38 @@ export const onRequest = clerkMiddleware(async (auth, context, next) => {
(await getUserOrgIds(context, userId)).includes(TARGET_ORG_ID) (await getUserOrgIds(context, userId)).includes(TARGET_ORG_ID)
) )
); );
// Expose the flag to your Astro pages via locals // Expose the flag to your Astro pages via locals
context.locals.canAddInventory = Boolean(canAddInventory); context.locals.canAddInventory = Boolean(canAddInventory);
// ── Admin route guard ─────────────────────────────────────────── // ── Admin route guard ───────────────────────────────────────────
if (isAdminRoute(context.request)) { if (isAdminRoute(context.request)) {
if (!isAuthenticated || !userId) { if (!isAuthenticated || !userId) {
return redirectToSignIn(); return redirectToSignIn();
} }
try { try {
const client = await clerkClient(context); const client = await clerkClient(context);
const memberships = await client.organizations.getOrganizationMembershipList({ const userOrgIds = await getUserOrgIds(context, userId);
organizationId: TARGET_ORG_ID, const matchingOrgIds = userOrgIds.filter((id) => ADMIN_ORG_IDS.has(id));
});
if (matchingOrgIds.length === 0) {
const userMembership = memberships.data.find( return new Response(null, { status: 404 });
(m) => m.publicUserData?.userId === userId }
const membershipLists = await Promise.all(
matchingOrgIds.map((orgId) =>
client.organizations.getOrganizationMembershipList({ organizationId: orgId })
)
); );
if (!userMembership || userMembership.role !== "org:admin") { const isAdmin = membershipLists.some((list) =>
list.data.some(
(m) => m.publicUserData?.userId === userId && m.role === "org:admin"
)
);
if (!isAdmin) {
return new Response(null, { status: 404 }); return new Response(null, { status: 404 });
} }
} catch (e) { } catch (e) {
@@ -61,10 +75,10 @@ export const onRequest = clerkMiddleware(async (auth, context, next) => {
return context.redirect("/"); return context.redirect("/");
} }
} }
return next(); return next();
}); });
// ── Helper: fetch all org IDs the current user belongs to ─────────────────── // ── Helper: fetch all org IDs the current user belongs to ───────────────────
async function getUserOrgIds(context: any, userId: string): Promise<string[]> { async function getUserOrgIds(context: any, userId: string): Promise<string[]> {
try { try {
@@ -75,4 +89,4 @@ async function getUserOrgIds(context: any, userId: string): Promise<string[]> {
console.error("Failed to fetch user org memberships:", e); console.error("Failed to fetch user org memberships:", e);
return []; return [];
} }
} }