From 7a0bfa2d68b720ec6593a659b6851c0786afece3 Mon Sep 17 00:00:00 2001 From: notmd <33456881+notmd@users.noreply.github.com> Date: Fri, 10 Feb 2023 16:18:48 +0700 Subject: [PATCH] add moderator role (#1419) --- website/.env | 1 + website/src/components/AdminArea.tsx | 5 +++- website/src/components/Header/UserMenu.tsx | 15 +++++++++--- .../LeaderboardTable/LeaderboardTable.tsx | 10 ++++---- .../Messages/MessageEmojiButton.tsx | 6 ++--- .../components/Messages/MessageTableEntry.tsx | 6 ++--- website/src/components/RoleSelect.tsx | 2 +- website/src/hooks/auth/useHasAnyRole.ts | 8 +++++++ website/src/lib/auth.ts | 14 +++++++++++ .../pages/api/admin/delete_message/[id].ts | 4 ++-- website/src/pages/api/admin/parameters.ts | 10 ++++++-- website/src/pages/api/admin/status.ts | 4 ++-- website/src/pages/api/admin/stop_tree/[id].ts | 4 ++-- website/src/pages/api/admin/trollboard.ts | 4 ++-- website/src/pages/api/admin/user_messages.ts | 4 ++-- website/src/pages/api/admin/users.ts | 4 ++-- website/src/pages/api/auth/[...nextauth].ts | 24 +++++++++++++++++-- website/types/env.d.ts | 2 ++ 18 files changed, 95 insertions(+), 32 deletions(-) create mode 100644 website/src/hooks/auth/useHasAnyRole.ts diff --git a/website/.env b/website/.env index 50ecb498..6c95c9a5 100644 --- a/website/.env +++ b/website/.env @@ -1,4 +1,5 @@ ADMIN_USERS = "credentials:admin,discord:root,email:admin@example.com" +MODERATOR_USERS = "credentials:mod,discord:mod,email:mod@example.com" # The database created by running the jobs in /scripts/frontend-development/docker-compose.yaml DATABASE_URL=postgres://postgres:postgres@localhost:5433/oasst_web diff --git a/website/src/components/AdminArea.tsx b/website/src/components/AdminArea.tsx index 8e6d1229..6bc7a919 100644 --- a/website/src/components/AdminArea.tsx +++ b/website/src/components/AdminArea.tsx @@ -10,9 +10,12 @@ export const AdminArea = ({ children }: { children: ReactNode }) => { if (status === "loading") { return; } - if (session?.user.role === "admin") { + const role = session?.user.role; + + if (role === "admin" || role === "moderator") { return; } + router.push("/"); }, [router, session, status]); return
{status === "loading" ? "loading..." : children}
; diff --git a/website/src/components/Header/UserMenu.tsx b/website/src/components/Header/UserMenu.tsx index cad2dbe8..aba03f05 100644 --- a/website/src/components/Header/UserMenu.tsx +++ b/website/src/components/Header/UserMenu.tsx @@ -1,5 +1,6 @@ import { Avatar, + Badge, Box, Link, Menu, @@ -16,6 +17,7 @@ import NextLink from "next/link"; import { signOut, useSession } from "next-auth/react"; import { useTranslation } from "next-i18next"; import React, { ElementType, useCallback } from "react"; +import { useHasAnyRole } from "src/hooks/auth/useHasAnyRole"; interface MenuOption { name: string; @@ -31,7 +33,7 @@ export function UserMenu() { signOut({ callbackUrl: "/" }); }, []); const { data: session, status } = useSession(); - + const isAdminOrMod = useHasAnyRole(["admin", "moderator"]); if (!session || status !== "authenticated") { return null; } @@ -56,7 +58,7 @@ export function UserMenu() { }, ]; - if (session.user.role === "admin") { + if (isAdminOrMod) { options.unshift({ name: t("admin_dashboard"), href: "/admin", @@ -77,7 +79,14 @@ export function UserMenu() { - {session.user.name} + + {session.user.name} + {isAdminOrMod ? ( + + {session.user.role} + + ) : null} + {/* 3,200 */} diff --git a/website/src/components/LeaderboardTable/LeaderboardTable.tsx b/website/src/components/LeaderboardTable/LeaderboardTable.tsx index fc3ae099..95cbd376 100644 --- a/website/src/components/LeaderboardTable/LeaderboardTable.tsx +++ b/website/src/components/LeaderboardTable/LeaderboardTable.tsx @@ -4,7 +4,7 @@ import { MoreHorizontal } from "lucide-react"; import NextLink from "next/link"; import { useTranslation } from "next-i18next"; import React, { useMemo } from "react"; -import { useHasRole } from "src/hooks/auth/useHasRole"; +import { useHasAnyRole } from "src/hooks/auth/useHasAnyRole"; import { LeaderboardEntity, LeaderboardReply, LeaderboardTimeFrame } from "src/types/Leaderboard"; import { DataTable, DataTableColumnDef } from "../DataTable/DataTable"; @@ -41,7 +41,7 @@ export const LeaderboardTable = ({ `/api/leaderboard?time_frame=${timeFrame}&limit=${limit}&includeUserStats=${!hideCurrentUserRanking}` ); - const isAdmin = useHasRole("admin"); + const isAdminOrMod = useHasAnyRole(["admin", "moderator"]); const columns: DataTableColumnDef[] = useMemo( () => [ @@ -51,7 +51,7 @@ export const LeaderboardTable = ({ cell: (ctx) => ctx.row.original.isSpaceRow ? ( - ) : isAdmin ? ( + ) : isAdminOrMod ? ( jsonExpandRowModel.renderCell(ctx) ) : ( ctx.getValue() @@ -62,7 +62,7 @@ export const LeaderboardTable = ({ columnHelper.accessor("display_name", { header: t("user"), cell: ({ getValue, row }) => - isAdmin ? ( + isAdminOrMod ? ( {getValue()} @@ -83,7 +83,7 @@ export const LeaderboardTable = ({ header: t("label"), }), ], - [isAdmin, t] + [isAdminOrMod, t] ); const { diff --git a/website/src/components/Messages/MessageEmojiButton.tsx b/website/src/components/Messages/MessageEmojiButton.tsx index e2cfd569..2c0c2442 100644 --- a/website/src/components/Messages/MessageEmojiButton.tsx +++ b/website/src/components/Messages/MessageEmojiButton.tsx @@ -1,5 +1,5 @@ import { Button, ButtonProps } from "@chakra-ui/react"; -import { useHasRole } from "src/hooks/auth/useHasRole"; +import { useHasAnyRole } from "src/hooks/auth/useHasAnyRole"; import { MessageEmoji } from "src/types/Conversation"; import { emojiIcons } from "src/types/Emoji"; @@ -23,12 +23,12 @@ export const MessageEmojiButton = ({ sx, }: MessageEmojiButtonProps) => { const EmojiIcon = emojiIcons.get(emoji.name); - const isAdmin = useHasRole("admin"); + const isAdminOrMod = useHasAnyRole(["admin", "moderator"]); if (!EmojiIcon) return null; const isDisabled = !!(userIsAuthor ? true : disabled); - const showCount = (emoji.count > 0 && userReacted) || userIsAuthor || isAdmin; + const showCount = (emoji.count > 0 && userReacted) || userIsAuthor || isAdminOrMod; return (