'How to report ModelNotFoundException with stacktrace to Sentry.io in Laravel 6?

I am using below laravel 6 code to report exceptions to Sentry.io:

public function report(Exception $exception)
{
    if ($this->shouldReport($exception) && app()->bound('sentry')) {
        app('sentry')->captureException($exception);
    }

    parent::report($exception);
}

All the exceptions are able to report to sentry. However recently I found that ModelNotFoundException is not sending to Sentry. Also I found the reason and it is due to the presence of ModelNotFoundException in the below code of the file (Illuminate\Foundation\Exceptions\Handler.php):

protected $internalDontReport = [
        AuthenticationException::class,
        AuthorizationException::class,
        HttpException::class,
        HttpResponseException::class,
        ModelNotFoundException::class,
        SuspiciousOperationException::class,
        TokenMismatchException::class,
        ValidationException::class,
    ];

As inbuilt code and I cannot remove ModelNotFoundException in the above code. Is there a way to send the ModelNotFoundException to sentry?



Solution 1:[1]

The $internalDontReport is protected so you could override it, although it's probably better not too since the list might change in the future and would require you to keep it in sync.

You can remove the $this->shouldReport($exception), however this will cause all of those ignored exception to be reported which might not be what you want.

You could do something like this in case you only care about the ModelNotFoundException:

    protected $doReportToSentry = [
        \Illuminate\Database\Eloquent\ModelNotFoundException::class,
    ];

    public function report(Exception $e)
    {
        if ($this->shouldReportToSentry($e) && app()->bound('sentry')) {
            app('sentry')->captureException($e);
        }

        parent::report($e);
    }

    protected function shouldReportToSentry(Exception $e)
    {
        if ($this->shouldReport($e)) {
            return true;
        }

        return !is_null(\Illuminate\Support\Arr::first($this->doReportToSentry, function ($type) use ($e) {
            return $e instanceof $type;
        }));
    }

You can add to that $doReportToSentry array any class you want to make sure it is reported even though Laravel might (by default) ignore it.

Sources

This article follows the attribution requirements of Stack Overflow and is licensed under CC BY-SA 3.0.

Source: Stack Overflow

Solution Source
Solution 1 Alex Bouma