1
Fork 0
mirror of https://github.com/wlinator/luminara.git synced 2024-10-02 22:23:13 +00:00

Merge remote-tracking branch 'origin/dev' into dev

This commit is contained in:
wlinator 2024-04-04 11:26:26 +02:00
commit 5d857fdf95
7 changed files with 200 additions and 54 deletions

View file

@ -88,6 +88,15 @@ CREATE TABLE guild_config (
PRIMARY KEY (guild_id) PRIMARY KEY (guild_id)
); );
CREATE TABLE level_rewards (
guild_id BIGINT NOT NULL,
level INT NOT NULL,
role_id BIGINT,
persistent BOOLEAN,
PRIMARY KEY (guild_id, level)
);
CREATE TABLE blacklist_user ( CREATE TABLE blacklist_user (
user_id BIGINT NOT NULL, user_id BIGINT NOT NULL,
reason TEXT, reason TEXT,

View file

@ -7,6 +7,7 @@ import discord
from config.parser import JsonCache from config.parser import JsonCache
from lib import formatter from lib import formatter
from services.GuildConfig import GuildConfig from services.GuildConfig import GuildConfig
from services.level_reward import LevelReward
from services.Xp import Xp from services.Xp import Xp
strings = JsonCache.read_json("strings") strings = JsonCache.read_json("strings")
@ -48,6 +49,8 @@ class XPHandler:
else: else:
await message.reply(content=level_message) await message.reply(content=level_message)
await self.assign_level_role(message.guild, message.author, level_config.level)
logs.info(f"[XpHandler] {message.author.name} leveled up to lv {level_config.level} " logs.info(f"[XpHandler] {message.author.name} leveled up to lv {level_config.level} "
f"in guild {message.guild.name} ({message.guild.id}).") f"in guild {message.guild.name} ({message.guild.id}).")
@ -59,10 +62,6 @@ class XPHandler:
level_config.ctime = current_time + level_config.new_cooldown level_config.ctime = current_time + level_config.new_cooldown
level_config.push() level_config.push()
# Legacy code for Rave Cave level roles
# turn into a global system soon
await self.legacy_assign_level_role(message.author, level_config.level)
@staticmethod @staticmethod
async def get_level_channel(message, guild_config): async def get_level_channel(message, guild_config):
if guild_config.level_channel_id: if guild_config.level_channel_id:
@ -120,50 +119,25 @@ class XPHandler:
return start_string + random_message.format(level) return start_string + random_message.format(level)
@staticmethod @staticmethod
async def legacy_assign_level_role(user, level): async def assign_level_role(guild, user, level: int) -> None:
_rew = LevelReward(guild.id)
role_id = _rew.role(level)
reason = "Automated Level Reward"
guild = user.guild if role_id:
if ( role = guild.get_role(role_id)
guild.id != 719227135151046699 or if role:
not (level % 5 == 0 and 5 <= level <= 100) try:
): await user.add_roles(role, reason=reason)
return except (discord.Forbidden, discord.NotFound, discord.HTTPException):
pass
level_roles = { previous = _rew.replace_previous_reward(level)
"level_5": 1118491431036792922, if previous[1]:
"level_10": 1118491486259003403, role = guild.get_role(previous[0])
"level_15": 1118491512536301570, if role:
"level_20": 1118491532111126578, try:
"level_25": 1118491554005393458, await user.remove_roles(role, reason=reason)
"level_30": 1118491572770713710, except (discord.Forbidden, discord.NotFound, discord.HTTPException):
"level_35": 1118491596820840492, pass
"level_40": 1118491622045405287,
"level_45": 1118491650721853500,
"level_50": 1118491681004732466,
"level_55": 1191681166848303135,
"level_60": 1191681220145319956,
"level_65": 1191681253322264587,
"level_70": 1191681274180554792,
"level_75": 1191681293277216859,
"level_80": 1191681312269017180,
"level_85": 1191681337560662086,
"level_90": 1191681359995998209,
"level_95": 1191681384113262683,
"level_100": 1191681405445492778,
# Add more level roles as needed
}
current_level_role = None
new_level_role_id = level_roles.get(f"level_{level}")
for role in user.roles:
if role.id in level_roles.values() and role.id != new_level_role_id:
current_level_role = role
break
new_level_role = guild.get_role(new_level_role_id)
await user.add_roles(new_level_role)
if current_level_role:
await user.remove_roles(current_level_role)

View file

@ -1,11 +1,12 @@
import os import os
import traceback
import discord import discord
from dotenv import load_dotenv from dotenv import load_dotenv
from handlers import LoggingHandler, ErrorHandler from handlers import LoggingHandler, ErrorHandler
from handlers.ReactionHandler import ReactionHandler from handlers.ReactionHandler import ReactionHandler
from handlers.XPHandler import XPHandler from handlers.xp_handler import XPHandler
from lib.embeds.greet import Greet from lib.embeds.greet import Greet
from services.Client import RacuBot from services.Client import RacuBot
from services.GuildConfig import GuildConfig from services.GuildConfig import GuildConfig
@ -50,8 +51,8 @@ async def on_message(message):
await reaction_handler.handle_message(message) await reaction_handler.handle_message(message)
except Exception as error: except Exception as error:
logs.error(f"[EventHandler] on_message (check debug log): {error}", exc_info=False) logs.error(f"[EventHandler] on_message (check debug log): {error}", exc_info=True)
logs.debug(f"[EventHandler] on_message (w/ stacktrace): {error}", exc_info=True) traceback.print_tb(error.__traceback__)
@client.event @client.event

View file

@ -7,7 +7,7 @@ from discord.ext import commands, bridge
from config.parser import JsonCache from config.parser import JsonCache
from lib import formatter from lib import formatter
from lib.embeds.greet import Greet from lib.embeds.greet import Greet
from modules.config import config, set_prefix from modules.config import config, set_prefix, xp_reward
from services.GuildConfig import GuildConfig from services.GuildConfig import GuildConfig
strings = JsonCache.read_json("strings") strings = JsonCache.read_json("strings")
@ -48,6 +48,48 @@ class Config(commands.Cog):
await set_prefix.set_cmd(ctx, prefix) await set_prefix.set_cmd(ctx, prefix)
@bridge.bridge_command(
name="xprewards",
aliases=["xpr"],
guild_only="True"
)
@commands.guild_only()
@commands.has_permissions(manage_roles=True)
async def xp_reward_command_show(self, ctx):
"""
[Read the guide before editing](https://gitlab.com/wlinator/Racu/wikis/Role-Rewards).
"""
await xp_reward.show(ctx)
@bridge.bridge_command(
name="addxpreward",
aliases=["axpr"],
guild_only="True"
)
@commands.guild_only()
@commands.has_permissions(manage_roles=True)
async def xp_reward_command_add(self, ctx, level: int, role: discord.Role, persistent: bool = False):
"""
[Read the guide before editing](https://gitlab.com/wlinator/Racu/wikis/Role-Rewards).
"""
await xp_reward.add_reward(ctx, level, role.id, persistent)
@bridge.bridge_command(
name="removexpreward",
aliases=["rxpr"],
guild_only="True"
)
@commands.guild_only()
@commands.has_permissions(manage_roles=True)
async def xp_reward_command_remove(self, ctx, level: int):
"""
[Read the guide before editing](https://gitlab.com/wlinator/Racu/wikis/Role-Rewards).
"""
await xp_reward.remove_reward(ctx, level)
"""
The guild config code is a mess.
"""
config = SlashCommandGroup("config", "server config commands.", guild_only=True, config = SlashCommandGroup("config", "server config commands.", guild_only=True,
default_member_permissions=discord.Permissions(manage_channels=True)) default_member_permissions=discord.Permissions(manage_channels=True))
birthday_config = config.create_subgroup(name="birthdays") birthday_config = config.create_subgroup(name="birthdays")

View file

@ -0,0 +1,46 @@
import discord
from services.level_reward import LevelReward
from config.parser import JsonCache
art = JsonCache.read_json("art")
async def show(ctx):
level_reward = LevelReward(ctx.guild.id)
embed = discord.Embed(
color=discord.Color.embed_background(),
description="[Read the guide before editing](https://gitlab.com/wlinator/Racu/wikis/Role-Rewards).\n"
)
icon = ctx.guild.icon if ctx.guild.icon else art["logo"]["opaque"]
embed.set_author(name="Level Rewards", icon_url=icon)
for level in sorted(sorted(level_reward.rewards.keys())):
role_id, persistent = level_reward.rewards.get(level)
role = ctx.guild.get_role(role_id)
embed.description += f"\n**Level {level}** -> {role.mention}"
if bool(persistent):
embed.description += " (persistent)"
await ctx.respond(embed=embed)
async def add_reward(ctx, level, role_id, persistent):
level_reward = LevelReward(ctx.guild.id)
if len(level_reward.rewards) >= 10:
raise discord.BadArgument("a server can't have more than 10 XP rewards.")
level_reward.add_reward(level, role_id, persistent)
await show(ctx)
async def remove_reward(ctx, level):
level_reward = LevelReward(ctx.guild.id)
level_reward.remove_reward(level)
await show(ctx)

View file

@ -62,8 +62,7 @@ class Economy(commands.Cog):
@commands.command( @commands.command(
name="give", name="give",
help="Give another user some cash. You can use someone's user ID or mention someone. The user has to be in the " help="Give another user some cash. You can use a user ID or mention them."
"guild you invoke this command in."
) )
@commands.guild_only() @commands.guild_only()
@checks.allowed_in_channel() @checks.allowed_in_channel()

75
services/level_reward.py Normal file
View file

@ -0,0 +1,75 @@
from datetime import datetime, timedelta
from db import database
from discord.ext import commands
import logging
from config.parser import JsonCache
resources = JsonCache.read_json("resources")
_logs = logging.getLogger('Racu.Core')
class LevelReward:
def __init__(self, guild_id):
self.guild_id = guild_id
self.rewards = self.get_rewards()
def get_rewards(self) -> dict:
query = """
SELECT level, role_id, persistent
FROM level_rewards
WHERE guild_id = %s
ORDER BY level DESC
"""
data = database.select_query(query, (self.guild_id,))
rewards = {}
for row in data:
rewards[int(row[0])] = [int(row[1]), bool(row[2])]
_logs.info(rewards)
return rewards
def add_reward(self, level: int, role_id: int, persistent: bool):
query = """
INSERT INTO level_rewards (guild_id, level, role_id, persistent)
VALUES (%s, %s, %s, %s)
ON DUPLICATE KEY UPDATE role_id = %s, persistent = %s;
"""
database.execute_query(query, (self.guild_id, level, role_id, persistent, role_id, persistent))
def remove_reward(self, level: int):
query = """
DELETE FROM level_rewards
WHERE guild_id = %s
AND level = %s;
"""
database.execute_query(query, (self.guild_id, level))
def role(self, level: int):
if self.rewards:
if level in self.rewards:
role_id = self.rewards.get(level)[0]
_logs.info(role_id)
return role_id
return None
def replace_previous_reward(self, level):
replace = False
previous_reward = None
levels = sorted(self.rewards.keys())
if level in levels:
values_below = [x for x in levels if x < level]
if values_below:
replace = not bool(self.rewards.get(max(values_below))[1])
if replace:
previous_reward = self.rewards.get(max(values_below))[0]
return previous_reward, replace