boredgame/src/lib/server/api/controllers/oauth.controller.ts

55 lines
1.7 KiB
TypeScript
Raw Normal View History

2024-09-16 16:07:22 +00:00
import 'reflect-metadata'
import { Controller } from '$lib/server/api/common/types/controller'
import { LuciaService } from '$lib/server/api/services/lucia.service'
import { OAuthService } from '$lib/server/api/services/oauth.service'
import { github } from '$lib/server/auth'
import { OAuth2RequestError } from 'arctic'
import { getCookie } from 'hono/cookie'
import { inject, injectable } from 'tsyringe'
@injectable()
export class OAuthController extends Controller {
constructor(
@inject(LuciaService) private luciaService: LuciaService,
@inject(OAuthService) private readonly oauthService: OAuthService) {
super()
}
routes() {
return this.controller
.get('/github', async (c) => {
try {
const code = c.req.query('code')?.toString() ?? null
const state = c.req.query('state')?.toString() ?? null
const storedState = getCookie(c).github_oauth_state ?? null
if (!code || !state || !storedState || state !== storedState) {
return c.body(null, 400)
}
const tokens = await github.validateAuthorizationCode(code)
const githubUserResponse = await fetch("https://api.github.com/user", {
headers: {
Authorization: `Bearer ${tokens.accessToken}`
}
});
const githubUser: GitHubUser = await githubUserResponse.json();
const token = await this.oauthService.handleOAuthUser(githubUser.id, githubUser.login, 'github')
return c.json({ token })
} catch (error) {
// the specific error message depends on the provider
if (error instanceof OAuth2RequestError) {
// invalid code
return c.body(null, 400)
}
return c.body(null, 500)
}
})
}
}
interface GitHubUser {
id: number;
login: string;
}