Take into consideration member timeouts in permission calculations

This commit is contained in:
Rapptz 2022-04-01 09:32:54 -04:00
parent 25ad5b675c
commit a5f1c2f592
3 changed files with 22 additions and 2 deletions

View File

@ -538,6 +538,7 @@ class GuildChannel:
- Guild roles
- Channel overrides
- Member overrides
- Member timeout
If a :class:`~discord.Role` is passed, then it checks the permissions
someone with that role would have, which is essentially:
@ -624,6 +625,12 @@ class GuildChannel:
if base.administrator:
return Permissions.all()
if obj.is_timed_out():
# Timeout leads to every permission except VIEW_CHANNEL and READ_MESSAGE_HISTORY
# being explicitly denied
base.value &= Permissions._timeout_mask()
return base
# Apply @everyone allow/deny first since it's special
try:
maybe_everyone = self._overwrites[0]

View File

@ -649,8 +649,11 @@ class Member(discord.abc.Messageable, _UserTag):
channel permission overwrites. For 100% accurate permission
calculation, please use :meth:`abc.GuildChannel.permissions_for`.
This does take into consideration guild ownership and the
administrator implication.
This does take into consideration guild ownership, the
administrator implication, and whether the member is timed out.
.. versionchanged:: 2.0
Member timeouts are taken into consideration.
"""
if self.guild.owner_id == self.id:
@ -663,6 +666,9 @@ class Member(discord.abc.Messageable, _UserTag):
if base.administrator:
return Permissions.all()
if self.is_timed_out():
base.value &= Permissions._timeout_mask()
return base
@property

View File

@ -151,6 +151,13 @@ class Permissions(BaseFlags):
"""
return cls(0b11111111111111111111111111111111111111111)
@classmethod
def _timeout_mask(cls) -> int:
p = cls.all()
p.view_channel = False
p.read_message_history = False
return ~p.value
@classmethod
def all_channel(cls) -> Self:
"""A :class:`Permissions` with all channel-specific permissions set to