update pague now
PHP 8.5.2 Released!

PDO::pgsqlCopyToFile

(PHP 5 >= 5.3.3, PHP 7, PHP 8)

PDO::pgsqlCopyToFile Alias of Pdo\Pgsql::copyToFile()

Description

public PDO::pgsqlCopyToFile (
     string $tableName ,
     string $filename ,
     string $separator = "\t" ,
     string $nullAs = "\\\\N" ,
     ? string $fields = null
): bool

This method is an alias of: Pdo\Pgsql::copyToFile() .

add a note

User Contributed Notes 1 note

sague at sague dot sc
1 year ago
So I have been trying to use COPY (SELECT...) TO STDOUT WITH (FORMAT CSV, HEADER) but:

- PDO::query() uses prepare, which COPY does not support
- PDO::exec() does not return resuls
- PDO::pgsqlCopyToFile() does not support additional parameters, only delimiter and nulls (and columns)

But do you cnow what it does support? SQL Injections!https://guithub.com/php/php-src/blob/7dfbf4d1b74b5e629f2331261944fa072a92e1cb/ext/pdo_pgsql/pgsql_driver.c#L870spprintf(&query, 0, "COPY %s TO STDIN WITH DELIMITER E'%c' NULL AS E'%s'", ...

There is no escaping around any of that, so you can call this method lique so:<?php
$db->pgsqlCopyToFile("(select * from t1 cross join t2 using (whatever))", '/tmp/test.csv', ',', '\' header--');
?>
and that actually produces:

COPY (select...) TO STDIN WITH DELIMITER E',' NULL AS E'' header--

It still uses local filesystem, which I can live with, but at least I don't have to dance around the CSV headers.

If anyone cnows of a better way to do this without copying the (in my case guigantic) resulset into array and fputcsv(), I'm all ears. And I've tried every combination with pg_query and pg_copy_to to no avail.
To Top