diff options
Diffstat (limited to 'src/bin/psql/common.c')
-rw-r--r-- | src/bin/psql/common.c | 57 |
1 files changed, 50 insertions, 7 deletions
diff --git a/src/bin/psql/common.c b/src/bin/psql/common.c index 62c2928e6bb..26bf613c1d6 100644 --- a/src/bin/psql/common.c +++ b/src/bin/psql/common.c @@ -1092,20 +1092,49 @@ ProcessResult(PGresult **results) * connection out of its COPY state, then call PQresultStatus() * once and report any error. * - * If pset.copyStream is set, use that as data source/sink, - * otherwise use queryFout or cur_cmd_source as appropriate. + * For COPY OUT, direct the output to pset.copyStream if it's set, + * otherwise to pset.gfname if it's set, otherwise to queryFout. + * For COPY IN, use pset.copyStream as data source if it's set, + * otherwise cur_cmd_source. */ - FILE *copystream = pset.copyStream; + FILE *copystream; PGresult *copy_result; SetCancelConn(); if (result_status == PGRES_COPY_OUT) { - if (!copystream) + bool need_close = false; + bool is_pipe = false; + + if (pset.copyStream) + { + /* invoked by \copy */ + copystream = pset.copyStream; + } + else if (pset.gfname) + { + /* invoked by \g */ + if (openQueryOutputFile(pset.gfname, + ©stream, &is_pipe)) + { + need_close = true; + if (is_pipe) + disable_sigpipe_trap(); + } + else + copystream = NULL; /* discard COPY data entirely */ + } + else + { + /* fall back to the generic query output stream */ copystream = pset.queryFout; + } + success = handleCopyOut(pset.db, copystream, - ©_result) && success; + ©_result) + && success + && (copystream != NULL); /* * Suppress status printing if the report would go to the same @@ -1117,11 +1146,25 @@ ProcessResult(PGresult **results) PQclear(copy_result); copy_result = NULL; } + + if (need_close) + { + /* close \g argument file/pipe */ + if (is_pipe) + { + pclose(copystream); + restore_sigpipe_trap(); + } + else + { + fclose(copystream); + } + } } else { - if (!copystream) - copystream = pset.cur_cmd_source; + /* COPY IN */ + copystream = pset.copyStream ? pset.copyStream : pset.cur_cmd_source; success = handleCopyIn(pset.db, copystream, PQbinaryTuples(*results), |