import { component$ } from '@builder.io/qwik' import * as access from 'wildebeest/backend/src/access' import type { Client } from 'wildebeest/backend/src/mastodon/client' import { getClientById } from 'wildebeest/backend/src/mastodon/client' import { DocumentHead, loader$ } from '@builder.io/qwik-city' import { WildebeestLogo } from '~/components/MastodonLogo' import { Avatar } from '~/components/avatar' import { getPersonByEmail } from 'wildebeest/backend/src/activitypub/actors' import { getErrorHtml } from '~/utils/getErrorHtml/getErrorHtml' import { buildRedirect } from 'wildebeest/functions/oauth/authorize' export const clientLoader = loader$, { DATABASE: D1Database }>(async ({ platform, query, html }) => { const client_id = query.get('client_id') || '' let client: Client | null = null try { client = await getClientById(platform.DATABASE, client_id) } catch { throw html(500, getErrorHtml('An error occurred while trying to fetch the client data, please try again later')) } if (client === null) { throw new Error('client not found') } return client }) export const userLoader = loader$< Promise<{ email: string; avatar: URL; name: string; url: URL }>, { DATABASE: D1Database; domain: string } >(async ({ cookie, platform, html, request, redirect, text }) => { const jwt = cookie.get('CF_Authorization') if (jwt === null) { throw html(500, getErrorHtml('Missing Authorization')) } let payload: access.JWTPayload try { // TODO: eventually, verify the JWT with Access, however this // is not critical. payload = access.getPayload(jwt.value) } catch (err: unknown) { console.warn((err as { stack: unknown }).stack) throw html(500, getErrorHtml('Failed to validate Access JWT')) } if (!payload.email) { throw html(500, getErrorHtml("The Access JWT doesn't contain an email")) } const person = await getPersonByEmail(platform.DATABASE, payload.email) if (person === null) { const isFirstLogin = true const res = await buildRedirect(platform.DATABASE, request as Request, isFirstLogin, jwt.value) if (res.status === 302) { throw redirect(302, res.headers.get('location') || '') } else { throw text(res.status, await res.text()) } } const name = person.name const avatar = person.icon?.url const url = person.url if (!name || !avatar) { throw html(500, getErrorHtml("The person associated with the Access JWT doesn't include a name or avatar")) } return { email: payload.email, avatar, name, url } }) export default component$(() => { const client = clientLoader().value const { email, avatar, name: display_name, url } = userLoader().value return (


Signed in as:

{email}

Authorization required

{client.name} {' '} would like permission to access your account. It is a third-party application. If you do not trust it, then you should not authorize it.

Review permissions

Everything Read and write access
) }) export const head: DocumentHead = () => { return { title: 'Wildebeest Authorization required', meta: [ { name: 'description', content: 'Wildebeest Authorization required', }, ], } }