繁体   English   中英

异常处理的最佳实践:PDO + 控制器和存储库

[英]Best practice for exception handling: PDO + controllers & repositories

我已经搜索了使用 PDO 进行异常处理的最佳实践,但大多数示例仅从简单的一类方法中查看它。

如果我在 ORM 类型模型中使用控制器和存储库,那么各种 try/catch 和 throw 块应该在哪里发生?

一个简化的例子:

控制器:(创建 repo 对象,触发 loadProduct 方法,并加载模板)

class ProductController {
    public function viewProduct($product_id) {
        $ProductRepository = new ProductRepository($this->Pdo);
        $Product = $ProductRepository->loadProduct($product_id);
            
        include(__DIR__.'/../templates/product_template.php');
    }
}

模型/存储库:

class ProductRepository
{
    private $Pdo;
        
    public function __construct(PDO $Pdo)
    {
        $this->Pdo = $Pdo;
    }
            
    public function loadProduct($product_id,$withimages=0)
    {
        $Stm = $this->Pdo->prepare('
            SELECT p.product_id,p.model,p.price,p.prodinfo,pi.image_path
            FROM products p LEFT JOIN product_images pi
            ON p.product_id = pi.product_id
            WHERE p.product_id = :product_id
            AND pi.is_primary = 1
        ');
        $Stm->bindParam(':product_id',$product_id,PDO::PARAM_INT);
        $Stm->execute();
    
        return $this->arrayToObject($Stm->fetch(PDO::FETCH_ASSOC));    
    }
}

是否应该将 try/catch 块放入控制器中,并在execute()返回任何内容时抛出异常? 如果$Pdo->prepare()方法没有触发,则抛出一个单独的异常?

一般来说,异常处理策略非常简单。 尤其是 PDO。 因为 PDO 只有在严重故障的情况下才会抛出一个,并且继续执行几乎没有意义——所以,默认暂停就可以了。

因此,对于代码的平均部分,无论是模型、存储库还是其他任何东西,根本不需要专门的处理。

只有在某些地方,您有查询失败的场景,才必须使用 try-catch。 最常用的场景是事务回滚。 因此,如果您有事务,您可能希望将其包装在try ,然后在catch.回滚catch.

要回答评论中的澄清:

这是两个本质上不同的场景:

  • 如果 SELECT 找不到产品,也没什么特别的。
  • 如果 INSERT 以某种方式创建了无效的 SQL 查询,那确实是一场灾难。

他们需要不同的处理方式。

对于第一种情况,您根本不需要任何例外,这是常规行为。 只要在你的模板中有一个分支,上面写着“没有找到”

对于第二个,创建一个自定义异常处理程序,记录错误,发送 503,并显示通用 503 错误页面。

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM