import discord from discord.ext import commands from discord.commands import Option from discord.commands import slash_command import configparser import time class actionlog(commands.Cog): def __init__(self, bot: discord.Bot): self.bot = bot def _load_config(self): config = configparser.ConfigParser() configFilePath = r'config.cfg' config.read(configFilePath) return config def _get_log_channel(self): config = self._load_config() log_channel_id = int(config["Logs"]["action_log"]) log_channel = self.bot.get_channel(log_channel_id) if log_channel is None: print(f"Log channel with ID {log_channel_id} not found.") return None return log_channel #Deleted Message Log @commands.Cog.listener() async def on_message_delete(self, message: discord.Message): if message.author.bot: return config = self._load_config() enable_log = config.getboolean("Logs","enable_action_log") if not enable_log: return log_channel = self._get_log_channel() if log_channel is None: return else: if message.content is None and not message.attachments: content = "No content available" elif message.content is None: content = "Content not available, but there are attachments." else: content = message.content embed = discord.Embed( title="Message Deleted", description=f"A message by {message.author.mention} was deleted in {message.channel.mention}.", color=discord.Color.red(), timestamp=message.created_at ) embed.add_field(name="Message Content", value=content[:1024], inline=False) embed.set_footer(text=f"User ID: {message.author.id} | Message ID: {message.id}") await log_channel.send(embed=embed) #Edited Message Log @commands.Cog.listener() async def on_message_edit(self, before, after): config = self._load_config() enable_log = config.getboolean("Logs","enable_action_log") if not enable_log: return log_channel = self._get_log_channel() if log_channel is None: return if before.author.bot: return else: embed = discord.Embed( title="Message Edited", description=f"A message by {before.author.mention} was edited in {before.channel.mention}.", color=discord.Color.orange(), timestamp=after.edited_at or discord.utils.utcnow() ) embed.add_field(name="Before", value=before.content or "No content", inline=False) embed.add_field(name="After", value=after.content or "No content", inline=False) embed.set_footer(text=f"User ID: {before.author.id} | Message ID: {before.id}") await log_channel.send(embed=embed) #Member Join Log @commands.Cog.listener() async def on_member_join(self, member): config = self._load_config() enable_log = config.getboolean("Logs","enable_action_log") if not enable_log: return log_channel = self._get_log_channel() if log_channel is None: return embed = discord.Embed( title="Member Joined", description=f"{member.mention} has joined the server.", color=discord.Color.green(), timestamp=discord.utils.utcnow() ) embed.set_footer(text=f"User ID: {member.id}") await log_channel.send(embed=embed) #Member Leave Log @commands.Cog.listener() async def on_member_remove(self, member): config = self._load_config() enable_log = config.getboolean("Logs","enable_action_log") if not enable_log: return log_channel = self._get_log_channel() if log_channel is None: return embed = discord.Embed( title="Member Left", description=f"{member.mention} has left the server. Joined at: {member.joined_at}", color=discord.Color.dark_red(), timestamp=discord.utils.utcnow() ) embed.set_footer(text=f"User ID: {member.id}") await log_channel.send(embed=embed) #Role Update Log @commands.Cog.listener() async def on_guild_role_update(self, before, after): config = self._load_config() enable_log = config.getboolean("Logs","enable_action_log") if not enable_log: return log_channel = self._get_log_channel() if log_channel is None: return embed = discord.Embed( title="Role Updated", description=f"The role **{before.name}** has been updated.", color=discord.Color.blue(), timestamp=discord.utils.utcnow() ) embed.add_field(name="Before", value=f"Name: {before.name}\nColor: {before.color}\nPermissions: {before.permissions}", inline=False) embed.add_field(name="After", value=f"Name: {after.name}\nColor: {after.color}\nPermissions: {after.permissions}", inline=False) embed.set_footer(text=f"Role ID: {before.id}") await log_channel.send(embed=embed) #Role added log @commands.Cog.listener() async def on_guild_role_create(self, role): config = self._load_config() enable_log = config.getboolean("Logs","enable_action_log") if not enable_log: return log_channel = self._get_log_channel() if log_channel is None: return embed = discord.Embed( title="Role Created", description=f"The role **{role.name}** has been created.", color=discord.Color.green(), timestamp=discord.utils.utcnow() ) embed.set_footer(text=f"Role ID: {role.id}") await log_channel.send(embed=embed) #Role deleted log @commands.Cog.listener() async def on_guild_role_delete(self, role): config = self._load_config() enable_log = config.getboolean("Logs","enable_action_log") if not enable_log: return log_channel = self._get_log_channel() if log_channel is None: return embed = discord.Embed( title="Role Deleted", description=f"The role **{role.name}** has been deleted.", color=discord.Color.red(), timestamp=discord.utils.utcnow() ) embed.set_footer(text=f"Role ID: {role.id}") await log_channel.send(embed=embed) #User Role update log @commands.Cog.listener() async def on_member_update(self, before, after): config = self._load_config() enable_log = config.getboolean("Logs","enable_action_log") if not enable_log: return log_channel = self._get_log_channel() if log_channel is None: return before_roles = set(before.roles) after_roles = set(after.roles) added_roles = after_roles - before_roles removed_roles = before_roles - after_roles for role in added_roles: embed = discord.Embed( title="Role Added", description=f"The role **{role.name}** has been added to {after.mention}.", color=discord.Color.green(), timestamp=discord.utils.utcnow() ) embed.set_footer(text=f"User ID: {after.id} | Role ID: {role.id}") await log_channel.send(embed=embed) for role in removed_roles: embed = discord.Embed( title="Role Removed", description=f"The role **{role.name}** has been removed from {after.mention}.", color=discord.Color.red(), timestamp=discord.utils.utcnow() ) embed.set_footer(text=f"User ID: {after.id} | Role ID: {role.id}") await log_channel.send(embed=embed) #Server Changes Log @commands.Cog.listener() async def on_guild_update(self, before, after, member): config = self._load_config() enable_log = config.getboolean("Logs","enable_action_log") if not enable_log: return log_channel = self._get_log_channel() if log_channel is None: return embed = discord.Embed( title="Server Updated", description=f"The server has been updated.", color=discord.Color.blue(), timestamp=discord.utils.utcnow() ) embed.add_field(name="Before", value=f"Name: {before.name}\nDescription: {before.description}\nOwner: {before.owner}", inline=False) embed.add_field(name="After", value=f"Name: {after.name}\nDescription: {after.description}\nOwner: {after.owner}", inline=False) embed.set_footer(text=f"Updated by: {member.mention} | Server ID: {before.id}") embed.set_footer(text=f"Server ID: {before.id}") await log_channel.send(embed=embed) #Voice channel log @commands.Cog.listener() async def on_voice_state_update(self, member, before, after): config = self._load_config() enable_log = config.getboolean("Logs","enable_action_log") if not enable_log: return log_channel = self._get_log_channel() if log_channel is None: return if before.channel is None and after.channel is not None: action = "joined" channel = after.channel elif before.channel is not None and after.channel is None: action = "left" channel = before.channel elif before.channel is not None and after.channel is not None and before.channel != after.channel: action = "moved from" channel = before.channel else: return embed = discord.Embed( title="Voice State Updated", description=f"{member.mention} has {action} the voice channel {channel.mention}.", color=discord.Color.purple(), timestamp=discord.utils.utcnow() ) embed.set_footer(text=f"User ID: {member.id}") await log_channel.send(embed=embed) def setup(bot: discord.Bot): bot.add_cog(actionlog(bot))