Search code examples
pythondiscorddiscord.py

Discord modal callback never called. The modal window gives a "Something went wrong" error, but no errors in console


Spawning the model from a command:

    @discord.app_commands.command(name="host_game_test", description="Host a new game")
    async def host_game_test(self, interaction: discord.Interaction):
        modal = HostGameModal(title="Host New Game", era=GameAge.EA)
        await interaction.response.send_modal(modal)

This works fine, creating the modal window. However, after filling it out and clicking submit, after a delay a red error message appears - "Something went wrong. Please try again." No errors are reported in the console at all.

from discord import Interaction, TextStyle
from discord.ui import TextInput, Modal

from utils import printlog


class HostGameModal(Modal):
    def __init__(self, era: str, *args, **kwargs):
        super().__init__(*args, **kwargs)
        self.era = era  # Store the era

        self.add_item(TextInput(label="Game Name", custom_id="game_name", placeholder="Enter your game's name"))
        self.add_item(TextInput(label="Max Players", custom_id="max_players", placeholder="Enter max number of players",
                                style=TextStyle.short))
        self.add_item(TextInput(label="Password", custom_id="password", placeholder="Enter a game password",
                                style=TextStyle.short))

    async def callback(self, interaction: Interaction):
        printlog("HostGameModal callback called.")
        try:
            await interaction.response.defer(ephemeral=True)

            game_name = self.children[0].value
            max_players = int(self.children[1].value)
            password = self.children[2].value
            # Use self.era here for the game's era
            await interaction.followup.send(f"Hosting a '{self.era}' game named '{game_name}' with max {max_players} "
                                            f"players and password '{password}'.")
        except Exception as e:
            printlog(f"Error in HostGameModal callback: {e}")
            await interaction.followup.send("An error occurred. Please try again later.", ephemeral=True)

Here's the Modal class. The printlog at the start of the callback function is never called, so it seems for some reason the callback is just never being called.

Have been stumped on this for a while, and there doesn't seem to be a huge amount of documentation about the modal stuff that I can find. Can anyone see what the problem might be?


Solution

  • Modals use on_submit method as the callback. Creating a method callback wouldn't be called because the modal is looking for the on_submit method.

    class MyModal(discord.ui.Modal):
        def __init__(self):
            super().__init__()
    
        async def on_submit(self, interaction: discord.Interaction):
            #  Do stuff
    

    For more: Modal, on_submit, Interaction