update(cog|admin): add commands for warns

This commit is contained in:
Romain J 2019-09-22 04:18:28 +02:00
parent 0849c1bdff
commit 2d175b4453
6 changed files with 247 additions and 52 deletions

View file

@ -1,6 +1,8 @@
import datetime import datetime
import logging
from typing import Union from typing import Union
import asyncio
import discord import discord
import humanize import humanize
from discord.ext import commands from discord.ext import commands
@ -8,12 +10,13 @@ from discord.ext import commands
from bot import TuxBot from bot import TuxBot
from .utils.lang import Texts from .utils.lang import Texts
log = logging.getLogger(__name__)
class Admin(commands.Cog): class Admin(commands.Cog):
def __init__(self, bot: TuxBot): def __init__(self, bot: TuxBot):
self.bot = bot self.bot = bot
self.db = bot.db
async def cog_check(self, ctx: commands.Context) -> bool: async def cog_check(self, ctx: commands.Context) -> bool:
permissions: discord.Permissions = ctx.channel.permissions_for( permissions: discord.Permissions = ctx.channel.permissions_for(
@ -97,7 +100,7 @@ class Admin(commands.Cog):
"""---------------------------------------------------------------------""" """---------------------------------------------------------------------"""
@commands.command(name='ban') @commands.command(name='ban')
async def _ban(self, ctx: commands.Context, user: discord.User, *, async def _ban(self, ctx: commands.Context, user: discord.Member, *,
reason=""): reason=""):
try: try:
member: discord.Member = await ctx.guild.fetch_member(user.id) member: discord.Member = await ctx.guild.fetch_member(user.id)
@ -122,7 +125,7 @@ class Admin(commands.Cog):
"""---------------------------------------------------------------------""" """---------------------------------------------------------------------"""
@commands.command(name='kick') @commands.command(name='kick')
async def _kick(self, ctx: commands.Context, user: discord.User, *, async def _kick(self, ctx: commands.Context, user: discord.Member, *,
reason=""): reason=""):
try: try:
member: discord.Member = await ctx.guild.fetch_member(user.id) member: discord.Member = await ctx.guild.fetch_member(user.id)
@ -221,48 +224,189 @@ class Admin(commands.Cog):
"""---------------------------------------------------------------------""" """---------------------------------------------------------------------"""
async def get_warn(self, ctx: commands.Context,
member: discord.Member = False):
query = """
SELECT * FROM warns
WHERE created_at >= $1 AND server_id = $2
"""
query += """AND user_id = $3""" if member else ""
query += """ORDER BY created_at DESC"""
week_ago = datetime.datetime.now() - datetime.timedelta(weeks=6)
async with self.bot.db.acquire() as con:
await ctx.trigger_typing()
args = [week_ago, ctx.guild.id]
if member:
args.append(member.id)
warns = await con.fetch(query, *args)
warns_list = ''
for warn in warns:
row_id = warn.get('id')
user_id = warn.get('user_id')
user = await self.bot.fetch_user(user_id)
reason = warn.get('reason')
ago = humanize.naturaldelta(
datetime.datetime.now() - warn.get('created_at')
)
warns_list += f"[{row_id}] **{user}**: `{reason}` " \
f"*({ago} ago)*\n"
return warns_list, warns
@commands.group(name='warn', aliases=['warns']) @commands.group(name='warn', aliases=['warns'])
async def _warn(self, ctx: commands.Context): async def _warn(self, ctx: commands.Context):
if ctx.invoked_subcommand is None: if ctx.invoked_subcommand is None:
query = """ warns_list, warns = await self.get_warn(ctx)
SELECT user_id, reason, created_at FROM warns e = discord.Embed(
WHERE created_at >= $1 AND server_id = $2 title=f"{len(warns)} {Texts('admin').get('last warns')}: ",
ORDER BY created_at description=warns_list
DESC LIMIT 10 )
"""
week_ago = datetime.datetime.now() - datetime.timedelta(weeks=6)
async with self.bot.db.acquire() as con: await ctx.send(embed=e)
await ctx.trigger_typing()
warns = await con.fetch(query, week_ago, ctx.guild.id)
warns_list = ''
for warn in warns: async def add_warn(self, ctx: commands.Context, member: discord.Member,
user_id = warn.get('user_id') reason):
user = await self.bot.fetch_user(user_id)
reason = warn.get('reason')
ago = humanize.naturaldelta(
datetime.datetime.now() - warn.get('created_at')
)
warns_list += f"**{user}**: `{reason}` *({ago} ago)*\n" query = """
INSERT INTO warns (server_id, user_id, reason, created_at)
VALUES ($1, $2, $3, $4)
"""
e = discord.Embed( now = datetime.datetime.now()
title=f"{len(warns)} {Texts('admin').get('last warns')}: ", await self.bot.db.execute(query, ctx.guild.id, member.id, reason, now)
description=warns_list
)
await ctx.send(embed=e)
@_warn.command(name='add', aliases=['new']) @_warn.command(name='add', aliases=['new'])
async def _warn_new(self, ctx: commands.Context, member: discord.Member, async def _warn_new(self, ctx: commands.Context, member: discord.Member,
*, reason): *, reason="N/A"):
member = await ctx.guild.fetch_member(member.id)
if not member:
return await ctx.send(
Texts('utils').get("Unable to find the user...")
)
query = """
SELECT user_id, reason, created_at FROM warns
WHERE created_at >= $1 AND server_id = $2 and user_id = $3
""" """
todo: push in database week_ago = datetime.datetime.now() - datetime.timedelta(weeks=6)
if warn > 2 for member:
todo: ask for confirmation to kick or ban def check(payload: discord.RawReactionActionEvent):
if payload.message_id != choice.id \
or payload.user_id != ctx.author.id:
return False
return payload.emoji.name in ('1⃣', '2⃣', '3⃣')
async with self.bot.db.acquire() as con:
await ctx.trigger_typing()
warns = await con.fetch(query, week_ago, ctx.guild.id, member.id)
if len(warns) >= 2:
e = discord.Embed(
title=Texts('admin').get('More than 2 warns'),
description=f"{member.mention} "
+ Texts('admin').get('has more than 2 warns')
)
e.add_field(
name='__Actions__',
value=':one: kick\n'
':two: ban\n'
':three: ' + Texts('admin').get('ignore')
)
choice = await ctx.send(embed=e)
for reaction in ('1⃣', '2⃣', '3⃣'):
await choice.add_reaction(reaction)
try:
payload = await self.bot.wait_for(
'raw_reaction_add',
check=check,
timeout=50.0
)
except asyncio.TimeoutError:
return await ctx.send(
Texts('admin').get('Took too long. Aborting.')
)
finally:
await choice.delete()
if payload.emoji.name == '1⃣':
from jishaku.models import copy_context_with
alt_ctx = await copy_context_with(
ctx,
content=f"{ctx.prefix}"
f"kick "
f"{member} "
f"{Texts('admin').get('More than 2 warns')}"
)
return await alt_ctx.command.invoke(alt_ctx)
elif payload.emoji.name == '2⃣':
from jishaku.models import copy_context_with
alt_ctx = await copy_context_with(
ctx,
content=f"{ctx.prefix}"
f"ban "
f"{member} "
f"{Texts('admin').get('More than 2 warns')}"
)
return await alt_ctx.command.invoke(alt_ctx)
await self.add_warn(ctx, member, reason)
await ctx.send(
content=f"{member.mention} **{Texts('admin').get('got a warn')}**"
f"\n**{Texts('admin').get('Reason')}:** `{reason}`"
if reason != 'N/A' else ''
)
@_warn.command(name='remove', aliases=['revoke'])
async def _warn_remove(self, ctx: commands.Context, warn_id: int):
query = """
DELETE FROM warns
WHERE id = $1
""" """
async with self.bot.db.acquire() as con:
await ctx.trigger_typing()
await con.fetch(query, warn_id)
await ctx.send(f"{Texts('admin').get('Warn with id')} `{warn_id}`"
f" {Texts('admin').get('successfully removed')}")
@_warn.command(name='show', aliases=['list'])
async def _warn_show(self, ctx: commands.Context, member: discord.Member):
warns_list, warns = await self.get_warn(ctx, member)
e = discord.Embed(
title=f"{len(warns)} {Texts('admin').get('last warns')}: ",
description=warns_list
)
await ctx.send(embed=e)
@_warn.command(name='edit', aliases=['change'])
async def _warn_edit(self, ctx: commands.Context, warn_id: int, *,
reason):
query = """
UPDATE warns
SET reason = $2
WHERE id = $1
"""
async with self.bot.db.acquire() as con:
await ctx.trigger_typing()
await con.fetch(query, warn_id, reason)
await ctx.send(f"{Texts('admin').get('Warn with id')} `{warn_id}`"
f" {Texts('admin').get('successfully edited')}")
def setup(bot: TuxBot): def setup(bot: TuxBot):
bot.add_cog(Admin(bot)) bot.add_cog(Admin(bot))

View file

@ -15,7 +15,22 @@ class Utility(commands.Cog):
"""---------------------------------------------------------------------""" """---------------------------------------------------------------------"""
async def fetch_api(self, ctx: commands.Context, ip, addr): @commands.command(name='iplocalise')
async def _iplocalise(self, ctx: commands.Context, addr, ip_type=''):
addr = re.sub(r'http(s?)://', '', addr)
addr = addr[:-1] if addr.endswith('/') else addr
await ctx.trigger_typing()
if ip_type in ('v6', 'ipv6'):
try:
ip = socket.getaddrinfo(addr, None, socket.AF_INET6)[1][4][0]
except socket.gaierror:
return await ctx.send(
Texts('utility').get('ipv6 not available'))
else:
ip = socket.gethostbyname(addr)
async with self.bot.session.get(f"http://ip-api.com/json/{ip}") as s: async with self.bot.session.get(f"http://ip-api.com/json/{ip}") as s:
response: dict = await s.json() response: dict = await s.json()
@ -55,24 +70,6 @@ class Utility(commands.Cog):
content=f"{Texts('utility').get('info not available')}" content=f"{Texts('utility').get('info not available')}"
f"``{response.get('query')}``") f"``{response.get('query')}``")
@commands.command(name='iplocalise')
async def _iplocalise(self, ctx: commands.Context, addr, ip_type=''):
addr = re.sub(r'http(s?)://', '', addr)
addr = addr[:-1] if addr.endswith('/') else addr
await ctx.trigger_typing()
if ip_type in ('v6', 'ipv6'):
try:
ip = socket.getaddrinfo(addr, None, socket.AF_INET6)[1][4][0]
except socket.gaierror:
return await ctx.send(
Texts('utility').get('ipv6 not available'))
else:
ip = socket.gethostbyname(addr)
await self.fetch_api(ctx, ip, addr)
def setup(bot: TuxBot): def setup(bot: TuxBot):
bot.add_cog(Utility(bot)) bot.add_cog(Utility(bot))

