[fpc-pascal] sqldb, copy table between databases is painfully slow
Luca Olivetti
luca at ventoso.org
Tue Feb 18 16:02:08 CET 2025
El 18/2/25 a les 14:49, Michael Van Canneyt via fpc-pascal ha escrit:
>
>
> On Tue, 18 Feb 2025, Luca Olivetti via fpc-pascal wrote:
>
>> Hello,
>>
>> I need to copy a table between an mssql database and a postgresql one.
>> I used a query to obtain the data, a datasource ponting to it and
>> another query using the datasource, the sql being
>>
>> INSERT INTO table (f1,f2,f3...) values (:f1,:f2,:f3,....)
>>
>>
>> and then doing
>>
>>
>> OrigTable.Open;
>> PQTrans.StartTransaction;
>> while not OrigTable.Eof do
>> begin
>> DestTable.ExecSql;
>> OrigTable.Next;
>> end;
>> PQTrans.Commit;
>> OrigTable.Close;
>>
>>
>> this works but it's too slow (it takes about 700ms for each ExecSql),
>> because it's constantly preparing and unpreparing the statement.
>>
>> If I manually prepare an insert statement for each original record and
>> use it with ExecuteDirect it only takes 30ms, considering that I
>> access the server through a vpn I think it's normal.
>>
>>
>> I'm quite sure it's a PEBKAC, so, is there a way to reduce the time
>> for the ExecSql?
>
> You must prepare the desttable query before starting the loop.
> Then it does not need to prepare/unprepare.
Silly me, I knew it was a PEBKAC ;-) Thank you.
OrigTable.Open;
PQTrans.StartTransaction;
DestTable.Prepare; // <------- that's it
while not OrigTable.Eof do
begin
DestTable.ExecSql;
OrigTable.Next;
end;
DestTable.UnPrepare;
PQTrans.Commit;
OrigTable.Close;
still a bit slower than manually constructing the query (47ms vs 30ms)
but it works.
>
> the faster way is using a foreign table definition in Postgres, though.
> You can then do the copy with 1 statement.
I know, but I don't want to go that route (at least not now).
Bye
--
Luca
More information about the fpc-pascal
mailing list