Laravel异常处理 - 如何使用API​​和Html处理异常

时间:2013-09-30 21:10:13

标签: exception-handling laravel laravel-4

Api Call

http://localhost:8888/api/v1/users/100 //doesn't exist

Html Call

http://localhost:8888/admin/users/100 //doesn't exist

显然,我不希望Html Call异常返回json数据,我不希望Api Call返回Html Data。

我不是控制器中的异常处理。我在UserRepository中处理异常。因此,我的控制器只是从用户存储库返回结果。

class Sentry2UserRepository implements UserInterface {
public function findById($id) {
    try {
        return Sentry::findUserById($id);
    }
    catch (\Cartalyst\Sentry\Users\UserNotFoundException $e) {
    // Do something here
    return false;
        }
}
}

问题1:将错误传回控制器的正常/正确方法是什么,以便知道要显示什么?

问题2:异常/错误是否有标准的json API格式?

问题3:Web UI使用内部JsonApi是一种好习惯吗?或者我是否正在使用我的WebUi控制器以正确的方式查询与Api相同的存储库?

2 个答案:

答案 0 :(得分:3)

在您的filters.php中尝试这个魔术:

App::error(function(Exception $exception, $httpCode)
{
    if (Request::is('api/*')){
         return Response::json( ['code' => $exception->getCode(), 'error' => $exception->getMessage()], $httpCode );
    }else{
         $layout = View::make('layouts.main');
         $layout->content = View::make('errors.error')->with('code', $exception->getCode())->with('error', $exception->getMessage())->with('httpCode',$httpCode);
         return Response::make($layout, $httpCode);
    }
});

答案 1 :(得分:0)

首先,我认为您在Sentry2UserRepository中的做法并不差,没关系,IMO

  

问题1:将错误传回的正常/正确方法是什么?   控制器,以便它知道要显示什么?

那么,IMO,根据应用程序,您应该确定应该如何处理异常。您提到了so that it will know what to display,在这种情况下,它取决于异常在需要发生异常后采取下一步操作所需的信息和信息。现在,如果您需要错误消息,那么您可以返回return $e->getMessage(),这样您就可以确切地知道实际发生了什么。有很多方法可以做到这一点,例如,使用单个catch

try{
    // ...
}
catch( Exception $e )
{
    if ($e instanceof UserNotFoundException) {
        // it's an instance of UserNotFoundException, return accordingly
    }
    elseif ($e instanceof SomethinElseException) {
        // it's an instance of SomethinElseException, return accordingly
    }
}

此外,您可以使用不同的自定义异常类,并可以使用多个catch块,即

class AnException extends Exception 
{
    public function customErrorMessage() 
    {
        return `AnException occurred!`
    }
}

class AnotherException extends Exception 
{
    public function customErrorMessage() 
    {
        return `AnotherException occurred!`
    }
}

然后使用多个catch块来捕获,即

try 
{
    // ...
}

catch(AnException $e) 
{
    return $e->customErrorMessage();
}

catch(AnotherException $e) 
{
    return $e->customErrorMessage();
}
catch(Exception $e)
{
    return $e->getMessage();
}
  

问题2:异常/错误是否有标准的json API格式?

     

问题3:Web UI使用内部JsonApi是一种好习惯吗?或者我是否正在使用我的WebUi控制器以正确的方式查询与Api相同的存储库?

实际上我不知道这样的api你做得对,IMO。这是因为,你有这个

class Sentry2UserRepository implements UserInterface {
    public function findById($id) {
        try {
            return Sentry::findUserById($id);
        }
        catch (\Cartalyst\Sentry\Users\UserNotFoundException $e) {
            // Do something here
            return false;
        }
    }
}

因此,可以在控制器中编写类似这样的代码

if(findById(5)) {
    // found and dump it to the view
}
else {
    // show "Not Found !", false will be back only for UserNotFoundException 
}

但是,如果你在UserNotFoundException捕获

中有这个
return $e; // or anything else (maybe an array containing status and message)

然后编写这个简单的代码

是不可能的
if(findById(5)) {
    // found and dump it to the view
}

因为,对于数组,$e对象oe的语句是真的,所以你必须再次检查它,使用像这样的somrthing

$result = findById(5);
if($result && $result->code && $result->code === 0) {
    // something according to code
}

或许,像这样的事情

if($result && $result->code) {
    // error happened, now determine the code
    switch($result->code){
        case 0:
        // show message
        break;

        case 1:
        // show message
        break;
    }
}

所以,IMO,为什么,你需要向用户展示,你的应用程序中发生了什么错误,为什么不只是为了状态,要么你有数据,要么你没有得到它。这不简单吗?只需KISS。这只是我的看法,就是这样。