Moved luci.sys.libpath to luci.util
[project/luci.git] / libs / web / luasrc / template.lua
index 5647865..907403f 100644 (file)
@@ -23,17 +23,20 @@ See the License for the specific language governing permissions and
 limitations under the License.
 
 ]]--
+
+--- LuCI template library.
 module("luci.template", package.seeall)
 
 require("luci.config")
 require("luci.util")
 require("luci.fs")
+require("luci.sys")
 require("luci.http")
 
 luci.config.template = luci.config.template or {}
 
-viewdir    = luci.config.template.viewdir or luci.sys.libpath() .. "/view"
-compiledir = luci.config.template.compiledir or luci.sys.libpath() .. "/view"
+viewdir    = luci.config.template.viewdir or luci.util.libpath() .. "/view"
+compiledir = luci.config.template.compiledir or luci.util.libpath() .. "/view"
 
 
 -- Compile modes:
@@ -50,9 +53,11 @@ viewns = {
        include    = function(name) Template(name):render(getfenv(2)) end,
 }
 
--- Compiles a given template into an executable Lua module
+--- Manually  compile a given template into an executable Lua function
+-- @param template     LuCI template
+-- @return                     Lua template function
 function compile(template)     
-       -- Search all <% %> expressions (remember: Lua table indexes begin with #1)
+       -- Search all <% %> expressions
        local function expr_add(ws1, skip1, command, skip2, ws2)
                table.insert(expr, command)
                return ( #skip1 > 0 and "" or ws1 ) .. 
@@ -68,31 +73,30 @@ function compile(template)
        template = template:gsub("(%s*)<%%(%-?)(.-)(%-?)%%>(%s*)", expr_add)
        
        local function sanitize(s)
-               s = luci.util.escape(s)
-               s = luci.util.escape(s, "'")
-               s = luci.util.escape(s, "\n")
-               return s
+               s = string.format("%q", s)
+               return s:sub(2, #s-1)
        end
        
        -- Escape and sanitize all the template (all non-expressions)
        template = sanitize(template)
 
        -- Template module header/footer declaration
-       local header = "write('"
-       local footer = "')"
+       local header = 'write("'
+       local footer = '")'
        
        template = header .. template .. footer
        
        -- Replacements
-       local r_include = "')\ninclude('%s')\nwrite('"
-       local r_i18n    = "'..translate('%1','%2')..'"
-       local r_i18n2    = "'..translate('%1', '')..'"
-       local r_pexec   = "'..(%s or '')..'"
-       local r_exec    = "')\n%s\nwrite('"
+       local r_include = '")\ninclude("%s")\nwrite("'
+       local r_i18n    = '"..translate("%1","%2").."'
+       local r_i18n2    = '"..translate("%1", "").."'
+       local r_pexec   = '"..(%s or "").."'
+       local r_exec    = '")\n%s\nwrite("'
        
        -- Parse the expressions
        for k,v in pairs(expr) do
                local p = v:sub(1, 1)
+               v = v:gsub("%%", "%%%%")
                local re = nil
                if p == "+" then
                        re = r_include:format(sanitize(string.sub(v, 2)))
@@ -115,7 +119,9 @@ function compile(template)
        return loadstring(template)
 end
 
--- Oldstyle render shortcut
+--- Render a certain template.
+-- @param name         Template name
+-- @param scope                Scope to assign to template
 function render(name, scope, ...)
        scope = scope or getfenv(2)
        local s, t = luci.util.copcall(Template, name)
@@ -179,7 +185,7 @@ function Template.__init__(self, name)
                        if source then
                                local compiled, err = compile(source)
                                
-                               luci.fs.writefile(compiledfile, luci.util.dump(compiled))
+                               luci.fs.writefile(compiledfile, luci.util.get_bytecode(compiled))
                                self.template = compiled
                        end
                else