У меня есть приложение Laravel 4.2 со следующим маршрутом:
Route::group(['prefix' => 'api/v1'], function()
{
Route::resource('service_logs', 'ServiceLogsController', [
'only' => ['index', 'store', 'show']
]);
});
ServiceLogsController
контроллер простирается от ApiController
, который выглядит примерно так урезанная версия:
class ApiController extends \BaseController {
protected $statusCode = 200;
public function getStatusCode()
{
return $this->statusCode;
}
public function setStatusCode($statusCode)
{
$this->statusCode = $statusCode;
return $this;
}
public function respondInternalError($message = 'Internal Error!')
{
return $this->setStatusCode(500)->respondWithError($message);
}
public function respondWithError($message)
{
return Response::json([
'error' => [
'message' => $message,
'status_code' => $this->getStatusCode()
]
], $this->getStatusCode());
}
// ...
}
Что я хотел бы сделать, так это то, что когда возникает неуловимое исключение, я хочу вызвать respondInternalError()
метод на моем ApiController
, так что потребитель API имеет последовательный ответ, а не ничего или HTML whoops
ошибка.
Чтобы добиться этого, я попытался добавить следующий код в моем app/start/global.php
App::error(function(Exception $exception, $code)
{
Log::error($exception);
if (Request::is('api/*'))
{
App::make('ApiController')->respondInternalError('Uncaught api exception error occurred - ' . $exception->getMessage());
}
});
и чтобы проверить это, я попытался сделать запрос POST на следующий URL: / api / v1 / service_logs / 123.
это не сработает, потому что этот URL является URL-адресом GET, поэтому Laravel выдает правильный method not allowed exception
, Тем не менее, это не попасться.
Любая идея, как реализовать обработчик исключений catch all для каждого класса контроллера?
Обновить Немного улучшен рабочий «глобальный» обработчик исключений API
App::error(function(Exception $exception, $code)
{
Log::error($exception);
if (Request::is('api/*'))
{
$errorName = Symfony\Component\HttpFoundation\Response::$statusTexts[$code];
return App::make('ApiController')
->setStatusCode($code)
->respondWithError($errorName . ' error has occurred.');
}
});
Когда происходит ошибка, вы получаете это сейчас (тестирование сделано в Chrome + Почтальон):
Решение на самом деле очень, очень просто. Вам нужно только вернуть возвращаемое значение вашей функции контроллера
if (Request::is('api/*'))
{
return App::make('ApiController')->respondInternalError('Uncaught api exception error occurred - ' . $exception->getMessage());
}
Других решений пока нет …