Skip to content

Commit 8463110

Browse files
committed
Address more review comments on commit 2d819a0.
Based on comments from Peter Eisentraut. * Document CREATE DATABASE ... BUILTIN_LOCALE. * Determine required encoding based on locale name for CREATE COLLATION. Use -1 for "C" (requires catversion bump). * initdb output fixups. * Make ctype_is_c a constant true for now. * Fixups to ICU 010_create_database.pl test. Discussion: https://postgr.es/m/4135cf11-206d-40ed-96c0-9363c1232379@eisentraut.org
1 parent 66ab937 commit 8463110

File tree

8 files changed

+58
-14
lines changed

8 files changed

+58
-14
lines changed

doc/src/sgml/ref/create_database.sgml

Lines changed: 18 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -29,6 +29,7 @@ CREATE DATABASE <replaceable class="parameter">name</replaceable>
2929
[ LOCALE [=] <replaceable class="parameter">locale</replaceable> ]
3030
[ LC_COLLATE [=] <replaceable class="parameter">lc_collate</replaceable> ]
3131
[ LC_CTYPE [=] <replaceable class="parameter">lc_ctype</replaceable> ]
32+
[ BUILTIN_LOCALE [=] <replaceable class="parameter">builtin_locale</replaceable> ]
3233
[ ICU_LOCALE [=] <replaceable class="parameter">icu_locale</replaceable> ]
3334
[ ICU_RULES [=] <replaceable class="parameter">icu_rules</replaceable> ]
3435
[ LOCALE_PROVIDER [=] <replaceable class="parameter">locale_provider</replaceable> ]
@@ -216,6 +217,23 @@ CREATE DATABASE <replaceable class="parameter">name</replaceable>
216217
</listitem>
217218
</varlistentry>
218219

220+
<varlistentry id="create-database-builtin-locale">
221+
<term><replaceable class="parameter">builtin_locale</replaceable></term>
222+
<listitem>
223+
<para>
224+
Specifies the builtin provider locale for the database default
225+
collation order and character classification, overriding the setting
226+
<xref linkend="create-database-locale"/>. The <link
227+
linkend="create-database-locale-provider">locale provider</link> must
228+
be <literal>builtin</literal>. The default is the setting of <xref
229+
linkend="create-database-locale"/> if specified; otherwise the same
230+
setting as the template database. Currently, the only available
231+
locale for the <literal>builtin</literal> provider is
232+
<literal>C</literal>.
233+
</para>
234+
</listitem>
235+
</varlistentry>
236+
219237
<varlistentry id="create-database-icu-locale">
220238
<term><replaceable class="parameter">icu_locale</replaceable></term>
221239
<listitem>

