]> granicus.if.org Git - postgresql/commitdiff
Add -L option to psql to log sessions.
authorBruce Momjian <bruce@momjian.us>
Tue, 14 Jun 2005 02:57:45 +0000 (02:57 +0000)
committerBruce Momjian <bruce@momjian.us>
Tue, 14 Jun 2005 02:57:45 +0000 (02:57 +0000)
Lorne Sunley

doc/src/sgml/ref/psql-ref.sgml
src/bin/psql/common.c
src/bin/psql/describe.c
src/bin/psql/help.c
src/bin/psql/large_obj.c
src/bin/psql/print.c
src/bin/psql/print.h
src/bin/psql/settings.h
src/bin/psql/startup.c
src/bin/scripts/createlang.c
src/bin/scripts/droplang.c

index 81fb06e14869acaa713610a78686c4135de58e52..4162e51b50218d04b5c65015466337c30b9d3dfa 100644 (file)
@@ -1,5 +1,5 @@
 <!--
-$PostgreSQL: pgsql/doc/src/sgml/ref/psql-ref.sgml,v 1.144 2005/06/13 06:36:22 neilc Exp $
+$PostgreSQL: pgsql/doc/src/sgml/ref/psql-ref.sgml,v 1.145 2005/06/14 02:57:38 momjian Exp $
 PostgreSQL documentation
 -->
 
@@ -222,6 +222,17 @@ PostgreSQL documentation
       </listitem>
     </varlistentry>
 
+    <varlistentry>
+      <term><option>-L <replaceable class="parameter">filename</replaceable></></term>
+      <term><option>--log <replaceable class="parameter">filename</replaceable></></term>
+      <listitem>
+      <para>
+      Log all query output into file <replaceable
+      class="parameter">filename</replaceable> in addition to the regular output source.
+      </para>
+      </listitem>
+    </varlistentry>
+
     <varlistentry>
       <term><option>-o <replaceable class="parameter">filename</replaceable></></term>
       <term><option>--output <replaceable class="parameter">filename</replaceable></></term>
index b1cec7449963056b8a7cffb0a641287cfe4ef48a..df17d0404bc9e4bd5045b3e8f280e6bbfc57bbb7 100644 (file)
@@ -3,7 +3,7 @@
  *
  * Copyright (c) 2000-2005, PostgreSQL Global Development Group
  *
- * $PostgreSQL: pgsql/src/bin/psql/common.c,v 1.101 2005/06/13 06:36:22 neilc Exp $
+ * $PostgreSQL: pgsql/src/bin/psql/common.c,v 1.102 2005/06/14 02:57:41 momjian Exp $
  */
 #include "postgres_fe.h"
 #include "common.h"
@@ -723,6 +723,13 @@ PSQLexec(const char *query, bool start_xact)
                           "%s\n"
                           "**************************\n\n", query);
                fflush(stdout);
+               if (pset.logfile)
+               {
+                       fprintf(pset.logfile, "********* QUERY **********\n"
+                          "%s\n"
+                          "**************************\n\n", query);
+                       fflush(pset.logfile);
+               }
 
                if (echo_hidden == 1)   /* noexec? */
                        return NULL;
@@ -803,7 +810,7 @@ PrintQueryTuples(const PGresult *results)
                        return false;
                }
 
-               printQuery(results, &my_popt, pset.queryFout);
+               printQuery(results, &my_popt, pset.queryFout, pset.logfile);
 
                /* close file/pipe, restore old setting */
                setQFout(NULL);
@@ -815,7 +822,7 @@ PrintQueryTuples(const PGresult *results)
                pset.gfname = NULL;
        }
        else
-               printQuery(results, &my_popt, pset.queryFout);
+               printQuery(results, &my_popt, pset.queryFout, pset.logfile);
 
        return true;
 }
@@ -905,6 +912,8 @@ PrintQueryResults(PGresult *results)
                                        else
                                                fprintf(pset.queryFout, "%s\n", PQcmdStatus(results));
                                }
+                               if (pset.logfile)
+                                       fprintf(pset.logfile, "%s\n", PQcmdStatus(results));
                                SetVariable(pset.vars, "LASTOID", buf);
                                break;
                        }
@@ -976,6 +985,14 @@ SendQuery(const char *query)
                fflush(stdout);
        }
 
+       if (pset.logfile)
+       {
+               fprintf(pset.logfile, "********* QUERY **********\n"
+                  "%s\n"
+                  "**************************\n\n", query);
+               fflush(pset.logfile);
+       }
+
        SetCancelConn();
 
        transaction_status = PQtransactionStatus(pset.db);
