From f4effde18e78d7b3ce21dba73027e9e657ccbe97 Mon Sep 17 00:00:00 2001 From: Deluan Date: Fri, 4 Sep 2026 23:32:29 -0400 Subject: [PATCH] fix(pglite): resend a request the backend produced no output for Three times during a scan on a real library, a new pool connection's first query got no bytes back at all, which the previous commit turned from a hang into an error. A run always emits at least a completion, so no output means the packet was not run; the bridge now hands it over again (twice at most) and logs it. --- db/pglite/pglite.go | 11 +++++++++++ 1 file changed, 11 insertions(+) diff --git a/db/pglite/pglite.go b/db/pglite/pglite.go index 9868dd6c6..81fae3bb6 100644 --- a/db/pglite/pglite.go +++ b/db/pglite/pglite.go @@ -512,6 +512,7 @@ func (pg *PGlite) forwardWire(packet []byte, outFile string) ([][]byte, error) { _, _ = pg.fnUseWire.Call(ctx, api.EncodeI32(1)) } var replies [][]byte + resends := 0 for range maxTicks { producedBefore := pg.collectReply(outFile, &replies) t0 := time.Now() @@ -544,6 +545,16 @@ func (pg *PGlite) forwardWire(packet []byte, outFile string) ([][]byte, error) { } producedAfter := pg.collectReply(outFile, &replies) if !producedBefore && !producedAfter { + // No output at all means the backend did not run the packet (a run always emits at + // least a completion); seen right after handshakes. Hand it over again, twice at most. + if len(packet) > 0 && len(replies) == 0 && resends < 2 { + resends++ + fmt.Fprintf(pg.cfg.Stderr, "# bridge: empty reply to %s; resending (%d)\n", wireTags(packet), resends) + if err := pg.send(packet, strings.TrimSuffix(outFile, ".out")); err != nil { + return nil, err + } + continue + } break } if endsWithReadyForQuery(replies) {