Received: from malur.postgresql.org ([217.196.149.56]) by arkaria.postgresql.org with esmtps (TLS1.2:ECDHE_RSA_AES_256_CBC_SHA1:256) (Exim 4.89) (envelope-from ) id 1hoQE7-0006lY-HF for pgsql-interfaces@arkaria.postgresql.org; Fri, 19 Jul 2019 10:34:59 +0000 Received: from localhost ([127.0.0.1] helo=malur.postgresql.org) by malur.postgresql.org with esmtp (Exim 4.89) (envelope-from ) id 1hoQE5-0008EA-Q2 for pgsql-interfaces@arkaria.postgresql.org; Fri, 19 Jul 2019 10:34:57 +0000 Received: from magus.postgresql.org ([2a02:c0:301:0:ffff::29]) by malur.postgresql.org with esmtps (TLS1.2:ECDHE_RSA_AES_256_CBC_SHA1:256) (Exim 4.89) (envelope-from ) id 1hoQE5-0008E3-Gm for pgsql-interfaces@lists.postgresql.org; Fri, 19 Jul 2019 10:34:57 +0000 Received: from mail-lj1-x243.google.com ([2a00:1450:4864:20::243]) by magus.postgresql.org with esmtps (TLS1.2:ECDHE_RSA_AES_256_CBC_SHA1:256) (Exim 4.89) (envelope-from ) id 1hoQDy-00012S-5A for pgsql-interfaces@postgresql.org; Fri, 19 Jul 2019 10:34:56 +0000 Received: by mail-lj1-x243.google.com with SMTP id v18so30275836ljh.6 for ; Fri, 19 Jul 2019 03:34:49 -0700 (PDT) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=gmail.com; s=20161025; h=mime-version:references:in-reply-to:from:date:message-id:subject:to :cc; bh=MH5f+Jrl+axjW+TXDNtj6/bYVq4MpykmlP/CZf8AOz8=; b=eJC6g2UdC9rm8YxKoLLMavaZX/A1Dy1Luwjxq7FEkRCYvBqrED0t5JrFT1+Bqsseeg 3KIpOyxxUiBGslti/SGWc2J+tDhhKDKMGob09zXCQA8rCgZ2XPPFz4/HwODAX4AU+AJZ svmTN9JMQ30/+PW7/hwnwwbhg6D9dS/J9RRuL9jq4MxOmQ7KDWzZ4fNuctB69f6J+d55 7jYokpHx/K4UIbY9ipzCk3DBrtaf+GkMplJlu5KBmh5pUTPZnXFA4k7qlHuBIIG8Dysv UijBHZsO59XiUPKes9ky3NxHqmaYTZvyxEh03MJoTvyeDQbr1kF9y+ODC314O+Nh9APS 6LWw== X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20161025; h=x-gm-message-state:mime-version:references:in-reply-to:from:date :message-id:subject:to:cc; bh=MH5f+Jrl+axjW+TXDNtj6/bYVq4MpykmlP/CZf8AOz8=; b=rKCp9B3OX5CeeSif7AOnWaHrz7LdYL4styzF6FGCFfQAhKzXUpWhRujJEeRm+x41ze yNVoU7PG1KK3cZH7oSw+jzLJY6e+ElLIrDc3t0C35G5gdCFS8cWKdyKljtxc6HqqwWPk xY6KOk6UmPy+SNu8AwW6F6EREzFb4ZwgMjPOqM/kGXbPeCw1dbHEL6v04Cc7EHbSnm4j FmRv0twvAmsOa1/eiZAjfTz0yEUZ8E+QUZ4J+tZu1IBVcgczSK2R8CKVXcSglmnr4loN 1iPEG+a1up2Ic/6fJQvq9rwsBUCv15l4d2S6e4mBB2ySxwJmsk1igF9EI8c6/cBonID+ 4R/g== X-Gm-Message-State: APjAAAWzjnGDIK195V8FZqIpLEvOQtRPg6gNoqp0gQgCd/2eN3AfEWrH mQit3su4R7ate7SC7zAKlSFkKp+KZdQM7Gjmh3UXU7MO+v4= X-Google-Smtp-Source: APXvYqwuclrK1fkaukMtCNbAMFSr/G7FxVxxz0UR9BdP1CLA11rlssqSon+b77OS4BzAm6mtal+M+4nz+DdbUVEan18= X-Received: by 2002:a2e:b003:: with SMTP id y3mr27556604ljk.72.1563532486446; Fri, 19 Jul 2019 03:34:46 -0700 (PDT) MIME-Version: 1.0 References: <19069.1563488801@sss.pgh.pa.us> In-Reply-To: <19069.1563488801@sss.pgh.pa.us> From: =?UTF-8?B?THVrw6HFoSBTb2JvdGth?= Date: Fri, 19 Jul 2019 12:34:19 +0200 Message-ID: Subject: Re: Using COPY command in pqlib To: Tom Lane Cc: pgsql-interfaces@postgresql.org Content-Type: multipart/alternative; boundary="000000000000731032058e064652" List-Id: List-Help: List-Subscribe: List-Post: List-Owner: List-Archive: Precedence: bulk --000000000000731032058e064652 Content-Type: text/plain; charset="UTF-8" Content-Transfer-Encoding: quoted-printable Hi Tom, I see we are not using copy in correct way. Many thanks for your time. Lukas p=C3=A1 19. 7. 2019 v 0:26 odes=C3=ADlatel Tom Lane nap= sal: > =3D?UTF-8?B?THVrw6HFoSBTb2JvdGth?=3D writes: > > I would like to ask you on correct way how to use pqlib for copying dat= a. > > We tried to do it according documentation but some problems occurred. > > > We have a multi-threaded application, all threads hold own non-blocking > > connection into the remote database. Each thread is collecting data and > > when a buffer is filled they copy data to remote DB as quick as possibl= e. > > Copying can run several times per minute. The postgresql related part o= f > > thread main loop is briefly shown in attached file main.c. > > > Most of the time copying works well but big delay sometimes occurred. I > > captured pcap (see https://ibb.co/2MhmSTZ) and the delay is between > getting > > PGRES_COPY_IN from PQresultStatus function and pushing data. But I am > sure > > that commands PQputCopyData and PQputCopyEnd are called immediately aft= er > > client gets PQexec. > > > What am I missing? Is there some other command which we should use? > > Well, you didn't show us any of the relevant parts of your code. > There is extra stuff you need to deal with if you're running the > connection in nonblock mode. > > --- what are you doing when PQputCopyData returns zero? > > The documentation says you should wait for write-ready and try again. > (You could just try again immediately, I suppose, but that would make it > a busy-wait loop which doesn't seem like a great idea.) > > --- what are you doing after PQputCopyEnd? > > The documentation says > > The result is 1 if the termination message was sent; or in nonblockin= g > mode, this may only indicate that the termination message was > successfully queued. (In nonblocking mode, to be certain that the dat= a > has been sent, you should next wait for write-ready and call PQflush, > repeating until it returns zero.) Zero indicates that the function > could not queue the termination message because of full buffers; this > will only happen in nonblocking mode. (In this case, wait for > write-ready and try the PQputCopyEnd call again.) If a hard error > occurs, -1 is returned; you can use PQerrorMessage to retrieve > details. > > regards, tom lane > --000000000000731032058e064652 Content-Type: text/html; charset="UTF-8" Content-Transfer-Encoding: quoted-printable
Hi Tom,

I see we are not using copy in correct way.=

Many thanks for your time.
Lukas

p=C3=A1 19. 7. 2019 v=C2=A00= :26 odes=C3=ADlatel Tom Lane <tgl@s= ss.pgh.pa.us> napsal:
=3D?UTF-8?B?THVrw6HFoSBTb2JvdGth?=3D <sobotka.luk@gmail.com> writes:=
> I would like to ask you on correct way how to use pqlib for copying da= ta.
> We tried to do it according documentation but some problems occurred.<= br>
> We have a multi-threaded application, all threads hold own non-blockin= g
> connection into the remote database. Each thread is collecting data an= d
> when a buffer is filled they copy data to remote DB as quick as possib= le.
> Copying can run several times per minute. The postgresql related part = of
> thread main loop is briefly shown in attached file main.c.

> Most of the time copying works well but big delay sometimes occurred. = I
> captured pcap (see https://ibb.co/2MhmSTZ) and the delay is between g= etting
> PGRES_COPY_IN from PQresultStatus function and pushing data. But I am = sure
> that commands PQputCopyData and PQputCopyEnd are called immediately af= ter
> client gets PQexec.

> What am I missing? Is there some other command which we should use?
Well, you didn't show us any of the relevant parts of your code.
There is extra stuff you need to deal with if you're running the
connection in nonblock mode.

--- what are you doing when PQputCopyData returns zero?

The documentation says you should wait for write-ready and try again.
(You could just try again immediately, I suppose, but that would make it a busy-wait loop which doesn't seem like a great idea.)

--- what are you doing after PQputCopyEnd?

The documentation says

=C2=A0 =C2=A0 The result is 1 if the termination message was sent; or in no= nblocking
=C2=A0 =C2=A0 mode, this may only indicate that the termination message was=
=C2=A0 =C2=A0 successfully queued. (In nonblocking mode, to be certain that= the data
=C2=A0 =C2=A0 has been sent, you should next wait for write-ready and call = PQflush,
=C2=A0 =C2=A0 repeating until it returns zero.) Zero indicates that the fun= ction
=C2=A0 =C2=A0 could not queue the termination message because of full buffe= rs; this
=C2=A0 =C2=A0 will only happen in nonblocking mode. (In this case, wait for=
=C2=A0 =C2=A0 write-ready and try the PQputCopyEnd call again.) If a hard e= rror
=C2=A0 =C2=A0 occurs, -1 is returned; you can use PQerrorMessage to retriev= e
=C2=A0 =C2=A0 details.

=C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2= =A0 =C2=A0 regards, tom lane
--000000000000731032058e064652--