aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorGravatar MarkKoz <[email protected]>2020-11-26 14:12:21 -0800
committerGravatar MarkKoz <[email protected]>2020-11-26 14:12:21 -0800
commit7729cfb618e8608cff4c8d458fb36d921629d466 (patch)
treefe4ffae7c013cdf46c8e21ec0e0a2bd536b02d3d
parentHelp channels: document the return value of notify() (diff)
parentMerge pull request #1307 from python-discord/sebastiaan/bugs/add-voiceban-to-... (diff)
Merge branch 'master' into feat/help/refactor
-rw-r--r--.github/CODEOWNERS27
-rw-r--r--.github/workflows/build.yml2
-rw-r--r--.github/workflows/deploy.yml5
-rw-r--r--bot/exts/moderation/infraction/_scheduler.py22
-rw-r--r--bot/exts/moderation/infraction/infractions.py2
-rw-r--r--bot/exts/moderation/infraction/superstarify.py77
-rw-r--r--deployment.yaml21
7 files changed, 82 insertions, 74 deletions
diff --git a/.github/CODEOWNERS b/.github/CODEOWNERS
index cf5f1590d..5f5386222 100644
--- a/.github/CODEOWNERS
+++ b/.github/CODEOWNERS
@@ -1 +1,26 @@
-* @python-discord/core-developers
+# Request Joe and Dennis for any PR
+* @jb3 @Den4200
+
+# Extensions
+**/bot/exts/backend/sync/** @MarkKoz
+**/bot/exts/filters/*token_remover.py @MarkKoz
+**/bot/exts/moderation/*silence.py @MarkKoz
+bot/exts/info/codeblock/** @MarkKoz
+bot/exts/utils/extensions.py @MarkKoz
+bot/exts/utils/snekbox.py @MarkKoz
+bot/exts/help_channels.py @MarkKoz
+
+# Utils
+bot/utils/extensions.py @MarkKoz
+bot/utils/function.py @MarkKoz
+bot/utils/lock.py @MarkKoz
+bot/utils/scheduling.py @MarkKoz
+
+# Tests
+tests/_autospec.py @MarkKoz
+tests/bot/exts/test_cogs.py @MarkKoz
+
+# CI & Docker
+.github/workflows/** @MarkKoz
+Dockerfile @MarkKoz
+docker-compose.yml @MarkKoz
diff --git a/.github/workflows/build.yml b/.github/workflows/build.yml
index 706ab462f..6152f1543 100644
--- a/.github/workflows/build.yml
+++ b/.github/workflows/build.yml
@@ -10,7 +10,7 @@ on:
jobs:
build:
- if: github.event.workflow_run.conclusion == 'success'
+ if: github.event.workflow_run.conclusion == 'success' && github.event.workflow_run.event == 'push'
name: Build & Push
runs-on: ubuntu-latest
diff --git a/.github/workflows/deploy.yml b/.github/workflows/deploy.yml
index 90555a8ee..5a4aede30 100644
--- a/.github/workflows/deploy.yml
+++ b/.github/workflows/deploy.yml
@@ -23,6 +23,9 @@ jobs:
- name: Checkout code
uses: actions/checkout@v2
+ with:
+ repository: python-discord/kubernetes
+ token: ${{ secrets.REPO_TOKEN }}
- name: Authenticate with Kubernetes
uses: azure/k8s-set-context@v1
@@ -34,6 +37,6 @@ jobs:
uses: Azure/k8s-deploy@v1
with:
manifests: |
- deployment.yaml
+ bot/deployment.yaml
images: 'ghcr.io/python-discord/bot:${{ steps.sha_tag.outputs.tag }}'
kubectl-version: 'latest'
diff --git a/bot/exts/moderation/infraction/_scheduler.py b/bot/exts/moderation/infraction/_scheduler.py
index bebade0ae..c062ae7f8 100644
--- a/bot/exts/moderation/infraction/_scheduler.py
+++ b/bot/exts/moderation/infraction/_scheduler.py
@@ -82,15 +82,27 @@ class InfractionScheduler:
ctx: Context,
infraction: _utils.Infraction,
user: UserSnowflake,
- action_coro: t.Optional[t.Awaitable] = None
- ) -> None:
- """Apply an infraction to the user, log the infraction, and optionally notify the user."""
+ action_coro: t.Optional[t.Awaitable] = None,
+ user_reason: t.Optional[str] = None,
+ additional_info: str = "",
+ ) -> bool:
+ """
+ Apply an infraction to the user, log the infraction, and optionally notify the user.
+
+ `user_reason`, if provided, will be sent to the user in place of the infraction reason.
+ `additional_info` will be attached to the text field in the mod-log embed.
+
+ Returns whether or not the infraction succeeded.
+ """
infr_type = infraction["type"]
icon = _utils.INFRACTION_ICONS[infr_type][0]
reason = infraction["reason"]
expiry = time.format_infraction_with_duration(infraction["expires_at"])
id_ = infraction['id']
+ if user_reason is None:
+ user_reason = reason
+
log.trace(f"Applying {infr_type} infraction #{id_} to {user}.")
# Default values for the confirmation message and mod log.
@@ -126,7 +138,7 @@ class InfractionScheduler:
log.error(f"Failed to DM {user.id}: could not fetch user (status {e.status})")
else:
# Accordingly display whether the user was successfully notified via DM.
- if await _utils.notify_infraction(user, " ".join(infr_type.split("_")).title(), expiry, reason, icon):
+ if await _utils.notify_infraction(user, infr_type.replace("_", " ").title(), expiry, user_reason, icon):
dm_result = ":incoming_envelope: "
dm_log_text = "\nDM: Sent"
@@ -198,12 +210,14 @@ class InfractionScheduler:
Member: {messages.format_user(user)}
Actor: {ctx.author.mention}{dm_log_text}{expiry_log_text}
Reason: {reason}
+ {additional_info}
"""),
content=log_content,
footer=f"ID {infraction['id']}"
)
log.info(f"Applied {infr_type} infraction #{id_} to {user}.")
+ return not failed
async def pardon_infraction(
self,
diff --git a/bot/exts/moderation/infraction/infractions.py b/bot/exts/moderation/infraction/infractions.py
index 746d4e154..6056df1d2 100644
--- a/bot/exts/moderation/infraction/infractions.py
+++ b/bot/exts/moderation/infraction/infractions.py
@@ -27,7 +27,7 @@ class Infractions(InfractionScheduler, commands.Cog):
category_description = "Server moderation tools."
def __init__(self, bot: Bot):
- super().__init__(bot, supported_infractions={"ban", "kick", "mute", "note", "warning"})
+ super().__init__(bot, supported_infractions={"ban", "kick", "mute", "note", "warning", "voice_ban"})
self.category = "Moderation"
self._muted_role = discord.Object(constants.Roles.muted)
diff --git a/bot/exts/moderation/infraction/superstarify.py b/bot/exts/moderation/infraction/superstarify.py
index adfe42fcd..96dfb562f 100644
--- a/bot/exts/moderation/infraction/superstarify.py
+++ b/bot/exts/moderation/infraction/superstarify.py
@@ -5,7 +5,7 @@ import textwrap
import typing as t
from pathlib import Path
-from discord import Colour, Embed, Member
+from discord import Embed, Member
from discord.ext.commands import Cog, Context, command, has_any_role
from discord.utils import escape_markdown
@@ -143,57 +143,44 @@ class Superstarify(InfractionScheduler, Cog):
forced_nick = self.get_nick(id_, member.id)
expiry_str = format_infraction(infraction["expires_at"])
- # Apply the infraction and schedule the expiration task.
- log.debug(f"Changing nickname of {member} to {forced_nick}.")
- self.mod_log.ignore(constants.Event.member_update, member.id)
- await member.edit(nick=forced_nick, reason=reason)
- self.schedule_expiration(infraction)
+ # Apply the infraction
+ async def action() -> None:
+ log.debug(f"Changing nickname of {member} to {forced_nick}.")
+ self.mod_log.ignore(constants.Event.member_update, member.id)
+ await member.edit(nick=forced_nick, reason=reason)
old_nick = escape_markdown(old_nick)
forced_nick = escape_markdown(forced_nick)
- # Send a DM to the user to notify them of their new infraction.
- await _utils.notify_infraction(
- user=member,
- infr_type="Superstarify",
- expires_at=expiry_str,
- icon_url=_utils.INFRACTION_ICONS["superstar"][0],
- reason=f"Your nickname didn't comply with our [nickname policy]({NICKNAME_POLICY_URL})."
+ superstar_reason = f"Your nickname didn't comply with our [nickname policy]({NICKNAME_POLICY_URL})."
+ nickname_info = textwrap.dedent(f"""
+ Old nickname: `{old_nick}`
+ New nickname: `{forced_nick}`
+ """).strip()
+
+ successful = await self.apply_infraction(
+ ctx, infraction, member, action(),
+ user_reason=superstar_reason,
+ additional_info=nickname_info
)
- # Send an embed with the infraction information to the invoking context.
- log.trace(f"Sending superstar #{id_} embed.")
- embed = Embed(
- title="Congratulations!",
- colour=constants.Colours.soft_orange,
- description=(
- f"Your previous nickname, **{old_nick}**, "
- f"was so bad that we have decided to change it. "
- f"Your new nickname will be **{forced_nick}**.\n\n"
- f"You will be unable to change your nickname until **{expiry_str}**.\n\n"
- "If you're confused by this, please read our "
- f"[official nickname policy]({NICKNAME_POLICY_URL})."
+ # Send an embed with the infraction information to the invoking context if
+ # superstar was successful.
+ if successful:
+ log.trace(f"Sending superstar #{id_} embed.")
+ embed = Embed(
+ title="Congratulations!",
+ colour=constants.Colours.soft_orange,
+ description=(
+ f"Your previous nickname, **{old_nick}**, "
+ f"was so bad that we have decided to change it. "
+ f"Your new nickname will be **{forced_nick}**.\n\n"
+ f"You will be unable to change your nickname until **{expiry_str}**.\n\n"
+ "If you're confused by this, please read our "
+ f"[official nickname policy]({NICKNAME_POLICY_URL})."
+ )
)
- )
- await ctx.send(embed=embed)
-
- # Log to the mod log channel.
- log.trace(f"Sending apply mod log for superstar #{id_}.")
- await self.mod_log.send_log_message(
- icon_url=_utils.INFRACTION_ICONS["superstar"][0],
- colour=Colour.gold(),
- title="Member achieved superstardom",
- thumbnail=member.avatar_url_as(static_format="png"),
- text=textwrap.dedent(f"""
- Member: {member.mention}
- Actor: {ctx.message.author.mention}
- Expires: {expiry_str}
- Old nickname: `{old_nick}`
- New nickname: `{forced_nick}`
- Reason: {reason}
- """),
- footer=f"ID {id_}"
- )
+ await ctx.send(embed=embed)
@command(name="unsuperstarify", aliases=("release_nick", "unstar"))
async def unsuperstarify(self, ctx: Context, member: Member) -> None:
diff --git a/deployment.yaml b/deployment.yaml
deleted file mode 100644
index ca5ff5941..000000000
--- a/deployment.yaml
+++ /dev/null
@@ -1,21 +0,0 @@
-apiVersion: apps/v1
-kind: Deployment
-metadata:
- name: bot
-spec:
- replicas: 1
- selector:
- matchLabels:
- app: bot
- template:
- metadata:
- labels:
- app: bot
- spec:
- containers:
- - name: bot
- image: ghcr.io/python-discord/bot:latest
- imagePullPolicy: Always
- envFrom:
- - secretRef:
- name: bot-env