index 45178c0eebbdaadf01dc5f6378c22b270590169e..17549b2b5f8a0a50e203e194e887cb61ebbebdcc 100644 (file)
@@ -3,7 +3,7 @@
  *
  * Copyright (c) 2000-2005, PostgreSQL Global Development Group
  *
- * $PostgreSQL: pgsql/src/bin/psql/describe.c,v 1.115 2005/04/06 05:23:32 neilc Exp $
+ * $PostgreSQL: pgsql/src/bin/psql/describe.c,v 1.116 2005/06/14 02:57:41 momjian Exp $
  */
 #include "postgres_fe.h"
 #include "describe.h"
@@ -94,7 +94,7 @@ describeAggregates(const char *pattern, bool verbose)
        myopt.nullPrint = NULL;
        myopt.title = _("List of aggregate functions");
 
-       printQuery(res, &myopt, pset.queryFout);
+       printQuery(res, &myopt, pset.queryFout, pset.logfile);
 
        PQclear(res);
        return true;
@@ -147,7 +147,7 @@ describeTablespaces(const char *pattern, bool verbose)
        myopt.nullPrint = NULL;
        myopt.title = _("List of tablespaces");
 
-       printQuery(res, &myopt, pset.queryFout);
+       printQuery(res, &myopt, pset.queryFout, pset.logfile);
 
        PQclear(res);
        return true;
@@ -219,7 +219,7 @@ describeFunctions(const char *pattern, bool verbose)
        myopt.nullPrint = NULL;
        myopt.title = _("List of functions");
 
-       printQuery(res, &myopt, pset.queryFout);
+       printQuery(res, &myopt, pset.queryFout, pset.logfile);
 
        PQclear(res);
        return true;
@@ -287,7 +287,7 @@ describeTypes(const char *pattern, bool verbose)
        myopt.nullPrint = NULL;
        myopt.title = _("List of data types");
 
-       printQuery(res, &myopt, pset.queryFout);
+       printQuery(res, &myopt, pset.queryFout, pset.logfile);
 
        PQclear(res);
        return true;
@@ -334,7 +334,7 @@ describeOperators(const char *pattern)
        myopt.nullPrint = NULL;
        myopt.title = _("List of operators");
 
-       printQuery(res, &myopt, pset.queryFout);
+       printQuery(res, &myopt, pset.queryFout, pset.logfile);
 
        PQclear(res);
        return true;
@@ -379,7 +379,7 @@ listAllDbs(bool verbose)
        myopt.nullPrint = NULL;
        myopt.title = _("List of databases");
 
-       printQuery(res, &myopt, pset.queryFout);
+       printQuery(res, &myopt, pset.queryFout, pset.logfile);
 
        PQclear(res);
        return true;
@@ -436,7 +436,7 @@ permissionsList(const char *pattern)
        printfPQExpBuffer(&buf, _("Access privileges for database \"%s\""), PQdb(pset.db));
        myopt.title = buf.data;
 
-       printQuery(res, &myopt, pset.queryFout);
+       printQuery(res, &myopt, pset.queryFout, pset.logfile);
 
        termPQExpBuffer(&buf);
        PQclear(res);
@@ -592,7 +592,7 @@ objectDescription(const char *pattern)
        myopt.nullPrint = NULL;
        myopt.title = _("Object descriptions");
 
-       printQuery(res, &myopt, pset.queryFout);
+       printQuery(res, &myopt, pset.queryFout, pset.logfile);
 
        PQclear(res);
        return true;
@@ -1279,7 +1279,7 @@ describeOneTableDetails(const char *schemaname,
 
        printTable(title.data, headers,
                           (const char **) cells, (const char **) footers,
-                          "llll", &myopt, pset.queryFout);
+                          "llll", &myopt, pset.queryFout, pset.logfile);
 
        retval = true;
 
@@ -1391,7 +1391,7 @@ describeUsers(const char *pattern)
        myopt.nullPrint = NULL;
        myopt.title = _("List of users");
 
-       printQuery(res, &myopt, pset.queryFout);
+       printQuery(res, &myopt, pset.queryFout, pset.logfile);
 
        PQclear(res);
        return true;
@@ -1431,7 +1431,7 @@ describeGroups(const char *pattern)
        myopt.nullPrint = NULL;
        myopt.title = _("List of groups");
 
-       printQuery(res, &myopt, pset.queryFout);
+       printQuery(res, &myopt, pset.queryFout, pset.logfile);
 
        PQclear(res);
        return true;
@@ -1549,7 +1549,7 @@ listTables(const char *tabtypes, const char *pattern, bool verbose)
                myopt.nullPrint = NULL;
                myopt.title = _("List of relations");
 
-               printQuery(res, &myopt, pset.queryFout);
+               printQuery(res, &myopt, pset.queryFout, pset.logfile);
        }
 
        PQclear(res);
@@ -1605,7 +1605,7 @@ listDomains(const char *pattern)
        myopt.nullPrint = NULL;
        myopt.title = _("List of domains");
 
-       printQuery(res, &myopt, pset.queryFout);
+       printQuery(res, &myopt, pset.queryFout, pset.logfile);
 
        PQclear(res);
        return true;
@@ -1656,7 +1656,7 @@ listConversions(const char *pattern)
        myopt.nullPrint = NULL;
        myopt.title = _("List of conversions");
 
-       printQuery(res, &myopt, pset.queryFout);
+       printQuery(res, &myopt, pset.queryFout, pset.logfile);
 
        PQclear(res);
        return true;
@@ -1706,7 +1706,7 @@ listCasts(const char *pattern)
        myopt.nullPrint = NULL;
        myopt.title = _("List of casts");
 
-       printQuery(res, &myopt, pset.queryFout);
+       printQuery(res, &myopt, pset.queryFout, pset.logfile);
 
        PQclear(res);
        return true;
@@ -1756,7 +1756,7 @@ listSchemas(const char *pattern, bool verbose)
        myopt.nullPrint = NULL;
        myopt.title = _("List of schemas");
 
-       printQuery(res, &myopt, pset.queryFout);
+       printQuery(res, &myopt, pset.queryFout, pset.logfile);
 
        PQclear(res);
        return true;
index 8b3dbcf602e090fe543991d1576762591bf3fbbf..9c1e6d3a57459f8c9652befb70c42fbfcc54562e 100644 (file)
@@ -3,7 +3,7 @@
  *
  * Copyright (c) 2000-2005, PostgreSQL Global Development Group
  *
- * $PostgreSQL: pgsql/src/bin/psql/help.c,v 1.101 2005/02/22 04:40:55 momjian Exp $
+ * $PostgreSQL: pgsql/src/bin/psql/help.c,v 1.102 2005/06/14 02:57:41 momjian Exp $
  */
 #include "postgres_fe.h"
 #include "common.h"
@@ -60,7 +60,7 @@ usage(void)
        user = getenv("PGUSER");
        if (!user)
        {
-#ifndef WIN32
+#if !defined(WIN32) && !defined(__OS2__)
                pw = getpwuid(geteuid());
                if (pw)
                        user = pw->pw_name;
@@ -107,6 +107,7 @@ usage(void)
        puts(_("  -n              disable enhanced command line editing (readline)"));
        puts(_("  -s              single-step mode (confirm each query)"));
        puts(_("  -S              single-line mode (end of line terminates SQL command)"));
+       puts(_("  -L FILENAME     send session log to file"));
 
        puts(_("\nOutput format options:"));
        puts(_("  -A              unaligned table output mode (-P format=unaligned)"));
index 624ccd0be6d41849c70ed044bec8746f7caa675d..6606e99849522f5b0c53ad533d581093f8979f20 100644 (file)
@@ -3,7 +3,7 @@
  *
  * Copyright (c) 2000-2005, PostgreSQL Global Development Group
  *
- * $PostgreSQL: pgsql/src/bin/psql/large_obj.c,v 1.36 2005/02/22 04:40:55 momjian Exp $
+ * $PostgreSQL: pgsql/src/bin/psql/large_obj.c,v 1.37 2005/06/14 02:57:41 momjian Exp $
  */
 #include "postgres_fe.h"
 #include "large_obj.h"
@@ -263,7 +263,7 @@ do_lo_list(void)
        myopt.nullPrint = NULL;
        myopt.title = _("Large objects");
 
-       printQuery(res, &myopt, pset.queryFout);
+       printQuery(res, &myopt, pset.queryFout, pset.logfile);
 
        PQclear(res);
        return true;
index ede239e2e92e27c555355caae8721be31bf1e155..d1ef95f50a635d4c1a3f523bd1e0ad7e089fd4df 100644 (file)
@@ -3,7 +3,7 @@
  *
  * Copyright (c) 2000-2005, PostgreSQL Global Development Group
  *
- * $PostgreSQL: pgsql/src/bin/psql/print.c,v 1.58 2005/06/13 06:36:22 neilc Exp $
+ * $PostgreSQL: pgsql/src/bin/psql/print.c,v 1.59 2005/06/14 02:57:41 momjian Exp $
  */
 #include "postgres_fe.h"
 #include "common.h"
@@ -1255,7 +1255,7 @@ printTable(const char *title,
                   const char *const * cells,
                   const char *const * footers,
                   const char *align,
-                  const printTableOpt *opt, FILE *fout)
+                  const printTableOpt *opt, FILE *fout, FILE *flog)
 {
        const char *default_footer[] = {NULL};
        unsigned short int border = opt->border;
@@ -1312,6 +1312,9 @@ printTable(const char *title,
 
        /* print the stuff */
 
+       if (flog)
+               print_aligned_text(title, headers, cells, footers, align, opt->tuples_only, border, opt->encoding, flog);
+
        switch (opt->format)
        {
                case PRINT_UNALIGNED:
@@ -1380,7 +1383,7 @@ printTable(const char *title,
 
 
 void
-printQuery(const PGresult *result, const printQueryOpt *opt, FILE *fout)
+printQuery(const PGresult *result, const printQueryOpt *opt, FILE *fout, FILE *flog)
 {
        int                     nfields;
        int                     ncells;
@@ -1476,7 +1479,7 @@ printQuery(const PGresult *result, const printQueryOpt *opt, FILE *fout)
        /* call table printer */
        printTable(opt->title, headers, cells,
                           (const char *const *) footers,
-                          align, &opt->topt, fout);
+                          align, &opt->topt, fout, flog);
 
        free(headers);
        free(cells);
index f28b7f9d2408243cc2685f1bbb986628f0c15e0b..7dcc2657f1d21f46cff30bcfbef60e4b8f9b1a39 100644 (file)
@@ -3,7 +3,7 @@
  *
  * Copyright (c) 2000-2005, PostgreSQL Global Development Group
  *
- * $PostgreSQL: pgsql/src/bin/psql/print.h,v 1.24 2005/06/13 06:36:22 neilc Exp $
+ * $PostgreSQL: pgsql/src/bin/psql/print.h,v 1.25 2005/06/14 02:57:41 momjian Exp $
  */
 #ifndef PRINT_H
 #define PRINT_H
@@ -62,7 +62,7 @@ typedef struct _printTableOpt
 void printTable(const char *title, const char *const * headers,
                   const char *const * cells, const char *const * footers,
                   const char *align,
-                  const printTableOpt *opt, FILE *fout);
+                  const printTableOpt *opt, FILE *fout, FILE *flog);
 
 
 
@@ -82,7 +82,8 @@ typedef struct _printQueryOpt
  *
  * It calls the printTable above with all the things set straight.
  */
-void           printQuery(const PGresult *result, const printQueryOpt *opt, FILE *fout);
+void           printQuery(const PGresult *result, const printQueryOpt *opt,
+                                          FILE *fout, FILE *flog);
 
 #ifndef __CYGWIN__
 #define DEFAULT_PAGER "more"
index 5090efd7b69973cb120a4a56afce34bef82d6607..f4e78f407e136cf9ae9824b6f852b844b1dfcbd1 100644 (file)
@@ -3,7 +3,7 @@
  *
  * Copyright (c) 2000-2005, PostgreSQL Global Development Group
  *
- * $PostgreSQL: pgsql/src/bin/psql/settings.h,v 1.24 2005/06/09 23:28:10 momjian Exp $
+ * $PostgreSQL: pgsql/src/bin/psql/settings.h,v 1.25 2005/06/14 02:57:41 momjian Exp $
  */
 #ifndef SETTINGS_H
 #define SETTINGS_H
@@ -56,6 +56,7 @@ typedef struct _psqlSettings
        bool            timing;                 /* enable timing of all queries */
 
        PGVerbosity verbosity;          /* current error verbosity level */
+       FILE            *logfile;       /* session log file handle */
 } PsqlSettings;
 
 extern PsqlSettings pset;
index 9e27b8c002bf62fe79ff02d07365f4bc9babcc55..ff8a5c2431b1b300f79b9e22f2448436ad246150 100644 (file)
@@ -3,7 +3,7 @@
  *
  * Copyright (c) 2000-2005, PostgreSQL Global Development Group
  *
- * $PostgreSQL: pgsql/src/bin/psql/startup.c,v 1.116 2005/06/13 06:36:22 neilc Exp $
+ * $PostgreSQL: pgsql/src/bin/psql/startup.c,v 1.117 2005/06/14 02:57:41 momjian Exp $
  */
 #include "postgres_fe.h"
 
@@ -71,6 +71,7 @@ struct adhoc_opts
        char       *host;
        char       *port;
        char       *username;
+       char       *logfilename;
        enum _actions action;
        char       *action_string;
        bool            no_readline;
@@ -109,8 +110,6 @@ main(int argc, char *argv[])
 
        set_pglocale_pgservice(argv[0], "psql");
 
-       pset.progname = get_progname(argv[0]);
-
        if (argc > 1)
        {
                if (strcmp(argv[1], "--help") == 0 || strcmp(argv[1], "-?") == 0)
@@ -125,6 +124,8 @@ main(int argc, char *argv[])
                }
        }
 
+       pset.progname = get_progname(argv[0]);
+
 #ifdef WIN32
        setvbuf(stderr, NULL, _IONBF, 0);
        setup_win32_locks();
@@ -234,6 +235,13 @@ main(int argc, char *argv[])
                exit(success ? EXIT_SUCCESS : EXIT_FAILURE);
        }
 
