0

在我继续之前,这纯粹是一个直觉问题。也就是说,我不是在寻找解决我的 PHP/MySQL 代码中特定错误的答案。相反,我想了解在解决我的问题时需要考虑的可能问题范围。为此,我不会发布代码或附加脚本 - 我将简单地解释我做了什么以及发生了什么。

我已经编写了 PHP 脚本

  1. 读取 X 记录的 CSV 文本文件以插入 MySQL 数据库表和/或更新适用的重复条目;
  2. 将所述记录插入我将称为该数据集的“根”表中;
  3. 从“根”表中选择特定字段的子集记录,然后将这些记录插入“主”表;和
  4. 从主表创建输出导出文本文件以进行分发。

我每 30 分钟通过单独的计划 cron 任务处理几个 CSV 文件。总而言之,从各种来源来看,估计有 420,000 个从文件到根表的插入事务,另外还有 420,000 个通过计划任务从根表到主表的插入事务。

其中一项任务涉及一个包含大约 400,000 条记录的 CSV 文件。处理过程没有错误,但问题是:在 MySQL 指示已成功插入根表的 400,000 条记录中,只有大约 92,000 条记录实际存储在根表中 - 我从计划中丢失了大约 308,000 条记录任务。

其他计划任务分别处理大约 16,000 和 1,000 个事务,并且这些事务处理完美。事实上,如果我将交易数量从 400,000 减少到 10,000,那么这些过程也很好。显然,这不是这里的目标。

为了解决这个问题,我尝试了几种补救措施......

  1. 增加我的服务器的内存(并增加 php.ini 文件中的最大限制)
  2. 获得具有扩展内存的专用数据库(与共享 VPS 数据库相反)
  3. 重写我的代码以大大消除存储数组,这些数组会占用内存并在运行时处理 fgetcsv() 进程
  4. 使用 INSERT DELAYED MySQL 语句(与普通的 INSERT 语句相反)

...而且这些补救措施都没有达到预期的效果。

鉴于迄今为止采取的行动缺乏成功,此时应考虑采取何种范围的补救行动?谢谢...

4

2 回答 2

0

我怀疑 CSV 文件有问题。

我的建议:

  • 在从 CSV 读取的每一行上打印一些用于调试信息的内容。这将显示处理了多少行。
  • 在每次插入/更新时,打印任何错误(如果有)

是这样的:

<?php
$csv = fopen('sample.csv', 'r'); $line = 1;
while (($item = fgetcsv($csv)) !== false) {
    echo 'Line ' . $line++ . '... ';

    $sql = ''; // your SQL query
    mysql_query($sql);
    $error = mysql_error();

    if ($error == '') {
        echo 'OK' . PHP_EOL;
    } else {
        echo 'FAILED' . PHP_EOL . $error . PHP_EOL;
    }
}

因此,如果有任何错误,您可以查看并找到问题(CSV 的哪些行有问题)。

于 2012-04-18T13:32:56.537 回答
0

csv 中的源数据可能有重复记录。即使 csv 中有 400,000 条记录,您的“插入或更新”逻辑也会将它们修剪成缩减集。更少的内存可能会导致异常等,但这种数据丢失。

于 2012-04-15T03:25:44.783 回答