Search code examples
c#exceptionbotsdiscorddiscord.net

Discord.NET - Get Which Type of Exception was Thrown in Command


I thought it would be easier to throw exceptions if say a person didn't have the right permissions to run a command, or there is a cooldown, or whatever, instead of just handling that every... single... time. So I made my own exceptions, but the problem is, that CommandService.ExecuteAsync().Error only returns the CommandError.Exception, with no way (as far as I can tell) to find out which type of exception was thrown.

My code is as follows:

try { var result = await _service.ExecuteAsync(context, argPos);

            if (!result.IsSuccess)
                switch (result.Error)
                {
                    case CommandError.BadArgCount:
                        await context.Channel.SendMessageAsync("Bad argument count.");
                        break;
                    case CommandError.UnknownCommand:
                        break;
                    case CommandError.Exception:
                        // This is what happens instead of the catch block.
                        break;
                    default:
                        await context.Channel.SendMessageAsync($"You 👏👏 Broke 👏👏 It ({result.ErrorReason})");
                        break;

                }
        }
        catch (Exceptions.GameCommandNotReadyException e)
        {
            // The code never gets here because of the CommandError.Exception
        }

Solution

  • You probably do not want to use try/catch there, as you would unnecessarily throw your own exception and then catch it directly afterwards. You can just put your error handling into the case CommandError.Exception.

    If you want to know more about the exception that led to the error:

    Since you're calling the ExecuteAsync function, it is likely that the "result" is not only of type IResult, but of type ExecuteResult. That would mean there is a property "Exception" that stores "what went wrong".

    case CommandError.Exception:
        if (result is ExecuteResult execResult)
        {
            //you can now access execResult.Exception to see what happened
        }
    
    break;