psql output change in 9.4

Started by Peter Eisentrautover 11 years ago9 messages
#1Peter Eisentraut
peter_e@gmx.net

This is 9.3:

peter=# \a
Output format is unaligned.
peter=# \a
Output format is aligned.
peter=# \x
Expanded display is on.
peter=# \x
Expanded display is off.

This is new in 9.4:

peter=# \a
Output format (format) is unaligned.
peter=# \a
Output format (format) is aligned.
peter=# \x
Expanded display (expanded) is on.
peter=# \x
Expanded display (expanded) is off.

What is the point of that change?

I suppose it is so that you can use \pset without arguments to show all
settings:

peter=# \pset
Border style (border) is 1.
Target width (columns) unset.
Expanded display (expanded) is off.
...

But those are unrelated features, and the changed output doesn't make
any sense in the contexts I show above.

I think this should be reverted, and the \pset output should be
implemented separately.

--
Sent via pgsql-hackers mailing list (pgsql-hackers@postgresql.org)
To make changes to your subscription:
http://www.postgresql.org/mailpref/pgsql-hackers

#2Robert Haas
robertmhaas@gmail.com
In reply to: Peter Eisentraut (#1)
Re: psql output change in 9.4

On Fri, Aug 8, 2014 at 9:34 PM, Peter Eisentraut <peter_e@gmx.net> wrote:

This is 9.3:

peter=# \a
Output format is unaligned.
peter=# \a
Output format is aligned.
peter=# \x
Expanded display is on.
peter=# \x
Expanded display is off.

This is new in 9.4:

peter=# \a
Output format (format) is unaligned.
peter=# \a
Output format (format) is aligned.
peter=# \x
Expanded display (expanded) is on.
peter=# \x
Expanded display (expanded) is off.

What is the point of that change?

I suppose it is so that you can use \pset without arguments to show all
settings:

peter=# \pset
Border style (border) is 1.
Target width (columns) unset.
Expanded display (expanded) is off.
...

But those are unrelated features, and the changed output doesn't make
any sense in the contexts I show above.

I think this should be reverted, and the \pset output should be
implemented separately.

Yes, the \pset patch (commit c64e68fd9f1132fec563fb5de53dc3bcccb5fc3b)
caused this behavior change. I can't remember whether I noticed it
at the time and thought it was a reasonable change, or whether I
didn't notice it when committing.

Either way, clarifying the name of the parameter which is being
displayed does not seem like particularly bad idea to me even in the
contexts you mention. I've certainly run commands like \a and \t and
then said to myself, "crap, which pset parameter does this correspond
to?". And there was no easy way to figure it out.

I think the output could justly be criticized for making it
insufficiently clear that the parenthesized text is, in fact, the name
of the pset parameter. We could write something like:

Border style (parameter "border") is 1.

But I don't know whether that would be considered an improvement or
just extra verbosity.

--
Robert Haas
EnterpriseDB: http://www.enterprisedb.com
The Enterprise PostgreSQL Company

--
Sent via pgsql-hackers mailing list (pgsql-hackers@postgresql.org)
To make changes to your subscription:
http://www.postgresql.org/mailpref/pgsql-hackers

#3Tom Lane
tgl@sss.pgh.pa.us
In reply to: Robert Haas (#2)
Re: psql output change in 9.4

Robert Haas <robertmhaas@gmail.com> writes:

On Fri, Aug 8, 2014 at 9:34 PM, Peter Eisentraut <peter_e@gmx.net> wrote:

What is the point of that change?

I think the output could justly be criticized for making it
insufficiently clear that the parenthesized text is, in fact, the name
of the pset parameter.

Quite; that wasn't apparent to me either.

We could write something like:
Border style (parameter "border") is 1.

How about

Border style (\pset border) is 1.

regards, tom lane

--
Sent via pgsql-hackers mailing list (pgsql-hackers@postgresql.org)
To make changes to your subscription:
http://www.postgresql.org/mailpref/pgsql-hackers

#4Pavel Stehule
pavel.stehule@gmail.com
In reply to: Tom Lane (#3)
Re: psql output change in 9.4

2014-08-11 19:52 GMT+02:00 Tom Lane <tgl@sss.pgh.pa.us>:

Robert Haas <robertmhaas@gmail.com> writes:

On Fri, Aug 8, 2014 at 9:34 PM, Peter Eisentraut <peter_e@gmx.net>

wrote:

What is the point of that change?

I think the output could justly be criticized for making it
insufficiently clear that the parenthesized text is, in fact, the name
of the pset parameter.

Quite; that wasn't apparent to me either.

We could write something like:
Border style (parameter "border") is 1.

How about

Border style (\pset border) is 1.

+1

Pavel

Show quoted text

regards, tom lane

--
Sent via pgsql-hackers mailing list (pgsql-hackers@postgresql.org)
To make changes to your subscription:
http://www.postgresql.org/mailpref/pgsql-hackers

#5Robert Haas
robertmhaas@gmail.com
In reply to: Tom Lane (#3)
Re: psql output change in 9.4

On Mon, Aug 11, 2014 at 1:52 PM, Tom Lane <tgl@sss.pgh.pa.us> wrote:

Robert Haas <robertmhaas@gmail.com> writes:

On Fri, Aug 8, 2014 at 9:34 PM, Peter Eisentraut <peter_e@gmx.net> wrote:

What is the point of that change?

I think the output could justly be criticized for making it
insufficiently clear that the parenthesized text is, in fact, the name
of the pset parameter.

Quite; that wasn't apparent to me either.

We could write something like:
Border style (parameter "border") is 1.

How about

Border style (\pset border) is 1.

That would look just fine as a response to \a or \x, but I'm not sure
it would look as good as a response to \pset, which prints out that
line for every parameter ("why does every line say \pset when the
command I just typed is \pset?"). However, I can certainly live with
it if others prefer that to what I suggested.

--
Robert Haas
EnterpriseDB: http://www.enterprisedb.com
The Enterprise PostgreSQL Company

--
Sent via pgsql-hackers mailing list (pgsql-hackers@postgresql.org)
To make changes to your subscription:
http://www.postgresql.org/mailpref/pgsql-hackers

#6Bruce Momjian
bruce@momjian.us
In reply to: Robert Haas (#5)
1 attachment(s)
Re: psql output change in 9.4

On Mon, Aug 11, 2014 at 02:28:45PM -0400, Robert Haas wrote:

On Mon, Aug 11, 2014 at 1:52 PM, Tom Lane <tgl@sss.pgh.pa.us> wrote:

Robert Haas <robertmhaas@gmail.com> writes:

On Fri, Aug 8, 2014 at 9:34 PM, Peter Eisentraut <peter_e@gmx.net> wrote:

What is the point of that change?

I think the output could justly be criticized for making it
insufficiently clear that the parenthesized text is, in fact, the name
of the pset parameter.

Quite; that wasn't apparent to me either.

We could write something like:
Border style (parameter "border") is 1.

How about

Border style (\pset border) is 1.

That would look just fine as a response to \a or \x, but I'm not sure
it would look as good as a response to \pset, which prints out that
line for every parameter ("why does every line say \pset when the
command I just typed is \pset?"). However, I can certainly live with
it if others prefer that to what I suggested.

I went with quoting the pset variable:

test=> \a
Output format ("format") is aligned.
test=> \x
Expanded display ("expanded") is on.

Patch attached. I think this would be for 9.5 only, at this point.

--
Bruce Momjian <bruce@momjian.us> http://momjian.us
EnterpriseDB http://enterprisedb.com

+ Everyone has their own god. +

Attachments:

psql.difftext/x-diff; charset=us-asciiDownload
diff --git a/src/bin/psql/command.c b/src/bin/psql/command.c
index 2227db4..76c3645 100644
--- a/src/bin/psql/command.c
+++ b/src/bin/psql/command.c
@@ -2538,9 +2538,9 @@ printPsetInfo(const char *param, struct printQueryOpt *popt)
 	if (strcmp(param, "border") == 0)
 	{
 		if (!popt->topt.border)
-			printf(_("Border style (%s) unset.\n"), param);
+			printf(_("Border style (\"%s\") unset.\n"), param);
 		else
-			printf(_("Border style (%s) is %d.\n"), param,
+			printf(_("Border style (\"%s\") is %d.\n"), param,
 				   popt->topt.border);
 	}
 
@@ -2548,9 +2548,9 @@ printPsetInfo(const char *param, struct printQueryOpt *popt)
 	else if (strcmp(param, "columns") == 0)
 	{
 		if (!popt->topt.columns)
-			printf(_("Target width (%s) unset.\n"), param);
+			printf(_("Target width (\"%s\") unset.\n"), param);
 		else
-			printf(_("Target width (%s) is %d.\n"), param,
+			printf(_("Target width (\"%s\") is %d.\n"), param,
 				   popt->topt.columns);
 	}
 
@@ -2558,58 +2558,58 @@ printPsetInfo(const char *param, struct printQueryOpt *popt)
 	else if (strcmp(param, "x") == 0 || strcmp(param, "expanded") == 0 || strcmp(param, "vertical") == 0)
 	{
 		if (popt->topt.expanded == 1)
-			printf(_("Expanded display (%s) is on.\n"), param);
+			printf(_("Expanded display (\"%s\") is on.\n"), param);
 		else if (popt->topt.expanded == 2)
-			printf(_("Expanded display (%s) is used automatically.\n"), param);
+			printf(_("Expanded display (\"%s\") is used automatically.\n"), param);
 		else
-			printf(_("Expanded display (%s) is off.\n"), param);
+			printf(_("Expanded display (\"%s\") is off.\n"), param);
 	}
 
 	/* show field separator for unaligned text */
 	else if (strcmp(param, "fieldsep") == 0)
 	{
 		if (popt->topt.fieldSep.separator_zero)
-			printf(_("Field separator (%s) is zero byte.\n"), param);
+			printf(_("Field separator (\"%s\") is zero byte.\n"), param);
 		else
-			printf(_("Field separator (%s) is \"%s\".\n"), param,
+			printf(_("Field separator (\"%s\") is \"%s\".\n"), param,
 				   popt->topt.fieldSep.separator);
 	}
 
 	else if (strcmp(param, "fieldsep_zero") == 0)
 	{
-		printf(_("Field separator (%s) is zero byte.\n"), param);
+		printf(_("Field separator (\"%s\") is zero byte.\n"), param);
 	}
 
 	/* show disable "(x rows)" footer */
 	else if (strcmp(param, "footer") == 0)
 	{
 		if (popt->topt.default_footer)
-			printf(_("Default footer (%s) is on.\n"), param);
+			printf(_("Default footer (\"%s\") is on.\n"), param);
 		else
-			printf(_("Default footer (%s) is off.\n"), param);
+			printf(_("Default footer (\"%s\") is off.\n"), param);
 	}
 
 	/* show format */
 	else if (strcmp(param, "format") == 0)
 	{
 		if (!popt->topt.format)
-			printf(_("Output format (%s) is aligned.\n"), param);
+			printf(_("Output format (\"%s\") is aligned.\n"), param);
 		else
-			printf(_("Output format (%s) is %s.\n"), param,
+			printf(_("Output format (\"%s\") is %s.\n"), param,
 				   _align2string(popt->topt.format));
 	}
 
 	/* show table line style */
 	else if (strcmp(param, "linestyle") == 0)
 	{
-		printf(_("Line style (%s) is %s.\n"), param,
+		printf(_("Line style (\"%s\") is %s.\n"), param,
 			   get_line_style(&popt->topt)->name);
 	}
 
 	/* show null display */
 	else if (strcmp(param, "null") == 0)
 	{
-		printf(_("Null display (%s) is \"%s\".\n"), param,
+		printf(_("Null display (\"%s\") is \"%s\".\n"), param,
 			   popt->nullPrint ? popt->nullPrint : "");
 	}
 
@@ -2617,65 +2617,65 @@ printPsetInfo(const char *param, struct printQueryOpt *popt)
 	else if (strcmp(param, "numericlocale") == 0)
 	{
 		if (popt->topt.numericLocale)
-			printf(_("Locale-adjusted numeric output (%s) is on.\n"), param);
+			printf(_("Locale-adjusted numeric output (\"%s\") is on.\n"), param);
 		else
-			printf(_("Locale-adjusted numeric output (%s) is off.\n"), param);
+			printf(_("Locale-adjusted numeric output (\"%s\") is off.\n"), param);
 	}
 
 	/* show toggle use of pager */
 	else if (strcmp(param, "pager") == 0)
 	{
 		if (popt->topt.pager == 1)
-			printf(_("Pager (%s) is used for long output.\n"), param);
+			printf(_("Pager (\"%s\") is used for long output.\n"), param);
 		else if (popt->topt.pager == 2)
-			printf(_("Pager (%s) is always used.\n"), param);
+			printf(_("Pager (\"%s\") is always used.\n"), param);
 		else
-			printf(_("Pager usage (%s) is off.\n"), param);
+			printf(_("Pager usage (\"%s\") is off.\n"), param);
 	}
 
 	/* show record separator for unaligned text */
 	else if (strcmp(param, "recordsep") == 0)
 	{
 		if (popt->topt.recordSep.separator_zero)
-			printf(_("Record separator (%s) is zero byte.\n"), param);
+			printf(_("Record separator (\"%s\") is zero byte.\n"), param);
 		else if (strcmp(popt->topt.recordSep.separator, "\n") == 0)
-			printf(_("Record separator (%s) is <newline>.\n"), param);
+			printf(_("Record separator (\"%s\") is <newline>.\n"), param);
 		else
-			printf(_("Record separator (%s) is \"%s\".\n"), param,
+			printf(_("Record separator (\"%s\") is \"%s\".\n"), param,
 				   popt->topt.recordSep.separator);
 	}
 
 	else if (strcmp(param, "recordsep_zero") == 0)
 	{
-		printf(_("Record separator (%s) is zero byte.\n"), param);
+		printf(_("Record separator (\"%s\") is zero byte.\n"), param);
 	}
 
 	/* show HTML table tag options */
 	else if (strcmp(param, "T") == 0 || strcmp(param, "tableattr") == 0)
 	{
 		if (popt->topt.tableAttr)
-			printf(_("Table attributes (%s) are \"%s\".\n"), param,
+			printf(_("Table attributes (\"%s\") are \"%s\".\n"), param,
 				   popt->topt.tableAttr);
 		else
-			printf(_("Table attributes (%s) unset.\n"), param);
+			printf(_("Table attributes (\"%s\") unset.\n"), param);
 	}
 
 	/* show title override */
 	else if (strcmp(param, "title") == 0)
 	{
 		if (popt->title)
-			printf(_("Title (%s) is \"%s\".\n"), param, popt->title);
+			printf(_("Title (\"%s\") is \"%s\".\n"), param, popt->title);
 		else
-			printf(_("Title (%s) unset.\n"), param);
+			printf(_("Title (\"%s\") unset.\n"), param);
 	}
 
 	/* show toggle between full and tuples-only format */
 	else if (strcmp(param, "t") == 0 || strcmp(param, "tuples_only") == 0)
 	{
 		if (popt->topt.tuples_only)
-			printf(_("Tuples only (%s) is on.\n"), param);
+			printf(_("Tuples only (\"%s\") is on.\n"), param);
 		else
-			printf(_("Tuples only (%s) is off.\n"), param);
+			printf(_("Tuples only (\"%s\") is off.\n"), param);
 	}
 
 	/* unicode style formatting */
#7Peter Eisentraut
peter_e@gmx.net
In reply to: Bruce Momjian (#6)
1 attachment(s)
Re: psql output change in 9.4

On 10/11/14 8:25 PM, Bruce Momjian wrote:

On Mon, Aug 11, 2014 at 02:28:45PM -0400, Robert Haas wrote:

On Mon, Aug 11, 2014 at 1:52 PM, Tom Lane <tgl@sss.pgh.pa.us> wrote:

Robert Haas <robertmhaas@gmail.com> writes:

On Fri, Aug 8, 2014 at 9:34 PM, Peter Eisentraut <peter_e@gmx.net> wrote:

What is the point of that change?

I think the output could justly be criticized for making it
insufficiently clear that the parenthesized text is, in fact, the name
of the pset parameter.

Quite; that wasn't apparent to me either.

We could write something like:
Border style (parameter "border") is 1.

How about

Border style (\pset border) is 1.

That would look just fine as a response to \a or \x, but I'm not sure
it would look as good as a response to \pset, which prints out that
line for every parameter ("why does every line say \pset when the
command I just typed is \pset?"). However, I can certainly live with
it if others prefer that to what I suggested.

I went with quoting the pset variable:

test=> \a
Output format ("format") is aligned.
test=> \x
Expanded display ("expanded") is on.

Patch attached. I think this would be for 9.5 only, at this point.

Funny, I was *just* working on that, too. I propose a patch that
reverts the output to how it was in 9.3 (without anything in
parentheses), and implements the output of \pset without any arguments
separately, thus:

# \a
Output format is unaligned.

# \pset
border 2
columns 0
expanded auto
fieldsep '|'
fieldsep_zero off
footer on
format unaligned
linestyle unicode
null ''
numericlocale off
pager 1
recordsep '\n'
recordsep_zero off
tableattr
title
tuples_only off

(This is also symmetric with what \set outputs.)

On closer examination, the change in 9.4, besides having the aesthetic
issues discussed earlier, also created some outright incorrect output by
mixing together fieldsep/fieldsep_zero and recordsep/recordsep_zero.
These issues become much clearer if you separate the case of "this is
what you just set" from "these are all the current settings".

Attachments:

pset.patchtext/x-patch; name=pset.patchDownload
commit 42b78a38970808611133031c9e6b30466fdd84b4
Author: Peter Eisentraut <peter_e@gmx.net>
Date:   Sun Oct 12 00:08:52 2014 -0400

    Fix \pset without arguments

diff --git a/src/bin/psql/command.c b/src/bin/psql/command.c
index 0d9b677..d8c477a 100644
--- a/src/bin/psql/command.c
+++ b/src/bin/psql/command.c
@@ -69,6 +69,7 @@ static void minimal_error_message(PGresult *res);
 
 static void printSSLInfo(void);
 static bool printPsetInfo(const char *param, struct printQueryOpt *popt);
+static char *pset_value_string(const char *param, struct printQueryOpt *popt);
 
 #ifdef WIN32
 static void checkWin32Codepage(void);
@@ -1050,15 +1051,19 @@ exec_command(const char *cmd,
 
 			int			i;
 			static const char *const my_list[] = {
-				"border", "columns", "expanded", "fieldsep",
+				"border", "columns", "expanded", "fieldsep", "fieldsep_zero",
 				"footer", "format", "linestyle", "null",
-				"numericlocale", "pager", "recordsep",
+				"numericlocale", "pager", "recordsep", "recordsep_zero",
 				"tableattr", "title", "tuples_only",
 				NULL
 			};
 
 			for (i = 0; my_list[i] != NULL; i++)
-				printPsetInfo(my_list[i], &pset.popt);
+			{
+				char   *val = pset_value_string(my_list[i], &pset.popt);
+				printf("%-14s %s\n", my_list[i], val);
+				free(val);
+			}
 
 			success = true;
 		}
@@ -2199,10 +2204,6 @@ process_file(char *filename, bool single_txn, bool use_relative_path)
 
 
 
-/*
- * do_pset
- *
- */
 static const char *
 _align2string(enum printFormat in)
 {
@@ -2237,6 +2238,10 @@ _align2string(enum printFormat in)
 }
 
 
+/*
+ * do_pset
+ *
+ */
 bool
 do_pset(const char *param, const char *value, printQueryOpt *popt, bool quiet)
 {
@@ -2447,80 +2452,69 @@ printPsetInfo(const char *param, struct printQueryOpt *popt)
 
 	/* show border style/width */
 	if (strcmp(param, "border") == 0)
-	{
-		if (!popt->topt.border)
-			printf(_("Border style (%s) unset.\n"), param);
-		else
-			printf(_("Border style (%s) is %d.\n"), param,
-				   popt->topt.border);
-	}
+		printf(_("Border style is %d.\n"), popt->topt.border);
 
 	/* show the target width for the wrapped format */
 	else if (strcmp(param, "columns") == 0)
 	{
 		if (!popt->topt.columns)
-			printf(_("Target width (%s) unset.\n"), param);
+			printf(_("Target width is unset.\n"));
 		else
-			printf(_("Target width (%s) is %d.\n"), param,
-				   popt->topt.columns);
+			printf(_("Target width is %d.\n"), popt->topt.columns);
 	}
 
 	/* show expanded/vertical mode */
 	else if (strcmp(param, "x") == 0 || strcmp(param, "expanded") == 0 || strcmp(param, "vertical") == 0)
 	{
 		if (popt->topt.expanded == 1)
-			printf(_("Expanded display (%s) is on.\n"), param);
+			printf(_("Expanded display is on.\n"));
 		else if (popt->topt.expanded == 2)
-			printf(_("Expanded display (%s) is used automatically.\n"), param);
+			printf(_("Expanded display is used automatically.\n"));
 		else
-			printf(_("Expanded display (%s) is off.\n"), param);
+			printf(_("Expanded display is off.\n"));
 	}
 
 	/* show field separator for unaligned text */
 	else if (strcmp(param, "fieldsep") == 0)
 	{
 		if (popt->topt.fieldSep.separator_zero)
-			printf(_("Field separator (%s) is zero byte.\n"), param);
+			printf(_("Field separator is zero byte.\n"));
 		else
-			printf(_("Field separator (%s) is \"%s\".\n"), param,
+			printf(_("Field separator is \"%s\".\n"),
 				   popt->topt.fieldSep.separator);
 	}
 
 	else if (strcmp(param, "fieldsep_zero") == 0)
 	{
-		printf(_("Field separator (%s) is zero byte.\n"), param);
+		printf(_("Field separator is zero byte.\n"));
 	}
 
 	/* show disable "(x rows)" footer */
 	else if (strcmp(param, "footer") == 0)
 	{
 		if (popt->topt.default_footer)
-			printf(_("Default footer (%s) is on.\n"), param);
+			printf(_("Default footer is on.\n"));
 		else
-			printf(_("Default footer (%s) is off.\n"), param);
+			printf(_("Default footer is off.\n"));
 	}
 
 	/* show format */
 	else if (strcmp(param, "format") == 0)
 	{
-		if (!popt->topt.format)
-			printf(_("Output format (%s) is aligned.\n"), param);
-		else
-			printf(_("Output format (%s) is %s.\n"), param,
-				   _align2string(popt->topt.format));
+		printf(_("Output format is %s.\n"), _align2string(popt->topt.format));
 	}
 
 	/* show table line style */
 	else if (strcmp(param, "linestyle") == 0)
 	{
-		printf(_("Line style (%s) is %s.\n"), param,
+		printf(_("Line style is %s.\n"),
 			   get_line_style(&popt->topt)->name);
 	}
 
 	/* show null display */
 	else if (strcmp(param, "null") == 0)
 	{
-		printf(_("Null display (%s) is \"%s\".\n"), param,
+		printf(_("Null display is \"%s\".\n"),
 			   popt->nullPrint ? popt->nullPrint : "");
 	}
 
@@ -2528,65 +2522,65 @@ printPsetInfo(const char *param, struct printQueryOpt *popt)
 	else if (strcmp(param, "numericlocale") == 0)
 	{
 		if (popt->topt.numericLocale)
-			printf(_("Locale-adjusted numeric output (%s) is on.\n"), param);
+			printf(_("Locale-adjusted numeric output is on.\n"));
 		else
-			printf(_("Locale-adjusted numeric output (%s) is off.\n"), param);
+			printf(_("Locale-adjusted numeric output is off.\n"));
 	}
 
 	/* show toggle use of pager */
 	else if (strcmp(param, "pager") == 0)
 	{
 		if (popt->topt.pager == 1)
-			printf(_("Pager (%s) is used for long output.\n"), param);
+			printf(_("Pager is used for long output.\n"));
 		else if (popt->topt.pager == 2)
-			printf(_("Pager (%s) is always used.\n"), param);
+			printf(_("Pager is always used.\n"));
 		else
-			printf(_("Pager usage (%s) is off.\n"), param);
+			printf(_("Pager usage is off.\n"));
 	}
 
 	/* show record separator for unaligned text */
 	else if (strcmp(param, "recordsep") == 0)
 	{
 		if (popt->topt.recordSep.separator_zero)
-			printf(_("Record separator (%s) is zero byte.\n"), param);
+			printf(_("Record separator is zero byte.\n"));
 		else if (strcmp(popt->topt.recordSep.separator, "\n") == 0)
-			printf(_("Record separator (%s) is <newline>.\n"), param);
+			printf(_("Record separator is <newline>.\n"));
 		else
-			printf(_("Record separator (%s) is \"%s\".\n"), param,
+			printf(_("Record separator is \"%s\".\n"),
 				   popt->topt.recordSep.separator);
 	}
 
 	else if (strcmp(param, "recordsep_zero") == 0)
 	{
-		printf(_("Record separator (%s) is zero byte.\n"), param);
+		printf(_("Record separator is zero byte.\n"));
 	}
 
 	/* show HTML table tag options */
 	else if (strcmp(param, "T") == 0 || strcmp(param, "tableattr") == 0)
 	{
 		if (popt->topt.tableAttr)
-			printf(_("Table attributes (%s) are \"%s\".\n"), param,
+			printf(_("Table attributes are \"%s\".\n"),
 				   popt->topt.tableAttr);
 		else
-			printf(_("Table attributes (%s) unset.\n"), param);
+			printf(_("Table attributes unset.\n"));
 	}
 
 	/* show title override */
 	else if (strcmp(param, "title") == 0)
 	{
 		if (popt->title)
-			printf(_("Title (%s) is \"%s\".\n"), param, popt->title);
+			printf(_("Title is \"%s\".\n"), popt->title);
 		else
-			printf(_("Title (%s) unset.\n"), param);
+			printf(_("Title is unset.\n"));
 	}
 
 	/* show toggle between full and tuples-only format */
 	else if (strcmp(param, "t") == 0 || strcmp(param, "tuples_only") == 0)
 	{
 		if (popt->topt.tuples_only)
-			printf(_("Tuples only (%s) is on.\n"), param);
+			printf(_("Tuples only is on.\n"));
 		else
-			printf(_("Tuples only (%s) is off.\n"), param);
+			printf(_("Tuples only is off.\n"));
 	}
 
 	else
@@ -2599,6 +2593,101 @@ printPsetInfo(const char *param, struct printQueryOpt *popt)
 }
 
 
+static const char *
+pset_bool_string(bool val)
+{
+	return val ? "on" : "off";
+}
+
+
+static char *
+pset_quoted_string(const char *str)
+{
+	char	   *ret = pg_malloc(strlen(str) * 2 + 2);
+	char	   *r = ret;
+
+	*r++ = '\'';
+
+	for (; *str; str++)
+	{
+		if (*str == '\n')
+		{
+			*r++ = '\\';
+			*r++ = 'n';
+		}
+		else if (*str == '\'')
+		{
+			*r++ = '\\';
+			*r++ = '\'';
+		}
+		else
+			*r++ = *str;
+	}
+
+	*r++ = '\'';
+	*r = '\0';
+
+	return ret;
+}
+
+
+/*
+ * Return a malloc'ed string for the \pset value.
+ *
+ * Note that for some string parameters, print.c distinguishes between unset
+ * and empty string, but for others it doesn't.  This function should produce
+ * output that produces the correct setting when fed back into \pset.
+ */
+static char *
+pset_value_string(const char *param, struct printQueryOpt *popt)
+{
+	Assert(param != NULL);
+
+	if (strcmp(param, "border") == 0)
+		return psprintf("%d", popt->topt.border);
+	else if (strcmp(param, "columns") == 0)
+		return psprintf("%d", popt->topt.columns);
+	else if (strcmp(param, "expanded") == 0)
+		return pstrdup(popt->topt.expanded == 2
+					   ? "auto"
+					   : pset_bool_string(popt->topt.expanded));
+	else if (strcmp(param, "fieldsep") == 0)
+		return pset_quoted_string(popt->topt.fieldSep.separator
+								  ? popt->topt.fieldSep.separator
+								  : "");
+	else if (strcmp(param, "fieldsep_zero") == 0)
+		return pstrdup(pset_bool_string(popt->topt.fieldSep.separator_zero));
+	else if (strcmp(param, "footer") == 0)
+		return pstrdup(pset_bool_string(popt->topt.default_footer));
+	else if (strcmp(param, "format") == 0)
+		return psprintf("%s", _align2string(popt->topt.format));
+	else if (strcmp(param, "linestyle") == 0)
+		return psprintf("%s", get_line_style(&popt->topt)->name);
+	else if (strcmp(param, "null") == 0)
+		return pset_quoted_string(popt->nullPrint
+								  ? popt->nullPrint
+								  : "");
+	else if (strcmp(param, "numericlocale") == 0)
+		return pstrdup(pset_bool_string(popt->topt.numericLocale));
+	else if (strcmp(param, "pager") == 0)
+		return psprintf("%d", popt->topt.pager);
+	else if (strcmp(param, "recordsep") == 0)
+		return pset_quoted_string(popt->topt.recordSep.separator
+								  ? popt->topt.recordSep.separator
+								  : "");
+	else if (strcmp(param, "recordsep_zero") == 0)
+		return pstrdup(pset_bool_string(popt->topt.recordSep.separator_zero));
+	else if (strcmp(param, "tableattr") == 0)
+		return popt->topt.tableAttr ? pset_quoted_string(popt->topt.tableAttr) : pstrdup("");
+	else if (strcmp(param, "title") == 0)
+		return popt->title ? pset_quoted_string(popt->title) : pstrdup("");
+	else if (strcmp(param, "tuples_only") == 0)
+		return pstrdup(pset_bool_string(popt->topt.tuples_only));
+	else
+		return pstrdup("ERROR");
+}
+
+
 
 #ifndef WIN32
 #define DEFAULT_SHELL "/bin/sh"
#8Bruce Momjian
bruce@momjian.us
In reply to: Peter Eisentraut (#7)
Re: psql output change in 9.4

On Sun, Oct 12, 2014 at 12:17:31AM -0400, Peter Eisentraut wrote:

I went with quoting the pset variable:

test=> \a
Output format ("format") is aligned.
test=> \x
Expanded display ("expanded") is on.

Patch attached. I think this would be for 9.5 only, at this point.

Funny, I was *just* working on that, too. I propose a patch that
reverts the output to how it was in 9.3 (without anything in
parentheses), and implements the output of \pset without any arguments
separately, thus:

# \a
Output format is unaligned.

Agreed.

--
Bruce Momjian <bruce@momjian.us> http://momjian.us
EnterpriseDB http://enterprisedb.com

+ Everyone has their own god. +

--
Sent via pgsql-hackers mailing list (pgsql-hackers@postgresql.org)
To make changes to your subscription:
http://www.postgresql.org/mailpref/pgsql-hackers

#9Tom Lane
tgl@sss.pgh.pa.us
In reply to: Bruce Momjian (#8)
Re: psql output change in 9.4

Bruce Momjian <bruce@momjian.us> writes:

On Sun, Oct 12, 2014 at 12:17:31AM -0400, Peter Eisentraut wrote:

Patch attached. I think this would be for 9.5 only, at this point.

Funny, I was *just* working on that, too. I propose a patch that
reverts the output to how it was in 9.3 (without anything in
parentheses), and implements the output of \pset without any arguments
separately, thus:

Agreed.

Works for me, too. If we are reverting to 9.3's output in the base case,
I think this *does* need to get back-patched into 9.4.

regards, tom lane

--
Sent via pgsql-hackers mailing list (pgsql-hackers@postgresql.org)
To make changes to your subscription:
http://www.postgresql.org/mailpref/pgsql-hackers