У меня есть база данных PostgreSQL, и мне нужно запросить таблицу, которая содержит 20 миллионов строк. Затем я пу sh результат набора в CSV и, наконец, в S3. Я скомпилировал php скрипт для достижения этой цели. Когда я ограничиваю свой запрос 6 миллионами строк, он успешен, но все, что выше этого, в значительной степени просто кажется неудачным Сообщения об ошибках не регистрируются и не отображаются даже при включенной проверке ошибок и включенных параметрах. Также увеличил объем памяти на моем экземпляре Centos до 3 ГБ и действительно не повезло. Мой код выглядит следующим образом:
//connect to database
$myPDO = new PDO('pgsql:host=127.0.0.1;port=5433;dbname=test', 'test', 'test');
$myPDO->setAttribute(PDO::ATTR_ERRMODE, PDO::ERRMODE_WARNING);
//time and memory usage variables
error_reporting(-1);
$time = microtime(TRUE);
$mem = memory_get_usage();
$stmt = $myPDO->prepare("SELECT * FROM table");
$stmt->execute();
$u = "export.csv";
$h = fopen($u, "w+");
$first = true;
//counter
$counter = 0;
//loop through all rows
while ($row = $stmt->fetch(PDO::FETCH_ASSOC)) {
$counter++;
//export column header
if ($first) {
fputcsv($h, array_keys($row));
$first = false;
}
//export content
fputcsv($h, $row);
}
fclose($h);
require('AwsS3Upload.php');
//pdo error output
if (!$stmt) {
echo "\nPDO::errorInfo():\n";
print_r($dbh->errorInfo());
}
print_r(array('memory' => (memory_get_usage() - $mem) / (1024 * 1024), 'seconds' => microtime(TRUE) - $time));
обновление - рабочий код:
$myPDO = new PDO('pgsql:host=127.0.0.1;port=5433;dbname=test', 'test', 'test');
$myPDO->setAttribute(PDO::ATTR_ERRMODE, PDO::ERRMODE_WARNING);
$myPDO->setAttribute(PDO::ATTR_EMULATE_PREPARES, false);
$myPDO->setAttribute(PDO::ATTR_STRINGIFY_FETCHES, false);
//time and memory usage variables
error_reporting(-1);
$time = microtime(TRUE);
$mem = memory_get_usage();
for($i=0; $i<6; $i++){
$limit = 5000000;
$offset = $i * $limit;
$sql = 'SELECT * FROM table ORDER BY :order LIMIT :limit OFFSET :offset';
$stmt = $myPDO->prepare($sql);
$stmt->bindParam(':order', $order, PDO::PARAM_INT);
$stmt->bindParam(':limit', $limit, PDO::PARAM_INT);
$stmt->bindParam(':offset', $offset, PDO::PARAM_INT);
$stmt->execute();
$u = "$i-export.csv";
$h = fopen($u, "w+");
$first = true;
//counter
$counter = 0;
while ($row = $stmt->fetch(PDO::FETCH_ASSOC)) {
$counter++;
if ($first) {
fputcsv($h, array_keys($row));
$first = false;
}
fputcsv($h, $row);
}
fclose($h);
require('AwsS3Upload.php');
}