【问题标题】:Efficient and Transaction-safe Ways to Process Millions of Rows with Multiple Table Joins in Laravel 5.4在 Laravel 5.4 中处理具有多个表连接的数百万行的高效且事务安全的方法
【发布时间】:2017-08-17 02:28:59
【问题描述】:

这不一定只适用于 Laravel php 框架,因为我相信我的预期任务也可以在 MySQL 服务器本身上使用适当的 SQL 语句进行处理。

有以下3个表:

用户(>200 万行)

  • 身份证
  • 姓名
  • 余额(十进制、14、2)
  • package_id

包(5 行)

  • 身份证
  • 姓名
  • 值(十进制、14、2)
  • 百分比(十进制、5、2)- 存储为 0.10 而不是 10

事务(日志)

  • 身份证
  • user_id
  • 说明
  • 金额

以上所有表格都分别链接到对象/模型 User、Package 和 Transaction。它们包含时间戳列,并由 Laravel 自动插入/更新。

  1. 应用程序计划根据包的 value(分配给用户)更新表 users 中的列 balance每天午夜 12:00 乘以 percent 字段加上原始余额值。更清晰的表达是:

    users.balance = users.balance + (packages.value * packages.percent)

  2. 同时,应将每次余额更新的事务日志插入数据库:

    user_id: [用户 ID]
    描述:用新余额更新了用户 [用户名]
    金额:[添加金额]

我已经设法使用以下 SQL 语句实现了第一个操作:

UPDATE users 
INNER JOIN packages 
ON users.package_id = packages.id
SET users.balance = users.balance + (packages.value * packages.percent);

我似乎找不到任何解决方案以最高效率和交易安全的方式同时实现这两项操作。我可能会同时检索用户和包并在应用程序中处理它们,然后执行更新和插入,但这将是一件不费吹灰之力的事情,因为它确实效率低下。

如果有人可以帮助我解决问题,我将不胜感激!

【问题讨论】:

    标签: php mysql laravel join transactions


    【解决方案1】:

    Luke 您想更新用户记录并同时使用相同的查询插入日志记录。您应该检查 Mysql 重复密钥更新。 我建议检查此链接。 https://dev.mysql.com/doc/refman/5.7/en/insert-on-duplicate.html http://www.digimantra.com/tutorials/insert-update-single-mysql-query-duplicate-key/

    【讨论】:

      【解决方案2】:

      我看不到任何可能的方法来更新或插入 mysql 中的两个不同表。我知道用一个查询更新 2 个不同的表,但不能在 2 个不同的表上插入和更新。我认为你可以使用触发器来实现你想要的

      CREATE TRIGGER insert_into_logs_when_user_balance_update
      AFTER UPDATE ON users 
      FOR EACH ROW
        IF NEW.balance <> OLD.balance
        then
          insert into logs(user_id, description, amount)
          values(New.id, New.balance, New.balance)
        END IF
      

      这将在 users.balance 更改/更新时更新日志表。

      希望这会有所帮助。

      【讨论】:

      • 这很完美!还有一个问题,当我尝试上面的方法时,似乎只使用了 24 个内核中的 2-3 个,处理 100 万用户需要 24 秒(服务器有 90GB RAM 和 SSD)。我试过将innodb R/W线程增加到48个,速度还是差不多的。关于如何减少执行时间的任何想法?
      • 您可以将innodb_thread_concurrency 设置为0 以实现无限并发。
      猜你喜欢
      • 1970-01-01
      • 2012-12-26
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2010-10-18
      • 1970-01-01
      • 2012-11-25
      相关资源
      最近更新 更多