diff --git a/website/src/lib/auth.ts b/website/src/lib/auth.ts new file mode 100644 index 00000000..1a0387f9 --- /dev/null +++ b/website/src/lib/auth.ts @@ -0,0 +1,19 @@ +import type { NextApiRequest, NextApiResponse } from "next"; +import { getToken } from "next-auth/jwt"; + +/** + * Wraps any API Route handler and verifies that the user has the appropriate + * role before running the handler. Returns a 403 otherwise. + */ +const withRole = (role: string, handler: (arg0: NextApiRequest, arg1: NextApiResponse) => any) => { + return async (req: NextApiRequest, res: NextApiResponse) => { + const token = await getToken({ req }); + if (!token || token.role !== role) { + res.status(403).end(); + return; + } + return handler(req, res); + }; +}; + +export default withRole; diff --git a/website/src/pages/admin/manage_user/[id].tsx b/website/src/pages/admin/manage_user/[id].tsx index 1d7cc015..ead55224 100644 --- a/website/src/pages/admin/manage_user/[id].tsx +++ b/website/src/pages/admin/manage_user/[id].tsx @@ -52,7 +52,7 @@ const ManageUser = ({ user }) => { return ( <> - Open Assistant + Manage Users - Open Assistant { - const token = await getToken({ req }); - - // Return nothing if the user isn't registered or if the user isn't an admin. - if (!token || token.role !== "admin") { - res.status(403).end(); - return; - } - +const handler = withRole("admin", async (req, res) => { const { id, role } = JSON.parse(req.body); + await prisma.user.update({ where: { id, @@ -24,6 +18,6 @@ const handler = async (req, res) => { }); res.status(200).end(); -}; +}); export default handler; diff --git a/website/src/pages/api/admin/users.ts b/website/src/pages/api/admin/users.ts index 186bb253..1490522a 100644 --- a/website/src/pages/api/admin/users.ts +++ b/website/src/pages/api/admin/users.ts @@ -1,21 +1,14 @@ import { getToken } from "next-auth/jwt"; -import client from "src/lib/prismadb"; +import withRole from "src/lib/auth"; +import prisma from "src/lib/prismadb"; /** * Returns a list of user results from the database when the requesting user is * a logged in admin. */ -const handler = async (req, res) => { - const token = await getToken({ req }); - - // Return nothing if the user isn't registered or if the user isn't an admin. - if (!token || token.role !== "admin") { - res.status(403).end(); - return; - } - +const handler = withRole("admin", async (req, res) => { // Fetch 20 users. - const users = await client.user.findMany({ + const users = await prisma.user.findMany({ select: { id: true, role: true, @@ -26,6 +19,6 @@ const handler = async (req, res) => { }); res.status(200).json(users); -}; +}); export default handler;