diff --git a/website/src/lib/oasst_api_client.ts b/website/src/lib/oasst_api_client.ts index d48a987c..de58ae71 100644 --- a/website/src/lib/oasst_api_client.ts +++ b/website/src/lib/oasst_api_client.ts @@ -1,7 +1,6 @@ -import { JWT } from "next-auth/jwt"; import type { Message } from "src/types/Conversation"; import { LeaderboardReply, LeaderboardTimeFrame } from "src/types/Leaderboard"; -import type { BackendUser } from "src/types/Users"; +import type { BackendUser, BackendUserCore } from "src/types/Users"; export class OasstError { message: string; @@ -108,14 +107,10 @@ export class OasstApiClient { // TODO return a strongly typed Task? // This method is used to store a task in RegisteredTask.task. // This is a raw Json type, so we can't use it to strongly type the task. - async fetchTask(taskType: string, userToken: JWT): Promise { + async fetchTask(taskType: string, user: BackendUserCore): Promise { return this.post("/api/v1/tasks/", { type: taskType, - user: { - id: userToken.sub, - display_name: userToken.name, - auth_method: "local", - }, + user, }); } @@ -140,15 +135,11 @@ export class OasstApiClient { messageId: string, userMessageId: string, content: object, - userToken: JWT + user: BackendUserCore ): Promise { return this.post("/api/v1/tasks/interaction", { type: updateType, - user: { - id: userToken.sub, - display_name: userToken.name, - auth_method: "local", - }, + user, task_id: taskId, message_id: messageId, user_message_id: userMessageId, diff --git a/website/src/lib/users.ts b/website/src/lib/users.ts new file mode 100644 index 00000000..2aa8c708 --- /dev/null +++ b/website/src/lib/users.ts @@ -0,0 +1,38 @@ +import prisma from "src/lib/prismadb"; +import type { BackendUserCore } from "src/types/Users"; + +/** + * Returns a `BackendUserCore` that can be used for interacting with the Backend service. + * + * @param {string} id The user's web auth id. + * + * @return {BackendUserCore} The most specific auth type and id for the user. + */ +const getBackendUserCore = async (id: string) => { + const user = await prisma.user.findUnique({ + where: { id }, + select: { + id: true, + name: true, + accounts: true, + }, + }); + + // If there are no linked accounts, just use what we have locally. + if (user.accounts.length === 0) { + return { + id: user.id, + display_name: user.name, + auth_method: "local", + } as BackendUserCore; + } + + // Otherwise, use the first linked account that the user created. + return { + id: user.accounts[0].providerAccountId, + display_name: user.name, + auth_method: user.accounts[0].provider, + } as BackendUserCore; +}; + +export { getBackendUserCore }; diff --git a/website/src/pages/api/new_task/[task_type].ts b/website/src/pages/api/new_task/[task_type].ts index e77c5eb2..c8255b18 100644 --- a/website/src/pages/api/new_task/[task_type].ts +++ b/website/src/pages/api/new_task/[task_type].ts @@ -1,6 +1,7 @@ import { withoutRole } from "src/lib/auth"; import { oasstApiClient } from "src/lib/oasst_api_client"; import prisma from "src/lib/prismadb"; +import { getBackendUserCore } from "src/lib/users"; /** * Returns a new task created from the Task Backend. We do a few things here: @@ -14,9 +15,10 @@ const handler = withoutRole("banned", async (req, res, token) => { // Fetch the new task. const { task_type } = req.query; + const user = await getBackendUserCore(token.sub); let task; try { - task = await oasstApiClient.fetchTask(task_type as string, token); + task = await oasstApiClient.fetchTask(task_type as string, user); } catch (err) { console.error(err); res.status(500).json(err); diff --git a/website/src/pages/api/update_task.ts b/website/src/pages/api/update_task.ts index 02982daa..b9de5c50 100644 --- a/website/src/pages/api/update_task.ts +++ b/website/src/pages/api/update_task.ts @@ -2,6 +2,8 @@ import { Prisma } from "@prisma/client"; import { withoutRole } from "src/lib/auth"; import { oasstApiClient } from "src/lib/oasst_api_client"; import prisma from "src/lib/prismadb"; +import { getBackendUserCore } from "src/lib/users"; +import type { BackendUserCore } from "src/types/Users"; /** * Stores the task interaction with the Task Backend and then returns the next task generated. @@ -39,9 +41,10 @@ const handler = withoutRole("banned", async (req, res, token) => { }, }); + const user = await getBackendUserCore(token.sub); let newTask; try { - newTask = await oasstApiClient.interactTask(update_type, taskId, frontendId, interaction.id, content, token); + newTask = await oasstApiClient.interactTask(update_type, taskId, frontendId, interaction.id, content, user); } catch (err) { console.error(JSON.stringify(err)); return res.status(500).json(err); diff --git a/website/src/types/Users.ts b/website/src/types/Users.ts index eeb1903a..39d2a663 100644 --- a/website/src/types/Users.ts +++ b/website/src/types/Users.ts @@ -1,7 +1,4 @@ -/** - * Reports the Backend's knowledge of a user. - */ -export interface BackendUser { +export interface BackendUserCore { /** * The user's unique ID according to the `auth_method`. */ @@ -18,7 +15,12 @@ export interface BackendUser { * - local */ auth_method: string; +} +/** + * Reports the Backend's knowledge of a user. + */ +export interface BackendUser extends BackendUserCore { /** * The backend's UUID for this user. */