libs/web: prepare template parser, dispatcher and i18n class for upcoming po format...
authorJo-Philipp Wich <jow@openwrt.org>
Sat, 31 Oct 2009 15:42:07 +0000 (15:42 +0000)
committerJo-Philipp Wich <jow@openwrt.org>
Sat, 31 Oct 2009 15:42:07 +0000 (15:42 +0000)
libs/web/luasrc/dispatcher.lua
libs/web/luasrc/i18n.lua
libs/web/src/template_parser.c
libs/web/src/template_parser.h

index ad4f24dc777205ddc15743efa55bd0a100023f24..6445c124ed5ee0fc076bccad528f7577ddcf7290 100644 (file)
@@ -235,6 +235,7 @@ function dispatch(request)
                   include     = function(name) tpl.Template(name):render(getfenv(2)) end;
                   translate   = function(...) return require("luci.i18n").translate(...) end;
                   striptags   = util.striptags;
+                  pcdata      = util.pcdata;
                   media       = media;
                   theme       = fs.basename(media);
                   resource    = luci.config.main.resourcebase
index 9a11a9dc8ff6744bdf89a63cfe81bee026025c77..816d90310af692298b830b6cbbd8be47ebc1eaae 100644 (file)
@@ -93,42 +93,38 @@ function setlanguage(lang)
 end
 
 --- Return the translated value for a specific translation key.
--- @param key  Translation key
--- @param def  Default translation
+-- @param key  Default translation text
 -- @return             Translated string
-function translate(key, def)
+function translate(key)
        return (table[context.lang] and table[context.lang][key])
                or (table[context.parent] and table[context.parent][key])
                or (table[default] and table[default][key])
-               or def
+               or key
 end
 
 --- Return the translated value for a specific translation key and use it as sprintf pattern.
--- @param key          Translation key
--- @param default      Default translation
+-- @param key          Default translation text
 -- @param ...          Format parameters
 -- @return                     Translated and formatted string
-function translatef(key, default, ...)
-       return tostring(translate(key, default)):format(...)
+function translatef(key, ...)
+       return tostring(translate(key)):format(...)
 end
 
 --- Return the translated value for a specific translation key
 -- and ensure that the returned value is a Lua string value.
 -- This is the same as calling <code>tostring(translate(...))</code>
--- @param key          Translation key
--- @param default      Default translation
+-- @param key          Default translation text
 -- @return                     Translated string
-function string(key, default)
-       return tostring(translate(key, default))
+function string(key)
+       return tostring(translate(key))
 end
 
 --- Return the translated value for a specific translation key and use it as sprintf pattern.
 -- Ensure that the returned value is a Lua string value.
 -- This is the same as calling <code>tostring(translatef(...))</code>
--- @param key          Translation key
--- @param default      Default translation
+-- @param key          Default translation text
 -- @param ...          Format parameters
 -- @return                     Translated and formatted string
-function stringf(key, default, ...)
-       return tostring(translate(key, default)):format(...)
+function stringf(key, ...)
+       return tostring(translate(key)):format(...)
 end
index fe324cedc85d4929b817da29b0c413cbaef5d8d5..a0a400bdf72558c8b5bfd06b8ca5426de678b79a 100644 (file)
 
 
 /* leading and trailing code for different types */
