diff --git a/components/pages/inspector/UserActions.tsx b/components/pages/inspector/UserActions.tsx
index 3cb1aa6..ed4f383 100644
--- a/components/pages/inspector/UserActions.tsx
+++ b/components/pages/inspector/UserActions.tsx
@@ -30,6 +30,7 @@ import {
unsuspendUser,
updateBotDiscoverability,
updateUserBadges,
+ wipeUser,
wipeUserProfile,
} from "@/lib/actions";
import { useRef, useState } from "react";
@@ -264,6 +265,51 @@ export function UserActions({ user, bot }: { user: User; bot?: Bot }) {
+
+
+
+
+
+
+
+ Are you sure you want to wipe this user's messages?
+
+
+ All messages sent by this user will be deleted immediately.
+
+
+ This action is irreversible and{" "}
+ will not publish any events!
+
+
+
+
+ Cancel
+
+ wipeUser(user._id, 0, true)
+ .then(() => {
+ setUserDraft((user) => ({ ...user, flags: 4 }));
+ toast({ title: "Wiped user's messages" });
+ })
+ .catch((err) =>
+ toast({
+ title: "Failed to wipe user's messages!",
+ description: String(err),
+ variant: "destructive",
+ })
+ )
+ }
+ >
+ Ban
+
+
+
+
+
@@ -424,29 +470,37 @@ export function UserActions({ user, bot }: { user: User; bot?: Bot }) {
-
+
Reset token
- Re-roll this bot's authentication token. This will not disconnect active connections.
+ Re-roll this bot's authentication token. This will
+ not disconnect active connections.
Cancel
resetBotToken(user._id)
- .then(() => toast({
- title: "Reset bot token",
- }))
- .catch((e) => toast({
- title: "Failed to reset token",
- description: String(e),
- variant: "destructive",
- }))
+ onClick={() =>
+ resetBotToken(user._id)
+ .then(() =>
+ toast({
+ title: "Reset bot token",
+ })
+ )
+ .catch((e) =>
+ toast({
+ title: "Failed to reset token",
+ description: String(e),
+ variant: "destructive",
+ })
+ )
}
>
Reset
@@ -457,18 +511,16 @@ export function UserActions({ user, bot }: { user: User; bot?: Bot }) {
-
+
Transfer bot
-
- Transfer this bot to a new owner.
-
-
+ Transfer this bot to a new owner.
+
setTransferResetToken(!!e)}
@@ -481,19 +533,28 @@ export function UserActions({ user, bot }: { user: User; bot?: Bot }) {
Cancel
transferBot(user._id, transferTarget!._id, transferResetToken)
- .then(() => toast({
- title: "Reset bot token",
- }))
- .catch((e) => toast({
- title: "Failed to reset token",
- description: String(e),
- variant: "destructive",
- }))
- .finally(() => {
- setTransferResetToken(true);
- setTransferTarget(null);
- })
+ onClick={() =>
+ transferBot(
+ user._id,
+ transferTarget!._id,
+ transferResetToken
+ )
+ .then(() =>
+ toast({
+ title: "Reset bot token",
+ })
+ )
+ .catch((e) =>
+ toast({
+ title: "Failed to reset token",
+ description: String(e),
+ variant: "destructive",
+ })
+ )
+ .finally(() => {
+ setTransferResetToken(true);
+ setTransferTarget(null);
+ })
}
>
Transfer
diff --git a/lib/actions.ts b/lib/actions.ts
index 05be383..8da25cb 100644
--- a/lib/actions.ts
+++ b/lib/actions.ts
@@ -446,15 +446,21 @@ export async function updateUserBadges(userId: string, badges: number) {
}
}
-export async function wipeUser(userId: string, flags = 4) {
+export async function wipeUser(
+ userId: string,
+ flags = 4,
+ onlyMessages = false
+) {
if (RESTRICT_ACCESS_LIST.includes(userId)) throw "restricted access";
await checkPermission("users/action/wipe", userId, { flags });
- const user = await mongo()
- .db("revolt")
- .collection("users")
- .findOne({ _id: userId });
+ const user = onlyMessages
+ ? null
+ : await mongo()
+ .db("revolt")
+ .collection("users")
+ .findOne({ _id: userId });
const messages = await mongo()
.db("revolt")
@@ -462,24 +468,28 @@ export async function wipeUser(userId: string, flags = 4) {
.find({ author: userId }, { sort: { _id: -1 } })
.toArray();
- const dms = await mongo()
- .db("revolt")
- .collection("channels")
- .find({
- channel_type: "DirectMessage",
- recipients: userId,
- })
- .toArray();
+ const dms = onlyMessages
+ ? null
+ : await mongo()
+ .db("revolt")
+ .collection("channels")
+ .find({
+ channel_type: "DirectMessage",
+ recipients: userId,
+ })
+ .toArray();
- const memberships = await mongo()
- .db("revolt")
- .collection<{ _id: { user: string; server: string } }>("server_members")
- .find({ "_id.user": userId })
- .toArray();
+ const memberships = onlyMessages
+ ? null
+ : await mongo()
+ .db("revolt")
+ .collection<{ _id: { user: string; server: string } }>("server_members")
+ .find({ "_id.user": userId })
+ .toArray();
// retrieve messages, dm channels, relationships, server memberships
const backup = {
- _event: "wipe",
+ _event: onlyMessages ? "messages" : "wipe",
user,
messages,
dms,
@@ -499,12 +509,14 @@ export async function wipeUser(userId: string, flags = 4) {
.filter((attachment) => attachment)
.map((attachment) => attachment!._id);
- if (backup.user?.avatar) {
- attachmentIds.push(backup.user.avatar._id);
- }
+ if (!onlyMessages) {
+ if (backup.user?.avatar) {
+ attachmentIds.push(backup.user.avatar._id);
+ }
- if (backup.user?.profile?.background) {
- attachmentIds.push(backup.user.profile.background._id);
+ if (backup.user?.profile?.background) {
+ attachmentIds.push(backup.user.profile.background._id);
+ }
}
if (attachmentIds.length) {
@@ -527,44 +539,46 @@ export async function wipeUser(userId: string, flags = 4) {
author: userId,
});
- // delete server memberships
- await mongo().db("revolt").collection("server_members").deleteMany({
- "_id.user": userId,
- });
-
- // disable account
- await disableAccount(userId);
-
- // clear user profile
- await mongo()
- .db("revolt")
- .collection("users")
- .updateOne(
- {
- _id: userId,
- },
- {
- $set: {
- flags,
- },
- $unset: {
- avatar: 1,
- profile: 1,
- status: 1,
- },
- }
- );
-
- // broadcast wipe event
- for (const topic of [
- ...backup.dms.map((x) => x._id),
- ...backup.memberships.map((x) => x._id.server),
- ]) {
- await publishMessage(topic, {
- type: "UserPlatformWipe",
- user_id: userId,
- flags,
+ if (!onlyMessages) {
+ // delete server memberships
+ await mongo().db("revolt").collection("server_members").deleteMany({
+ "_id.user": userId,
});
+
+ // disable account
+ await disableAccount(userId);
+
+ // clear user profile
+ await mongo()
+ .db("revolt")
+ .collection("users")
+ .updateOne(
+ {
+ _id: userId,
+ },
+ {
+ $set: {
+ flags,
+ },
+ $unset: {
+ avatar: 1,
+ profile: 1,
+ status: 1,
+ },
+ }
+ );
+
+ // broadcast wipe event
+ for (const topic of [
+ ...backup.dms!.map((x) => x._id),
+ ...backup.memberships!.map((x) => x._id.server),
+ ]) {
+ await publishMessage(topic, {
+ type: "UserPlatformWipe",
+ user_id: userId,
+ flags,
+ });
+ }
}
}