Commit b4771d7c authored by Tom Lane's avatar Tom Lane

Don't treat complete_from_const as equivalent to complete_from_list.

Commit 4f3b38fe supposed that complete_from_const() is equivalent to
the one-element-list case of complete_from_list(), but that's not
really true at all.  complete_from_const() supposes that the completion
is certain enough to justify wiping out whatever the user typed, while
complete_from_list() will only provide completions that match the
word-so-far.

In practice, given the lame parsing technology used by tab-complete.c,
it's fairly hard to believe that we're *ever* certain enough about
a completion to justify auto-correcting user input that doesn't match.

Hence, remove the inappropriate unification of the two cases.
As things now stand, complete_from_const() is used only for the
situation where we have no matches and we need to keep readline
from applying its default complete-with-file-names behavior.

This (mis?) behavior actually exists much further back, but
I'm hesitant to change it in released branches.  It's not too
late for v12, though, especially seeing that the aforesaid
commit is new in v12.

Per gripe from Ken Tanzer.

Discussion: https://postgr.es/m/CAD3a31XpXzrZA9TT3BqLSHghdTK+=cXjNCE+oL2Zn4+oWoc=qA@mail.gmail.com
parent 0ec3e13c
...@@ -205,19 +205,22 @@ do { \ ...@@ -205,19 +205,22 @@ do { \
matches = completion_matches(text, complete_from_versioned_schema_query); \ matches = completion_matches(text, complete_from_versioned_schema_query); \
} while (0) } while (0)
#define COMPLETE_WITH_LIST_INT(cs, list) \ /*
* Caution: COMPLETE_WITH_CONST is not for general-purpose use; you probably
* want COMPLETE_WITH() with one element, instead.
*/
#define COMPLETE_WITH_CONST(cs, con) \
do { \ do { \
completion_case_sensitive = (cs); \ completion_case_sensitive = (cs); \
if (!(list)[1]) \ completion_charp = (con); \
{ \
completion_charp = (list)[0]; \
matches = completion_matches(text, complete_from_const); \ matches = completion_matches(text, complete_from_const); \
} \ } while (0)
else \
{ \ #define COMPLETE_WITH_LIST_INT(cs, list) \
do { \
completion_case_sensitive = (cs); \
completion_charpp = (list); \ completion_charpp = (list); \
matches = completion_matches(text, complete_from_list); \ matches = completion_matches(text, complete_from_list); \
} \
} while (0) } while (0)
#define COMPLETE_WITH_LIST(list) COMPLETE_WITH_LIST_INT(false, list) #define COMPLETE_WITH_LIST(list) COMPLETE_WITH_LIST_INT(false, list)
...@@ -3758,7 +3761,7 @@ psql_completion(const char *text, int start, int end) ...@@ -3758,7 +3761,7 @@ psql_completion(const char *text, int start, int end)
*/ */
if (matches == NULL) if (matches == NULL)
{ {
COMPLETE_WITH(""); COMPLETE_WITH_CONST(true, "");
#ifdef HAVE_RL_COMPLETION_APPEND_CHARACTER #ifdef HAVE_RL_COMPLETION_APPEND_CHARACTER
rl_completion_append_character = '\0'; rl_completion_append_character = '\0';
#endif #endif
...@@ -4188,10 +4191,21 @@ complete_from_list(const char *text, int state) ...@@ -4188,10 +4191,21 @@ complete_from_list(const char *text, int state)
/* /*
* This function returns one fixed string the first time even if it doesn't * This function returns one fixed string the first time even if it doesn't
* match what's there, and nothing the second time. This should be used if * match what's there, and nothing the second time. The string
* there is only one possibility that can appear at a certain spot, so * to be used must be in completion_charp.
* misspellings will be overwritten. The string to be passed must be in *
* completion_charp. * If the given string is "", this has the effect of preventing readline
* from doing any completion. (Without this, readline tries to do filename
* completion which is seldom the right thing.)
*
* If the given string is not empty, readline will replace whatever the
* user typed with that string. This behavior might be useful if it's
* completely certain that we know what must appear at a certain spot,
* so that it's okay to overwrite misspellings. In practice, given the
* relatively lame parsing technology used in this file, the level of
* certainty is seldom that high, so that you probably don't want to
* use this. Use complete_from_list with a one-element list instead;
* that won't try to auto-correct "misspellings".
*/ */
static char * static char *
complete_from_const(const char *text, int state) complete_from_const(const char *text, int state)
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment