File size: 2,659 Bytes
d1007e5
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
import { redirect } from "@sveltejs/kit";
const GET = async ({ url, cookies, fetch }) => {
  const code = url.searchParams.get("code");
  const state = url.searchParams.get("state");
  const error = url.searchParams.get("error");
  const errorDescription = url.searchParams.get("error_description");
  if (error) {
    console.error("OAuth error:", error, errorDescription);
    throw redirect(303, `/login?error=${encodeURIComponent(error)}`);
  }
  if (!code) {
    console.error("No authorization code received");
    throw redirect(303, "/login?error=no_code");
  }
  const savedState = cookies.get("oauth_state");
  if (state !== savedState) {
    console.error("State mismatch - possible CSRF attack");
    throw redirect(303, "/login?error=invalid_state");
  }
  try {
    const tokenResponse = await fetch("https://huggingface.co/oauth/token", {
      method: "POST",
      headers: {
        "Content-Type": "application/json"
      },
      body: JSON.stringify({
        grant_type: "authorization_code",
        code,
        client_id: process.env.OAUTH_CLIENT_ID,
        client_secret: process.env.OAUTH_CLIENT_SECRET,
        redirect_uri: process.env.OAUTH_REDIRECT_URI || `${url.origin}/oauth/callback`
      })
    });
    if (!tokenResponse.ok) {
      const errorData = await tokenResponse.text();
      console.error("Token exchange failed:", errorData);
      throw redirect(303, "/login?error=token_exchange_failed");
    }
    const tokenData = await tokenResponse.json();
    const accessToken = tokenData.access_token;
    const userResponse = await fetch("https://huggingface.co/api/whoami-v2", {
      headers: {
        Authorization: `Bearer ${accessToken}`
      }
    });
    if (!userResponse.ok) {
      console.error("Failed to fetch user info");
      throw redirect(303, "/login?error=user_fetch_failed");
    }
    const userData = await userResponse.json();
    cookies.set("access_token", accessToken, {
      path: "/",
      httpOnly: true,
      secure: process.env.NODE_ENV === "production",
      sameSite: "lax",
      maxAge: 60 * 60 * 24 * 30
      // 30 days
    });
    cookies.set("user", JSON.stringify(userData), {
      path: "/",
      httpOnly: true,
      secure: process.env.NODE_ENV === "production",
      sameSite: "lax",
      maxAge: 60 * 60 * 24 * 30
      // 30 days
    });
    cookies.delete("oauth_state", { path: "/" });
    throw redirect(303, "/");
  } catch (error2) {
    if (error2 instanceof Response) {
      throw error2;
    }
    console.error("Unexpected error during OAuth callback:", error2);
    throw redirect(303, "/login?error=unexpected_error");
  }
};
export {
  GET
};