• PHP:PDO 事务示例


    在本指南中,我们将向您展示如何将事务与 PHP 的 PDO 对象一起使用。

    对于那些不知道的人,数据库事务代表一个“块”或一个“单元”工作。

    在大多数情况下,这个工作“单元”将由多个查询组成,这些查询以某种方式相互关联。

    在某些情况下,您可能希望确保在将更改提交到数据库之前成功执行所有查询。

    对于这个例子,我们将创建一个模拟 PHP 应用程序,为用户帐户添加资金。

    在这种情况下,我们有两个查询。第一个将支付记录插入一个名为“payments”的表中。第二个将更新用户帐户的余额。

    1. /**
    2. * Connect to MySQL and instantiate the PDO object.
    3. * Set the error mode to throw exceptions and disable emulated prepared statements.
    4. */
    5. $pdo = new PDO('mysql:host=localhost;dbname=test', 'root', '', array(
    6. PDO::ATTR_ERRMODE => PDO::ERRMODE_EXCEPTION,
    7. PDO::ATTR_EMULATE_PREPARES => false
    8. ));
    9. //We are going to assume that the user with ID #1 has paid 10.50.
    10. $userId = 1;
    11. $paymentAmount = 10.50;
    12. //We will need to wrap our queries inside a TRY / CATCH block.
    13. //That way, we can rollback the transaction if a query fails and a PDO exception occurs.
    14. try{
    15. //We start our transaction.
    16. $pdo->beginTransaction();
    17. //Query 1: Attempt to insert the payment record into our database.
    18. $sql = "INSERT INTO payments (user_id, amount) VALUES (?, ?)";
    19. $stmt = $pdo->prepare($sql);
    20. $stmt->execute(array(
    21. $userId,
    22. $paymentAmount,
    23. )
    24. );
    25. //Query 2: Attempt to update the user's profile.
    26. $sql = "UPDATE users SET credit = credit + ? WHERE id = ?";
    27. $stmt = $pdo->prepare($sql);
    28. $stmt->execute(array(
    29. $paymentAmount,
    30. $userId
    31. )
    32. );
    33. //We've got this far without an exception, so commit the changes.
    34. $pdo->commit();
    35. }
    36. //Our catch block will handle any exceptions that are thrown.
    37. catch(Exception $e){
    38. //An exception has occured, which means that one of our database queries
    39. //failed.
    40. //Print out the error message.
    41. echo $e->getMessage();
    42. //Rollback the transaction.
    43. $pdo->rollBack();
    44. }

    在此示例中,我们确保在提交更改之前所有查询都成功。

    换句话说,如果第二个查询无法更新用户的信用余额,我们不想在支付表中插入记录。

    我们的 PDO 事务代码的解释。

    上面的PHP代码的一步一步的解释:

    1. 首先,我们使用 PDO 对象连接到 MySQL 。我们将错误模式设置为 PDO::ERRMODE_EXCEPTION以便 PHP 在发生错误时抛出 PDO 异常。我们还通过将PDO::ATTR_EMULATE_PREPARES设置为 false 来禁用模拟的预处理语句。
    2. 为了这个例子,我们将用户 ID 设置为 1,支付金额设置为 10.50。
    3. 我们首先打开Try / Catch块。我们所有的查询都将发生在这个“尝试块”内,以便我们可以捕获任何可能发生的异常。
    4. 我们通过调用beginTransaction函数在 Try 块中开始我们的事务。当我们调用这个函数时,它将禁用 MySQL 的自动提交模式。这意味着 MySQL 在我们告诉它之前不会提交任何更改。
    5. 之后,我们尝试将付款插入到付款表中。
    6. 然后,我们使用新的信用计数更新用户的帐户。
    7. 最后,我们通过调用commit函数来提交事务。

    如果我们的查询之一失败,则会抛出 PDO 异常

    如果发生这种情况,我们的 catch 块内的代码将执行。

    在那个阶段,MySQL 将中止事务并回滚任何更改。

    交易条款。

    一些关键术语的快速解释。

    • 开始事务:事务从禁用 MySQL 的默认自动提交性质开始。例如,如果您运行 INSERT 查询,MySQL 将不会提交更改。相反,它将“保留”查询,直到您手动提交它。
    • 提交:当您提交事务时,您基本上是在告诉 MySQL 它应该继续并保存任何更改。这是“一切顺利”的另一种说法。您现在可以保存这些更改。”
    • Rollback:当你执行回滚时,你是在告诉 MySQL 中止事务并丢弃任何更改。通常,只有在查询失败时才会发生回滚。
  • 相关阅读:
    窗口-视口转换(详细)
    堆结构的深度理解
    干货分享,快来看这两款优质软件
    李飞飞:云原生数据库是大势所趋
    【MATLAB】全网唯一的11种信号分解+模糊熵(近似熵)联合算法全家桶
    【Python开发】Flask项目的组织架构
    金仓数据库KingbaseES安全指南--6.3. Kerberos身份验证
    提高Oracle数据库缓存命中率
    什么是数据同步利器DataX,如何使用?
    Qt QObject::connect: Cannot queue arguments of type ‘***’
  • 原文地址:https://blog.csdn.net/allway2/article/details/126887427