NODEDC_LAUNCHER/src/shared/api/inviteApi.ts

73 lines
2.0 KiB
TypeScript

import type { ClientMembership, LauncherUser } from "../../entities/user/types";
import type { Client } from "../../entities/client/types";
import type { Invite } from "../../entities/invite/types";
import type { LauncherData } from "./mockApi";
export interface PublicInviteResponse {
invite: Pick<Invite, "id" | "role" | "expiresAt" | "status">;
client: Pick<Client, "id" | "name" | "status">;
}
export interface AcceptInviteResponse {
invite: Invite;
client: Client;
user: LauncherUser;
membership: ClientMembership;
data: LauncherData;
}
export interface RegisterInviteCommand {
email: string;
name: string;
password: string;
}
export interface RegisterInviteResponse extends AcceptInviteResponse {
loginUrl: string;
}
export async function fetchPublicInvite(token: string): Promise<PublicInviteResponse> {
return requestJson<PublicInviteResponse>(`/api/invites/${encodeURIComponent(token)}`);
}
export async function registerInvite(token: string, command: RegisterInviteCommand): Promise<RegisterInviteResponse> {
return requestJson<RegisterInviteResponse>(`/api/invites/${encodeURIComponent(token)}/register`, {
method: "POST",
body: JSON.stringify(command),
});
}
export async function acceptInvite(token: string): Promise<AcceptInviteResponse> {
return requestJson<AcceptInviteResponse>(`/api/invites/${encodeURIComponent(token)}/accept`, {
method: "POST",
});
}
async function requestJson<T>(url: string, init: RequestInit = {}): Promise<T> {
const headers = new Headers(init.headers);
if (!headers.has("Content-Type")) {
headers.set("Content-Type", "application/json");
}
const response = await fetch(url, {
...init,
headers,
});
if (!response.ok) {
throw new Error(await readErrorMessage(response));
}
return (await response.json()) as T;
}
async function readErrorMessage(response: Response) {
try {
const payload = (await response.json()) as { error?: string };
return payload.error ?? response.statusText;
} catch {
return response.statusText;
}
}