Tom Lane wrote:
Another idea is to try the values listed in our encoding_match_list[]
until bind_textdomain_codeset succeeds.  The problem here is that the
GNU documentation is *exceedingly* vague about whether
bind_textdomain_codeset behaves sanely (ie throws a recognizable error)
when given a bad encoding name.  (I guess we could look at the source
code.)

Unfortunately it doesn't give any error. The value passed to it is just
stored, and isn't used until gettext(). Quick testing shows that if you
give an invalid encoding name, gettext will simply refrain from
translating anything and revert to English.

We could exploit that to determine if the codeset name we gave
bind_textdomain_codeset was valid: pick a string that is known to be
translated in all translations, like "syntax error", and see if
gettext("syntax error") returns the original string. Something along the
lines of:

const char *teststring = "syntax error";
encoding_match *m = encoding_match_list;
while(m->system_enc_name)
{
  if (m->pg_enc_code != GetDatabaseEncoding())
    continue;
  bind_textdomain_codeset("postgres");
  if (gettext(teststring) != teststring)
    break; /* found! */
}


This feels rather hacky, but if we only do that with the combination of LC_CTYPE=C and LC_MESSAGES=other than C that we have a problem with, I think it would be ok. The current behavior is highly unlikely to give correct results, so I don't think we can do much worse than that.

Another possibility is to just refrain from translating anything if LC_CTYPE=C. If the above loop fails to find anything that works, that's what we should fall back to IMHO.

--
  Heikki Linnakangas
  EnterpriseDB   http://www.enterprisedb.com


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

Reply via email to