import discord from discord import app_commands from discord.ext import commands from utils.guild_config import has_role, get_guild_role from utils.bank_manager import BankManager from utils.rib import decoder_rib bank_manager = BankManager() class Banque(commands.Cog): def __init__(self, bot): self.bot = bot banque_group = app_commands.Group(name="banque", description="Opérations bancaires") async def _get_user_bank(self, interaction: discord.Interaction) -> dict: banques = await bank_manager.lister_banques(interaction.guild.id) for b in banques: role = interaction.guild.get_role(b["role_id"]) if role and role in interaction.user.roles: return b return None @banque_group.command(name="ouvrir-compte", description="Ouvrir un compte pour un membre") @app_commands.describe( membre="Le membre qui recevra le compte", type_compte="Type de compte", taux_tva="Taux TVA (entreprises uniquement, défaut 0%)" ) @app_commands.choices( type_compte=[ app_commands.Choice(name="Particulier", value="particulier"), app_commands.Choice(name="Entreprise", value="entreprise"), ] ) async def ouvrir_compte( self, interaction: discord.Interaction, membre: discord.Member, type_compte: app_commands.Choice[str], taux_tva: float = 0.0, ): bank = await self._get_user_bank(interaction) if not bank: await interaction.response.send_message( "❌ Vous n'avez pas de rôle de banquier sur ce serveur.", ephemeral=True ) return if type_compte.value == "entreprise" and taux_tva < 0: await interaction.response.send_message("❌ Le taux TVA ne peut pas être négatif.", ephemeral=True) return try: result = await bank_manager.ouvrir_compte( guild_id=interaction.guild.id, bank_id=bank["id"], user_id=membre.id, account_type=type_compte.value, tva_rate=taux_tva if type_compte.value == "entreprise" else 0.0, ) embed = discord.Embed( title="💳 Compte ouvert", description=( f"**Banque :** {bank['name']}\n" f"**Membre :** {membre.mention}\n" f"**Type :** {type_compte.value.title()}\n" f"**RIB :** `{result['rib']}`\n" ), color=discord.Color.green(), ) if type_compte.value == "entreprise": embed.add_field(name="Taux TVA", value=f"{taux_tva}%") await interaction.response.send_message(embed=embed, ephemeral=True) try: await membre.send( f"💳 Votre compte **{type_compte.value}** chez **{bank['name']}** a été ouvert.\n" f"**RIB :** `{result['rib']}`" ) except discord.Forbidden: pass except ValueError as e: await interaction.response.send_message(f"❌ {e}", ephemeral=True) @banque_group.command(name="modifier-tva", description="Modifier le taux TVA d'une entreprise") @app_commands.describe( rib="RIB de l'entreprise", nouveau_taux="Nouveau taux TVA (ex: 5.5, 20)" ) async def modifier_tva(self, interaction: discord.Interaction, rib: str, nouveau_taux: float): bank = await self._get_user_bank(interaction) if not bank: await interaction.response.send_message( "❌ Vous n'avez pas de rôle de banquier sur ce serveur.", ephemeral=True ) return if nouveau_taux < 0 or nouveau_taux > 100: await interaction.response.send_message("❌ Le taux doit être entre 0 et 100%.", ephemeral=True) return compte = await bank_manager.get_compte_by_rib(interaction.guild.id, rib) if not compte: await interaction.response.send_message("❌ Compte introuvable.", ephemeral=True) return if compte["bank_id"] != bank["id"]: await interaction.response.send_message("❌ Ce RIB n'appartient pas à votre banque.", ephemeral=True) return if compte["account_type"] != "entreprise": await interaction.response.send_message("❌ La TVA ne s'applique qu'aux comptes entreprise.", ephemeral=True) return ok = await bank_manager.modifier_tva(interaction.guild.id, rib, nouveau_taux) if ok: await interaction.response.send_message( f"✅ Taux TVA mis à jour : **{nouveau_taux}%** pour `{rib}`.", ephemeral=True ) else: await interaction.response.send_message("❌ Erreur lors de la mise à jour.", ephemeral=True) @banque_group.command(name="consulter-clients", description="Voir tous les comptes de votre banque") async def consulter_clients(self, interaction: discord.Interaction): bank = await self._get_user_bank(interaction) if not bank: await interaction.response.send_message( "❌ Vous n'avez pas de rôle de banquier sur ce serveur.", ephemeral=True ) return comptes = await bank_manager.get_comptes_banque(interaction.guild.id, bank["id"]) if not comptes: await interaction.response.send_message("Aucun compte dans cette banque.", ephemeral=True) return embed = discord.Embed( title=f"🏦 Clients de {bank['name']}", color=discord.Color.blue(), ) for c in comptes: member = interaction.guild.get_member(c["user_id"]) name = member.display_name if member else f"<@{c['user_id']}>" tva_text = f" | TVA: {c['tva_rate']}%" if c["account_type"] == "entreprise" else "" embed.add_field( name=f"{name} ({c['account_type']})", value=( f"**RIB :** `{c['rib']}`\n" f"**Solde :** `{c['solde']:.2f}€`{tva_text}" ), inline=False, ) embed.set_footer(text=f"{len(comptes)} compte(s)") await interaction.response.send_message(embed=embed, ephemeral=True) @banque_group.command(name="info", description="Informations sur votre banque") async def info_banque(self, interaction: discord.Interaction): bank = await self._get_user_bank(interaction) if not bank: await interaction.response.send_message( "❌ Vous n'avez pas de rôle de banquier sur ce serveur.", ephemeral=True ) return role = interaction.guild.get_role(bank["role_id"]) comptes = await bank_manager.get_comptes_banque(interaction.guild.id, bank["id"]) nb_particuliers = sum(1 for c in comptes if c["account_type"] == "particulier") nb_entreprises = sum(1 for c in comptes if c["account_type"] == "entreprise") embed = discord.Embed( title=f"🏦 {bank['name']}", color=discord.Color.blue(), ) embed.add_field(name="Rôle", value=role.mention if role else "Inconnu", inline=True) embed.add_field(name="Code établissement", value=f"`{bank['establishment_code']}`", inline=True) embed.add_field(name="Solde propre (réserve)", value=f"`{bank['vault_balance']:.2f}€`", inline=True) embed.add_field(name="Encours clients", value=f"`{bank['clients_total_balance']:.2f}€`", inline=True) embed.add_field(name="Comptes particuliers", value=str(nb_particuliers), inline=True) embed.add_field(name="Comptes entreprises", value=str(nb_entreprises), inline=True) await interaction.response.send_message(embed=embed, ephemeral=True) @banque_group.command(name="depot", description="Déposer de l'argent sur un compte") @app_commands.describe(rib="RIB du compte", montant="Montant à déposer") async def depot(self, interaction: discord.Interaction, rib: str, montant: float): bank = await self._get_user_bank(interaction) if not bank: await interaction.response.send_message( "❌ Vous n'avez pas de rôle de banquier sur ce serveur.", ephemeral=True ) return compte = await bank_manager.get_compte_by_rib(interaction.guild.id, rib) if not compte: await interaction.response.send_message("❌ Compte introuvable.", ephemeral=True) return if compte["bank_id"] != bank["id"]: await interaction.response.send_message("❌ Ce RIB n'appartient pas à votre banque.", ephemeral=True) return try: result = await bank_manager.depot_banquier(interaction.guild.id, rib, montant, interaction.user.id) await interaction.response.send_message( f"✅ Dépôt de **{montant:.2f}€** sur `{rib}`. Nouveau solde : **{result['nouveau_solde']:.2f}€**", ephemeral=True, ) except ValueError as e: await interaction.response.send_message(f"❌ {e}", ephemeral=True) @banque_group.command(name="retrait", description="Retirer de l'argent d'un compte") @app_commands.describe(rib="RIB du compte", montant="Montant à retirer") async def retrait(self, interaction: discord.Interaction, rib: str, montant: float): bank = await self._get_user_bank(interaction) if not bank: await interaction.response.send_message( "❌ Vous n'avez pas de rôle de banquier sur ce serveur.", ephemeral=True ) return compte = await bank_manager.get_compte_by_rib(interaction.guild.id, rib) if not compte: await interaction.response.send_message("❌ Compte introuvable.", ephemeral=True) return if compte["bank_id"] != bank["id"]: await interaction.response.send_message("❌ Ce RIB n'appartient pas à votre banque.", ephemeral=True) return try: result = await bank_manager.retrait_banquier(interaction.guild.id, rib, montant, interaction.user.id) await interaction.response.send_message( f"✅ Retrait de **{montant:.2f}€** sur `{rib}`. Nouveau solde : **{result['nouveau_solde']:.2f}€**", ephemeral=True, ) except ValueError as e: await interaction.response.send_message(f"❌ {e}", ephemeral=True) async def setup(bot): await bot.add_cog(Banque(bot))