ICU-2429 review changes - updated header; changed layout of resource to be flat (one tier); updated test and test data

X-SVN-Rev: 11903
This commit is contained in:
Alan Liu 2003-05-13 00:10:12 +00:00
parent 1714ca9827
commit bdcad9ca57
4 changed files with 96 additions and 55 deletions

View file

@ -13,30 +13,26 @@
#include "cstring.h"
#include "uassert.h"
/* set_num key prefix string. msg_num key is simply a number. */
static const char SET_KEY_PREFIX[] = "%cat%";
/* Separator between set_num and msg_num */
static const char SEPARATOR = '%';
/* length of SET_KEY_PREFIX */
#define SET_KEY_PREFIX_LEN 5
/* Maximum length of a set_num/msg_num key, incl. terminating zero */
#define MAX_KEY_LEN (SET_KEY_PREFIX_LEN+11)
/* Maximum length of a set_num/msg_num key, incl. terminating zero.
* Longest possible key is "2147483647%2147483647" */
#define MAX_KEY_LEN (22)
/**
* Fill in buffer with a set_num/msg_num key string, given the numeric
* value. Numeric value must be >= 0. Buffer must be of length
* MAX_KEY_LEN or more. If isSet is true, then a set_num key is
* created; otherwise a msg_num key is created.
* values. Numeric values must be >= 0. Buffer must be of length
* MAX_KEY_LEN or more.
*/
static char*
_catkey(char* buffer, int32_t num, UBool isSet) {
_catkey(char* buffer, int32_t set_num, int32_t msg_num) {
int32_t i = 0;
U_ASSERT(num>=0);
if (isSet) {
uprv_strcpy(buffer, SET_KEY_PREFIX);
i = SET_KEY_PREFIX_LEN;
}
T_CString_integerToString(buffer + i, num, 10);
U_ASSERT(set_num>=0 && msg_num>=0);
T_CString_integerToString(buffer, set_num, 10);
i = uprv_strlen(buffer);
buffer[i++] = SEPARATOR;
T_CString_integerToString(buffer+i, msg_num, 10);
return buffer;
}
@ -55,7 +51,6 @@ u_catgets(u_nl_catd catd, int32_t set_num, int32_t msg_num,
const UChar* s,
int32_t* len, UErrorCode* ec) {
UResourceBundle* res;
char key[MAX_KEY_LEN];
const UChar* result;
@ -63,18 +58,9 @@ u_catgets(u_nl_catd catd, int32_t set_num, int32_t msg_num,
goto ERROR;
}
res = ures_getByKey((const UResourceBundle*) catd,
_catkey(key, set_num, TRUE),
NULL, ec);
if (U_FAILURE(*ec)) {
goto ERROR;
}
result = ures_getStringByKey(res,
_catkey(key, msg_num, FALSE),
result = ures_getStringByKey((const UResourceBundle*) catd,
_catkey(key, set_num, msg_num),
len, ec);
ures_close(res);
if (U_FAILURE(*ec)) {
goto ERROR;
}

View file

@ -14,6 +14,53 @@
#include "unicode/utypes.h"
#include "unicode/ures.h"
/**
* \file
* \brief C API: Message Catalog Wrappers
*
* This C API provides look-alike functions that deliberately resemble
* the POSIX catopen, catclose, and catgets functions. The underlying
* implementation is in terms of ICU resource bundles, rather than
* POSIX message catalogs.
*
* The ICU resource bundles obey standard ICU inheritance policies.
* To facilitate this, sets and messages are flattened into one tier.
* This is done by creating resource bundle keys of the form
* <set_num>%<msg_num> where set_num is the set number and msg_num is
* the message number, formatted as decimal strings.
*
* Example: Consider a message catalog containing two sets:
*
* Set 1: Message 4 = "Good morning."
* Message 5 = "Good afternoon."
* Message 7 = "Good evening."
* Message 8 = "Good night."
* Set 4: Message 14 = "Please "
* Message 19 = "Thank you."
* Message 20 = "Sincerely,"
*
* The ICU resource bundle source file would, assuming it is named
* "greet.txt", would look like this:
*
* greet
* {
* 1%4 { "Good morning." }
* 1%5 { "Good afternoon." }
* 1%7 { "Good evening." }
* 1%8 { "Good night." }
*
* 4%14 { "Please " }
* 4%19 { "Thank you." }
* 4%20 { "Sincerely," }
* }
*
* The catgets function is commonly used in combination with functions
* like printf and strftime. ICU components like message format can
* be used instead, although they use a different format syntax.
* There is an unsupported ICU package, ustdio, that provides some of
* the POSIX-style formatting API.
*/
U_CDECL_BEGIN
/**
@ -32,9 +79,12 @@ typedef UResourceBundle* u_nl_catd;
* e.g. "/usr/resource/my_app/resources/guimessages" on a Unix system.
* If NULL, ICU default data files will be used.
*
* Unlike POSIX, environment variables are not interpolated within the
* name.
*
* @param locale the locale for which we want to open the resource. If
* NULL, the default locale will be used. If strlen(locale) == 0, the
* root locale will be used.
* NULL, the default ICU locale will be used (see uloc_getDefault). If
* strlen(locale) == 0, the root locale will be used.
*
* @param ec input/output error code. Upon output,
* U_USING_FALLBACK_WARNING indicates that a fallback locale was
@ -91,7 +141,9 @@ u_catclose(u_nl_catd catd);
* @return a pointer to a zero-terminated UChar array which lives in
* an internal buffer area, typically a memory mapped/DLL file. The
* caller must NOT delete this pointer. If the call is unsuccessful
* for any reason, then s is returned.
* for any reason, then s is returned. This includes the situation in
* which ec indicates a failing error code upon entry to this
* function.
*
* @draft ICU 2.6
*/

View file

@ -36,12 +36,17 @@ void TestMessageCatalog(void) {
u_nl_catd catd;
const char* DATA[] = {
/* set_num, msg_num, expected string result, expected error code */
"1", "1", "FAIL", "U_MISSING_RESOURCE_ERROR",
"19006", "4", "Miranda", "U_ZERO_ERROR",
"19006", "24", "Laura", "U_ZERO_ERROR",
"19006", "99", "FAIL", "U_MISSING_RESOURCE_ERROR",
"20014", "5", "Ava", "U_ZERO_ERROR",
"20014", "99", "FAIL", "U_MISSING_RESOURCE_ERROR",
"1", "4", "Good morning.", "U_ZERO_ERROR",
"1", "5", "Good afternoon.", "U_ZERO_ERROR",
"1", "6", "FAIL", "U_MISSING_RESOURCE_ERROR",
"1", "7", "Good evening.", "U_ZERO_ERROR",
"1", "8", "Good night.", "U_ZERO_ERROR",
"1", "9", "FAIL", "U_MISSING_RESOURCE_ERROR",
"3", "1", "FAIL", "U_MISSING_RESOURCE_ERROR",
"4", "14", "Please ", "U_ZERO_ERROR",
"4", "15", "FAIL", "U_MISSING_RESOURCE_ERROR",
"4", "19", "Thank you.", "U_ZERO_ERROR",
"4", "20", "Sincerely,", "U_ZERO_ERROR",
NULL
};
const UChar FAIL[] = {0x46, 0x41, 0x49, 0x4C, 0x00}; /* "FAIL" */
@ -75,23 +80,23 @@ void TestMessageCatalog(void) {
u_austrcpy(str, ustr);
err = u_errorName(ec);
log_verbose("u_catgets(%d, %d) => %s, len=%d, %s\n",
log_verbose("u_catgets(%d, %d) => \"%s\", len=%d, %s\n",
set_num, msg_num, str, len, err);
if (uprv_strcmp(err, DATA[i+3]) != 0) {
log_err("FAIL: u_catgets => %s, exp. %s\n",
err, DATA[i+3]);
}
if (u_strcmp(ustr, exp) != 0) {
log_err("FAIL: u_catgets => %s, exp. %s\n",
log_err("FAIL: u_catgets => \"%s\", exp. \"%s\"\n",
str, DATA[i+2]);
}
if (len != (int32_t) uprv_strlen(DATA[i+2])) {
log_err("FAIL: u_catgets => len=%s, exp. %s\n",
log_err("FAIL: u_catgets => len=%d, exp. %d\n",
len, uprv_strlen(DATA[i+2]));
}
if (uprv_strcmp(err, DATA[i+3]) != 0) {
log_err("FAIL: u_catgets => %s, exp. %s\n",
err, DATA[i+3]);
}
}
u_catclose(catd);

View file

@ -12,16 +12,14 @@
mc
{
"%cat%19006"
{
"4" { "Miranda" }
"24" { "Laura" }
}
1%4 { "Good morning." }
1%5 { "Good afternoon." }
1%7 { "Good evening." }
1%8 { "Good night." }
"%cat%20014"
{
"5" { "Ava" }
}
4%14 { "Please " }
4%19 { "Thank you." }
4%20 { "Sincerely," }
}
//eof