Highly ambitious ATProtocol AppView service and sdks
1import { AtProtoClient } from "./client.ts";
2import { OAuthClient, SQLiteOAuthStorage } from "@slices/oauth";
3import { SessionStore, SQLiteAdapter, withOAuthSession } from "@slices/session";
4
5const OAUTH_CLIENT_ID = Deno.env.get("OAUTH_CLIENT_ID");
6const OAUTH_CLIENT_SECRET = Deno.env.get("OAUTH_CLIENT_SECRET");
7const OAUTH_REDIRECT_URI = Deno.env.get("OAUTH_REDIRECT_URI");
8const OAUTH_AIP_BASE_URL = Deno.env.get("OAUTH_AIP_BASE_URL");
9const API_URL = Deno.env.get("API_URL");
10export const SLICE_URI = Deno.env.get("SLICE_URI");
11export const ADMIN_DID = Deno.env.get("ADMIN_DID");
12
13if (
14 !OAUTH_CLIENT_ID ||
15 !OAUTH_CLIENT_SECRET ||
16 !OAUTH_REDIRECT_URI ||
17 !OAUTH_AIP_BASE_URL ||
18 !API_URL ||
19 !SLICE_URI
20) {
21 throw new Error(
22 "Missing OAuth configuration. Please ensure .env file contains:\n" +
23 "OAUTH_CLIENT_ID, OAUTH_CLIENT_SECRET, OAUTH_REDIRECT_URI, OAUTH_AIP_BASE_URL, API_URL, SLICE_URI"
24 );
25}
26
27const DATABASE_URL = Deno.env.get("DATABASE_URL") || "slices.db";
28
29// OAuth setup
30const oauthStorage = new SQLiteOAuthStorage(DATABASE_URL);
31const oauthConfig = {
32 clientId: OAUTH_CLIENT_ID,
33 clientSecret: OAUTH_CLIENT_SECRET,
34 authBaseUrl: OAUTH_AIP_BASE_URL,
35 redirectUri: OAUTH_REDIRECT_URI,
36 scopes: [
37 "openid",
38 "email",
39 "profile",
40 "atproto",
41 "transition:generic",
42 "account:email",
43 "blob:image/*",
44 "repo:network.slices.slice",
45 "repo:network.slices.lexicon",
46 "repo:network.slices.actor.profile",
47 "repo:network.slices.waitlist.request",
48 ],
49};
50
51// Export config and storage for creating session-scoped clients
52export { oauthConfig, oauthStorage };
53
54// Session setup (shared database)
55export const sessionStore = new SessionStore({
56 adapter: new SQLiteAdapter(DATABASE_URL),
57 cookieOptions: {
58 httpOnly: true,
59 secure: Deno.env.get("DENO_ENV") === "production",
60 sameSite: "lax",
61 path: "/",
62 },
63});
64
65// OAuth + Session integration
66export const oauthSessions = withOAuthSession(
67 sessionStore,
68 oauthConfig,
69 oauthStorage,
70 {
71 autoRefresh: true,
72 }
73);
74
75// Helper function to create session-scoped OAuth client
76export function createOAuthClient(sessionId: string): OAuthClient {
77 return new OAuthClient(oauthConfig, oauthStorage, sessionId);
78}
79
80// Helper function to create authenticated AtProto client for a session
81export function createSessionClient(sessionId: string): AtProtoClient {
82 const sessionOAuthClient = createOAuthClient(sessionId);
83 return new AtProtoClient(API_URL!, SLICE_URI!, sessionOAuthClient);
84}
85
86// Public client for unauthenticated requests
87export const publicClient = new AtProtoClient(API_URL, SLICE_URI);