-const char * gen_code[6][2] = {
+const char * gen_code[7][2] = {
        { "write(\"",                   "\")"                   },
        { NULL,                                 NULL                    },
        { "write(tostring(",    " or \"\"))"    },
        { "include(\"",                 "\")"                   },
+       { "write(pcdata(translate(\"",  "\")))" },
        { "write(translate(\"", "\"))"                  },
        { NULL,                                 " "                             }
 };
@@ -127,7 +128,7 @@ static const char * generate_expression(struct template_parser *data, size_t *sz
        int i;
        int size = 0;
        int start = 0;
-       int i18n_hasdef = 0;
+       int whitespace = 0;
 
        memset(tmp, 0, T_OUTBUFSZ);
 
@@ -142,31 +143,35 @@ static const char * generate_expression(struct template_parser *data, size_t *sz
        for( i = 0; i < data->outsize; i++ )
        {
                /* Skip leading whitespace for non-raw and non-expr chunks */
-               if( !start && isspace(data->out[i]) && (data->type == T_TYPE_I18N || data->type == T_TYPE_INCLUDE) )
+               if( !start && isspace(data->out[i]) && (data->type == T_TYPE_I18N ||
+           data->type == T_TYPE_I18N_RAW || data->type == T_TYPE_INCLUDE) )
                        continue;
                else if( !start )
                        start = 1;
 
                /* Found whitespace after i18n key */
-               if( (data->type == T_TYPE_I18N) && (i18n_hasdef == 1) )
+               if( data->type == T_TYPE_I18N || data->type == T_TYPE_I18N_RAW )
                {
-                       /* At non-whitespace char, inject seperator token */
-                       if( !isspace(data->out[i]) )
+                       /* Is initial whitespace, insert space */
+                       if( !whitespace && isspace(data->out[i]) )
                        {
-                               memcpy(&tmp[size], T_TOK_I18NSEP, strlen(T_TOK_I18NSEP));
-                               size += strlen(T_TOK_I18NSEP);
-                               i18n_hasdef = 2;
+                               tmp[size++] = ' ';
+                               whitespace = 1;
                        }
 
-                       /* At further whitespace, skip */
-                       else
+                       /* Suppress subsequent whitespace, escape special chars */
+                       else if( !isspace(data->out[i]) )
                        {
-                               continue;
+                               if( data->out[i] == '\\' || data->out[i] == '"' )
+                                       tmp[size++] = '\\';
+
+                               tmp[size++] = data->out[i];
+                               whitespace = 0;
                        }
                }
 
-               /* Escape quotes, backslashes and newlines for plain, i18n and include expressions */
-               if( (data->type == T_TYPE_TEXT || data->type == T_TYPE_I18N || data->type == T_TYPE_INCLUDE) &&
+               /* Escape quotes, backslashes and newlines for plain and include expressions */
+               else if( (data->type == T_TYPE_TEXT || data->type == T_TYPE_INCLUDE) &&
                    (data->out[i] == '\\' || data->out[i] == '"' || data->out[i] == '\n' || data->out[i] == '\t') )
                {
                        tmp[size++] = '\\';
@@ -186,12 +191,6 @@ static const char * generate_expression(struct template_parser *data, size_t *sz
                        }
                }
 
-               /* Found first whitespace in i18n expression, raise flag */
-               else if( isspace(data->out[i]) && (data->type == T_TYPE_I18N) && (i18n_hasdef == 0) )
-               {
-                       i18n_hasdef = 1;
-               }
-
                /* Normal char */
                else
                {
@@ -199,16 +198,14 @@ static const char * generate_expression(struct template_parser *data, size_t *sz
                }
        }
 
-       /* Processed i18n expression without default text, inject separator */
-       if( (data->type == T_TYPE_I18N) && (i18n_hasdef < 2) )
-       {
-               memcpy(&tmp[size], T_TOK_I18NSEP, strlen(T_TOK_I18NSEP));
-               size += strlen(T_TOK_I18NSEP);
-       }
-
        /* Inject trailing expression code (if any) */
        if( (what & T_GEN_END) && (gen_code[data->type][1] != NULL) )
        {
+               /* Strip trailing space for i18n expressions */
+               if( data->type == T_TYPE_I18N || data->type == T_TYPE_I18N_RAW )
+                       if( (size > 0) && (tmp[size-1] == ' ') )
+                               size--;
+
                memcpy(&tmp[size], gen_code[data->type][1], strlen(gen_code[data->type][1]));
                size += strlen(gen_code[data->type][1]);
        }
@@ -403,6 +400,11 @@ const char *template_reader(lua_State *L, void *ud, size_t *sz)
                                                data->type = T_TYPE_I18N;
                                                break;
 
+                                       case '_':
+                                               off++;
+                                               data->type = T_TYPE_I18N_RAW;
+                                               break;
+
                                        default:
                                                data->type = T_TYPE_CODE;
                                                break;
index 42ebdff69dc19019834dc7ea0091aedc405e8e50..24933f0c979c54fdb8206ed4617cefab3a6a7c44 100644 (file)
@@ -49,7 +49,6 @@
 #define T_TOK_START                    "<%"
 #define T_TOK_END                      "%>"
 #define T_TOK_SKIPWS           "-"
-#define T_TOK_I18NSEP          "\", \""
 
 /* generator flags */
 #define T_GEN_START                    0x01
@@ -61,7 +60,8 @@
 #define T_TYPE_EXPR                    2
 #define T_TYPE_INCLUDE                 3
 #define T_TYPE_I18N                    4
-#define T_TYPE_CODE                    5
+#define T_TYPE_I18N_RAW                5
+#define T_TYPE_CODE                    6
 
 /* parser state */
 struct template_parser {