fix channel permission thing

This commit is contained in:
ITOH
2021-05-01 18:35:19 +02:00
parent 642cf58bae
commit cff1b61af5
4 changed files with 46 additions and 31 deletions
+2 -2
View File
@@ -13,8 +13,8 @@ export async function cloneChannel(channelId: string, reason?: string) {
//Check for DM channel
if (
channelToClone.type === DiscordChannelTypes.DM ||
channelToClone.type === DiscordChannelTypes.GROUP_DM
channelToClone.type === DiscordChannelTypes.Dm ||
channelToClone.type === DiscordChannelTypes.GroupDm
) {
throw new Error(Errors.CHANNEL_NOT_IN_GUILD);
}
+7 -15
View File
@@ -1,4 +1,3 @@
import { eventHandlers } from "../../bot.ts";
import { cacheHandlers } from "../../cache.ts";
import { rest } from "../../rest/rest.ts";
import { structures } from "../../structures/mod.ts";
@@ -8,11 +7,10 @@ import {
CreateGuildChannel,
DiscordCreateGuildChannel,
} from "../../types/guilds/create_guild_channel.ts";
import { PermissionStrings } from "../../types/permissions/permission_strings.ts";
import { endpoints } from "../../util/constants.ts";
import {
calculateBits,
requireBotGuildPermissions,
requireOverwritePermissions,
} from "../../util/permissions.ts";
import { camelKeysToSnakeCase } from "../../util/utils.ts";
@@ -22,18 +20,12 @@ export async function createChannel(
options?: CreateGuildChannel,
reason?: string,
) {
const requiredPerms: Set<PermissionStrings> = new Set(["MANAGE_CHANNELS"]);
options?.permissionOverwrites?.forEach((overwrite) => {
eventHandlers.debug?.(
"loop",
`Running forEach loop in create_channel file.`,
if (options?.permissionOverwrites) {
await requireOverwritePermissions(
guildId,
options.permissionOverwrites,
);
overwrite.allow.forEach(requiredPerms.add, requiredPerms);
overwrite.deny.forEach(requiredPerms.add, requiredPerms);
});
await requireBotGuildPermissions(guildId, [...requiredPerms]);
}
// BITRATES ARE IN THOUSANDS SO IF USER PROVIDES 32 WE CONVERT TO 32000
if (options?.bitrate && options.bitrate < 1000) options.bitrate *= 1000;
@@ -48,7 +40,7 @@ export async function createChannel(
allow: calculateBits(perm.allow),
deny: calculateBits(perm.deny),
})),
type: options?.type || DiscordChannelTypes.GUILD_TEXT,
type: options?.type || DiscordChannelTypes.GuildText,
reason,
},
);
+10 -3
View File
@@ -1,20 +1,27 @@
import { eventHandlers } from "../../bot.ts";
import { cacheHandlers } from "../../cache.ts";
import { rest } from "../../rest/rest.ts";
import { ModifyChannel } from "../../types/channels/modify_channel.ts";
import { Channel } from "../../types/mod.ts";
import { endpoints } from "../../util/constants.ts";
import {
calculateBits,
requireBotChannelPermissions,
requireOverwritePermissions,
} from "../../util/permissions.ts";
//TODO: implement DM group channel edit
/** Update a channel's settings. Requires the `MANAGE_CHANNELS` permission for the guild. */
export async function editChannel(
channelId: string,
options: ModifyChannel,
reason?: string,
) {
await requireBotChannelPermissions(channelId, ["MANAGE_CHANNELS"]);
const channel = await cacheHandlers.get("channels", channelId);
if (channel?.guildId) {
await requireOverwritePermissions(
channel.guildId,
options.permissionOverwrites || [],
);
}
if (options.name || options.topic) {
const request = editChannelNameTopicQueue.get(channelId);
+27 -11
View File
@@ -4,6 +4,7 @@ import { DiscordenoChannel } from "../structures/channel.ts";
import { DiscordenoGuild } from "../structures/guild.ts";
import { DiscordenoMember } from "../structures/member.ts";
import { DiscordenoRole } from "../structures/role.ts";
import { Overwrite } from "../types/channels/overwrite.ts";
import { Errors } from "../types/misc/errors.ts";
import { DiscordBitwisePermissionFlags } from "../types/permissions/bitwise_permission_flags.ts";
import { PermissionStrings } from "../types/permissions/permission_strings.ts";
@@ -28,11 +29,6 @@ async function getCached(
? // @ts-ignore TS is wrong here
await cacheHandlers.get(table, key)
: key;
if (!cached || typeof cached === "string") {
throw new Error(
Errors[`${table.slice(0, -1).toUpperCase()}_NOT_FOUND` as Errors],
);
}
return typeof cached === "string" ? undefined : cached;
}
@@ -50,7 +46,7 @@ export async function calculateBasePermissions(
let permissions = 0n;
// Calculate the role permissions bits, @everyone role is not in memberRoleIds so we need to pass guildId manualy
permissions |= [...(member.guilds.get(guild.id)?.roles || []), guild.id]
.map((id) => (guild as DiscordenoGuild).roles.get(id)?.permissions)
.map((id) => guild.roles.get(id)?.permissions)
// Removes any edge case undefined
.filter((perm) => perm)
.reduce((bits, perms) => {
@@ -76,7 +72,7 @@ export async function calculateChannelOverwrites(
const member = await getCached("members", memberOrId);
if (!member) return "8";
if (!channel || !member) return "8";
// Get all the role permissions this member already has
let permissions = BigInt(
@@ -84,7 +80,7 @@ export async function calculateChannelOverwrites(
);
// First calculate @everyone overwrites since these have the lowest priority
const overwriteEveryone = channel?.permissionOverwrites?.find(
const overwriteEveryone = channel.permissionOverwrites.find(
(overwrite) => overwrite.id === (channel as DiscordenoChannel).guildId,
);
if (overwriteEveryone) {
@@ -93,7 +89,7 @@ export async function calculateChannelOverwrites(
permissions |= BigInt(overwriteEveryone.allow);
}
const overwrites = channel?.permissionOverwrites;
const overwrites = channel.permissionOverwrites;
// In order to calculate the role permissions correctly we need to temporarily save the allowed and denied permissions
let allow = 0n;
@@ -111,8 +107,8 @@ export async function calculateChannelOverwrites(
permissions |= allow;
// Third calculate member specific overwrites since these have the highest priority
const overwriteMember = overwrites?.find(
(overwrite) => overwrite.id === (member as DiscordenoMember).id,
const overwriteMember = overwrites.find(
(overwrite) => overwrite.id === member.id,
);
if (overwriteMember) {
permissions &= ~BigInt(overwriteMember.deny);
@@ -290,6 +286,26 @@ export function calculateBits(permissions: PermissionStrings[]) {
.toString();
}
/** Internal function to check if the bot has the permissions to set these overwrites */
export async function requireOverwritePermissions(
guildOrId: string | DiscordenoGuild,
overwrites: Overwrite[],
) {
let requiredPerms: Set<PermissionStrings> = new Set(["MANAGE_CHANNELS"]);
overwrites?.forEach((overwrite) => {
overwrite.allow.forEach(requiredPerms.add, requiredPerms);
overwrite.deny.forEach(requiredPerms.add, requiredPerms);
});
// MANAGE_ROLES permission can only be set by administrators
if (requiredPerms.has("MANAGE_ROLES")) {
requiredPerms = new Set<PermissionStrings>(["ADMINISTRATOR"]);
}
await requireGuildPermissions(guildOrId, botId, [...requiredPerms]);
}
/** Gets the highest role from the member in this guild */
export async function highestRole(
guildOrId: string | DiscordenoGuild,