+       if (options.logfilename)
+       {
+               pset.logfile = fopen(options.logfilename, "a");
+               if (!pset.logfile)
+                       fprintf(stderr, gettext("logfile open failed for %s\n\n"), options.logfilename);
+       }
+
        /*
         * Now find something to do
         */
@@ -316,6 +324,8 @@ main(int argc, char *argv[])
        }
 
        /* clean up */
+       if (pset.logfile)
+               fclose(pset.logfile);
        PQfinish(pset.db);
        setQFout(NULL);
 
@@ -344,6 +354,7 @@ parse_psql_options(int argc, char *argv[], struct adhoc_opts * options)
                {"host", required_argument, NULL, 'h'},
                {"html", no_argument, NULL, 'H'},
                {"list", no_argument, NULL, 'l'},
+               {"log", required_argument, NULL, 'L'},
                {"no-readline", no_argument, NULL, 'n'},
                {"output", required_argument, NULL, 'o'},
                {"port", required_argument, NULL, 'p'},
@@ -373,7 +384,7 @@ parse_psql_options(int argc, char *argv[], struct adhoc_opts * options)
 
        memset(options, 0, sizeof *options);
 
-       while ((c = getopt_long(argc, argv, "aAc:d:eEf:F:h:Hlno:p:P:qR:sStT:uU:v:VWxX?",
+       while ((c = getopt_long(argc, argv, "aAc:d:eEf:F:h:HlL:no:p:P:qR:sStT:uU:v:VWxX?",
                                                        long_options, &optindex)) != -1)
        {
                switch (c)
@@ -419,6 +430,9 @@ parse_psql_options(int argc, char *argv[], struct adhoc_opts * options)
                        case 'l':
                                options->action = ACT_LIST_DB;
                                break;
+                       case 'L':
+                               options->logfilename = optarg;
+                               break;
                        case 'n':
                                options->no_readline = true;
                                break;
index b5ab23818f5fc35f6275b1bddd8377b7c825f6bb..e8015089c9a3461908eaf931c684891ecfc00e62 100644 (file)
@@ -5,7 +5,7 @@
  * Portions Copyright (c) 1996-2005, PostgreSQL Global Development Group
  * Portions Copyright (c) 1994, Regents of the University of California
  *
- * $PostgreSQL: pgsql/src/bin/scripts/createlang.c,v 1.15 2004/12/31 22:03:17 pgsql Exp $
+ * $PostgreSQL: pgsql/src/bin/scripts/createlang.c,v 1.16 2005/06/14 02:57:45 momjian Exp $
  *
  *-------------------------------------------------------------------------
  */
@@ -148,7 +148,7 @@ main(int argc, char *argv[])
                popt.topt.border = 1;
                popt.topt.encoding = PQclientEncoding(conn);
                popt.title = _("Procedural Languages");
-               printQuery(result, &popt, stdout);
+               printQuery(result, &popt, stdout, NULL);
 
                PQfinish(conn);
                exit(0);
index cbd7dc91991c65520575b059dd6139f7e6e72c2d..5be336dd6d704a216e0cc3349442a69b1717f72c 100644 (file)
@@ -5,7 +5,7 @@
  * Portions Copyright (c) 1996-2005, PostgreSQL Global Development Group
  * Portions Copyright (c) 1994, Regents of the University of California
  *
- * $PostgreSQL: pgsql/src/bin/scripts/droplang.c,v 1.14 2004/12/31 22:03:17 pgsql Exp $
+ * $PostgreSQL: pgsql/src/bin/scripts/droplang.c,v 1.15 2005/06/14 02:57:45 momjian Exp $
  *
  *-------------------------------------------------------------------------
  */
@@ -145,7 +145,7 @@ main(int argc, char *argv[])
                popt.topt.border = 1;
                popt.topt.encoding = PQclientEncoding(conn);
                popt.title = _("Procedural Languages");
-               printQuery(result, &popt, stdout);
+               printQuery(result, &popt, stdout, NULL);
 
                PQfinish(conn);
                exit(0);