如何将抛出的错误传回控制器?

时间:2016-03-10 15:19:41

标签: php oop laravel

我有一个控制器:

$objImporter->import('filename');

然后是一个类:

public function import ($filename){

if(this->notExcelFile){
    return "not an excel file";
}
else carry on
}

而不是有很多返回(我只喜欢函数的一个退出,在底部)我通常抛出异常,然后在catch中返回它。

这是最好的方法吗?我最初是一名VB开发人员,并想知道是否有更好的OO方式来做到这一点?

米克

4 个答案:

答案 0 :(得分:2)

将try catch块添加到控制器:

try {
    $objImporter->import('filename');
} catch (Exception $e) {
    //Do something with error. You can send mail alert. 
}

如果发生任何错误,则抛出异常。

public function import ($filename) {
    if(this->notExcelFile){
        throw new Exception('Given file is not an Excel file');
    } else {
       //Your logic goes here
    }
}

答案 1 :(得分:1)

答案很简单,抛出异常。如今,这在Java / PHP代码库中非常流行。但实际上,使用Exceptions进行控制流会破坏OO设计。消息是在对象之间发送的,但是由于使用了Try / catch,您的代码开始上下跳动,不规则且不可能跟随控制流。

更为纯粹主义者,在OO理想世界中,你将返回的是某种Result对象,它包含操作是否成功以及它是否成功的原因。类似的东西:

public function import ($filename){
    if (this->notExcelFile) {
        return new UnsuccessfulResult("not an excel file");
    }
    else {
        //carry on
        return new SuccessfulResult($excelFile);
    }
}

调用者会像以下一样工作:

$result = $objImporter->import('filename');
if(!$result->succeded()) {
    //show error to the user
}

// continue with a successful result
$exelFile = $result->getResult();

你会如何实现这样的目标?

您可以创建ResultLike

等界面
interface ResultLike {
    /** @return boolean */
    public function succeeded();
    /** @return mixed */
    public function getResult();
}

然后您可以在对象中实现:

class UnsuccessfulResult implements ResultLike {
    public function __construct($message) {
        $this->message = $message;
    }

    public function succeeded() {
        return false;
    }

    /** @return mixed */
    public function getResult() {
        return $this->message;
    }
}

class SuccessfulResult implements ResultLike {
    public function __construct($result) {
        $this->result = $result;
    }

    public function succeeded() {
        return true;
    }

    /** @return mixed */
    public function getResult() {
        return $this->result;
    }
}

快乐的日子

答案 2 :(得分:0)

一个好的做法是检查它是Excel文件并返回数据或链接到数据(如果它是Excel)。如果它不是Excel文件,您应该return false(或者在某些情况下return -1),例如。

然后在控制器中你只是检查数据,如:

if($data){
    // It's not Excel file, there is not data
}else{
    // work with data
}

答案 3 :(得分:0)

异常是好的,比返回“null”或“不是excel文件”之类的虚假结果要好得多。

更多“OOP-ish”方法是使用Null object pattern

在代码中你可以有这样的东西:

public function import ($filename) {
    if(this->notExcelFile){
       return new NullExcelFile();
    } else {
       //read the data
       return new ExcelFile($data);
    }
}

让我们假设你有一个API方法,它将excel文件内容作为json:

返回
$excel = import('path/to/the/file');
$jsonData = $excel->asJson();
echo json_encode($jsonData);

现在您不必担心文件是否存在,现在处理“null”,没有异常处理,无论文件是否存在,代码都以相同的方式工作。

当然,返回的响应会有所不同,真正的ExcelFile将返回带有文件内容的j​​son,而NullExcelFile将返回带有错误的json,例如{"error": "no_file", "message": "The specified file does not exist"}。客户端代码将处理它并为用户呈现错误消息。