diff --git a/app/api/bsky/thread/route.ts b/app/api/bsky/thread/route.ts index fafbcf42..4247b49f 100644 --- a/app/api/bsky/thread/route.ts +++ b/app/api/bsky/thread/route.ts @@ -1,9 +1,40 @@ import { Agent, lexToJson } from "@atproto/api"; import { ThreadViewPost } from "@atproto/api/dist/client/types/app/bsky/feed/defs"; +import { cookies } from "next/headers"; import { NextRequest } from "next/server"; +import { createOauthClient } from "src/atproto-oauth"; +import { supabaseServerClient } from "supabase/serverClient"; export const runtime = "nodejs"; +async function getAuthenticatedAgent(): Promise { + try { + const cookieStore = await cookies(); + const authToken = + cookieStore.get("auth_token")?.value || + cookieStore.get("external_auth_token")?.value; + + if (!authToken || authToken === "null") return null; + + const { data } = await supabaseServerClient + .from("email_auth_tokens") + .select("identities(atp_did)") + .eq("id", authToken) + .eq("confirmed", true) + .single(); + + const did = data?.identities?.atp_did; + if (!did) return null; + + const oauthClient = await createOauthClient(); + const session = await oauthClient.restore(did); + return new Agent(session); + } catch (error) { + console.error("Failed to get authenticated agent:", error); + return null; + } +} + export async function GET(req: NextRequest) { try { const searchParams = req.nextUrl.searchParams; @@ -18,10 +49,13 @@ export async function GET(req: NextRequest) { ); } - // Fetch thread from Bluesky - let agent = new Agent({ - service: "https://public.api.bsky.app", - }); + // Try to use authenticated agent if user is logged in, otherwise fall back to public API + let agent = await getAuthenticatedAgent(); + if (!agent) { + agent = new Agent({ + service: "https://public.api.bsky.app", + }); + } const response = await agent.getPostThread({ uri,