owltide/server/utils/session.ts

74 lines
2.3 KiB
TypeScript
Raw Normal View History

import type { H3Event } from "h3";
import { nextSessionId, readSessions, readSubscriptions, writeSessions, writeSubscriptions } from "~/server/database";
import { Session } from "~/shared/types/account";
const oneYearSeconds = 365 * 24 * 60 * 60;
async function removeSessionSubscription(sessionId: number) {
const subscriptions = await readSubscriptions();
const index = subscriptions.findIndex(subscription => subscription.sessionId === sessionId);
if (index !== -1) {
subscriptions.splice(index, 1);
await writeSubscriptions(subscriptions);
}
}
async function clearAccountSessionInternal(event: H3Event, sessions: Session[]) {
const existingSessionCookie = await getSignedCookie(event, "session");
if (existingSessionCookie) {
const sessionId = parseInt(existingSessionCookie, 10);
const sessionIndex = sessions.findIndex(session => session.id === sessionId);
if (sessionIndex !== -1) {
sessions.splice(sessionIndex, 1);
await removeSessionSubscription(sessionId);
return true;
}
}
return false;
}
export async function clearAccountSession(event: H3Event) {
const sessions = await readSessions();
if (await clearAccountSessionInternal(event, sessions)) {
await writeSessions(sessions);
}
deleteCookie(event, "session");
}
export async function setAccountSession(event: H3Event, accountId: number) {
const sessions = await readSessions();
await clearAccountSessionInternal(event, sessions);
const newSession: Session = {
accountId,
id: await nextSessionId(),
};
sessions.push(newSession);
await writeSessions(sessions);
await setSignedCookie(event, "session", String(newSession.id), oneYearSeconds)
}
export async function refreshAccountSession(event: H3Event, session: Session) {
await setSignedCookie(event, "session", String(session.id), oneYearSeconds)
}
export async function getAccountSession(event: H3Event) {
const sessionCookie = await getSignedCookie(event, "session");
if (sessionCookie) {
const sessionId = parseInt(sessionCookie, 10);
const sessions = await readSessions();
return sessions.find(session => session.id === sessionId);
}
}
export async function requireAccountSession(event: H3Event) {
const session = await getAccountSession(event);
if (!session)
throw createError({
status: 401,
message: "Account session required",
});
return session;
}