View file

@ -25,4 +25,31 @@ msgid "Unable to kick this user"
msgstr "" msgstr ""
msgid "last warns" msgid "last warns"
msgstr ""
msgid "More than 2 warns"
msgstr ""
msgid "has more than 2 warns"
msgstr "has more than 2 warns, what do you want to do ?"
msgid "ignore"
msgstr ""
msgid "Took too long. Aborting."
msgstr ""
msgid "got a warn"
msgstr ""
msgid "Reason"
msgstr ""
msgid "Warn with id"
msgstr ""
msgid "successfully removed"
msgstr ""
msgid "successfully edited"
msgstr "" msgstr ""

View file

@ -25,4 +25,31 @@ msgid "Unable to kick this user"
msgstr "Impossible d'expulser cet utilisateur" msgstr "Impossible d'expulser cet utilisateur"
msgid "last warns" msgid "last warns"
msgstr "derniers avertissements" msgstr "derniers avertissements"
msgid "More than 2 warns"
msgstr "Plus de 2 avertissements"
msgid "has more than 2 warns"
msgstr "a plus de 2 avertissements, que voulez-vous faire?"
msgid "ignore"
msgstr "ignorer"
msgid "Took too long. Aborting."
msgstr "Temps expiré. Abandons."
msgid "got a warn"
msgstr "a recu un avertissement"
msgid "Reason"
msgstr "Raison"
msgid "Warn with id"
msgstr "L'avertissement avec l'id"
msgid "successfully removed"
msgstr "a été enlevé avec succes"
msgid "successfully edited"
msgstr "a été édité avec succes"