src/backend/commands/collationcmds.c

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -318,7 +318,7 @@ DefineCollation(ParseState *pstate, List *names, List *parameters, bool if_not_e
318318

319319
if (collprovider == COLLPROVIDER_BUILTIN)
320320
{
321-
collencoding = GetDatabaseEncoding();
321+
collencoding = builtin_locale_encoding(colllocale);
322322
}
323323
else if (collprovider == COLLPROVIDER_ICU)
324324
{

src/backend/utils/adt/pg_locale.c

Lines changed: 21 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -1270,14 +1270,8 @@ lookup_collation_cache(Oid collation, bool set_flags)
12701270

12711271
if (collform->collprovider == COLLPROVIDER_BUILTIN)
12721272
{
1273-
Datum datum;
1274-
const char *colllocale;
1275-
1276-
datum = SysCacheGetAttrNotNull(COLLOID, tp, Anum_pg_collation_colllocale);
1277-
colllocale = TextDatumGetCString(datum);
1278-
12791273
cache_entry->collate_is_c = true;
1280-
cache_entry->ctype_is_c = (strcmp(colllocale, "C") == 0);
1274+
cache_entry->ctype_is_c = true;
12811275
}
12821276
else if (collform->collprovider == COLLPROVIDER_LIBC)
12831277
{
@@ -2501,6 +2495,26 @@ pg_strnxfrm_prefix(char *dest, size_t destsize, const char *src,
25012495
return result;
25022496
}
25032497

2498+
/*
2499+
* Return required encoding ID for the given locale, or -1 if any encoding is
2500+
* valid for the locale.
2501+
*
2502+
* The only supported locale for the builtin provider is "C", and it's
2503+
* available for any encoding.
2504+
*/
2505+
int
2506+
builtin_locale_encoding(const char *locale)
2507+
{
2508+
if (strcmp(locale, "C") == 0)
2509+
return -1;
2510+
else
2511+
ereport(ERROR,
2512+
(errcode(ERRCODE_WRONG_OBJECT_TYPE),
2513+
errmsg("invalid locale name \"%s\" for builtin provider",
2514+
locale)));
2515+
}
2516+
2517+
25042518
/*
25052519
* Validate the locale and encoding combination, and return the canonical form
25062520
* of the locale name.

src/bin/initdb/initdb.c

Lines changed: 4 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -2455,7 +2455,8 @@ usage(const char *progname)
24552455
" set default locale in the respective category for\n"
24562456
" new databases (default taken from environment)\n"));
24572457
printf(_(" --no-locale equivalent to --locale=C\n"));
2458-
printf(_(" --builtin-locale=LOCALE set builtin locale name for new databases\n"));
2458+
printf(_(" --builtin-locale=LOCALE\n"
2459+
" set builtin locale name for new databases\n"));
24592460
printf(_(" --locale-provider={builtin|libc|icu}\n"
24602461
" set default locale provider for new databases\n"));
24612462
printf(_(" --pwfile=FILE read password for the new superuser from file\n"));
@@ -2618,9 +2619,9 @@ setup_locale_encoding(void)
26182619
else
26192620
{
26202621
printf(_("The database cluster will be initialized with this locale configuration:\n"));
2621-
printf(_(" default collation provider: %s\n"), collprovider_name(locale_provider));
2622+
printf(_(" locale provider: %s\n"), collprovider_name(locale_provider));
26222623
if (locale_provider != COLLPROVIDER_LIBC)
2623-
printf(_(" default collation locale: %s\n"), datlocale);
2624+
printf(_(" default collation: %s\n"), datlocale);
26242625
printf(_(" LC_COLLATE: %s\n"
26252626
" LC_CTYPE: %s\n"
26262627
" LC_MESSAGES: %s\n"

src/bin/initdb/t/001_initdb.pl

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -138,7 +138,7 @@
138138
'--lc-monetary=C', '--lc-time=C',
139139
"$tempdir/data4"
140140
],
141-
qr/^\s+default collation locale:\s+und\n/ms,
141+
qr/^\s+default collation:\s+und\n/ms,
142142
'options --locale-provider=icu --locale=und --lc-*=C');
143143

144144
command_fails_like(

src/include/catalog/catversion.h

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -57,6 +57,6 @@
5757
*/
5858

5959
/* yyyymmddN */
60-
#define CATALOG_VERSION_NO 202403172
60+
#define CATALOG_VERSION_NO 202403181
6161

6262
#endif

src/include/utils/pg_locale.h

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -117,6 +117,7 @@ extern size_t pg_strxfrm_prefix(char *dest, const char *src, size_t destsize,
117117
extern size_t pg_strnxfrm_prefix(char *dest, size_t destsize, const char *src,
118118
size_t srclen, pg_locale_t locale);
119119

120+
extern int builtin_locale_encoding(const char *loc_str);
120121
extern const char *builtin_validate_locale(int encoding, const char *loc_str);
121122
extern void icu_validate_locale(const char *loc_str);
122123
extern char *icu_language_tag(const char *loc_str, int elevel);

src/test/icu/t/010_database.pl

Lines changed: 11 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -62,8 +62,18 @@
6262
0,
6363
"C locale works for ICU");
6464

65+
# Test that LOCALE works for ICU locales if LC_COLLATE and LC_CTYPE
66+
# are specified
67+
is( $node1->psql(
68+
'postgres',
69+
q{CREATE DATABASE dbicu2 LOCALE_PROVIDER icu LOCALE '@colStrength=primary'
70+
LC_COLLATE='C' LC_CTYPE='C' TEMPLATE template0 ENCODING UTF8}
71+
),
72+
0,
73+
"LOCALE works for ICU locales if LC_COLLATE and LC_CTYPE are specified");
74+
6575
my ($ret, $stdout, $stderr) = $node1->psql('postgres',
66-
q{CREATE DATABASE dbicu LOCALE_PROVIDER builtin LOCALE 'C' TEMPLATE dbicu}
76+
q{CREATE DATABASE dbicu3 LOCALE_PROVIDER builtin LOCALE 'C' TEMPLATE dbicu}
6777
);
6878
isnt($ret, 0, "locale provider must match template: exit code not 0");
6979
like(

0 commit comments

Comments
 (0)