diff options
author | Taco Hoekwater <taco@elvenkind.com> | 2009-08-23 11:11:32 +0000 |
---|---|---|
committer | Taco Hoekwater <taco@elvenkind.com> | 2009-08-23 11:11:32 +0000 |
commit | 8fc3039c82d48605b5ca8b2eda3f4fdd755681e1 (patch) | |
tree | 3cd9bbdd599bc4d1ac0409e167fee2136e4c0ec9 /Master/texmf-dist/tex/context/base/l-xml-edu.lua | |
parent | 850fc99b7cd3ae7a20065531fe866ff7bae642ec (diff) |
this is context 2009.08.19 17:10
git-svn-id: svn://tug.org/texlive/trunk@14827 c570f23f-e606-0410-a88d-b1316a301751
Diffstat (limited to 'Master/texmf-dist/tex/context/base/l-xml-edu.lua')
-rw-r--r-- | Master/texmf-dist/tex/context/base/l-xml-edu.lua | 381 |
1 files changed, 0 insertions, 381 deletions
diff --git a/Master/texmf-dist/tex/context/base/l-xml-edu.lua b/Master/texmf-dist/tex/context/base/l-xml-edu.lua deleted file mode 100644 index 5aba4604349..00000000000 --- a/Master/texmf-dist/tex/context/base/l-xml-edu.lua +++ /dev/null @@ -1,381 +0,0 @@ -if not modules then modules = { } end modules ['l-xml-edu'] = { - version = 1.001, - comment = "this module is the basis for the lxml-* ones", - author = "Hans Hagen, PRAGMA-ADE, Hasselt NL", - copyright = "PRAGMA ADE / ConTeXt Development Team", - license = "see context related readme files" -} - ---[[ldx-- -<p>This module contains older code thatwe keep around for educational -purposes. Here you find the find based xml and lpath parsers.</p> ---ldx]]-- - -if false then - - do - - -- Loading 12 cont-*.xml and keys-*.xml files totaling to 2.62 MBytes takes 1.1 sec - -- on a windows vista laptop with dual core 7600 (2.3 Ghz), which is not that bad. - -- Of this half time is spent on doctype etc parsing. - - local doctype_patterns = { - "<!DOCTYPE%s+(.-%s+PUBLIC%s+%b\"\"%s+%b\"\"%s+%b[])%s*>", - "<!DOCTYPE%s+(.-%s+PUBLIC%s+%b\"\"%s+%b\"\")%s*>", - "<!DOCTYPE%s+(.-%s+SYSTEM%s+%b\"\"%s+%b[])%s*>", - "<!DOCTYPE%s+(.-%s+SYSTEM%s+%b\"\")%s*>", - "<!DOCTYPE%s+(.-%s%b[])%s*>", - "<!DOCTYPE%s+(.-)%s*>" - } - - -- We assume no "<" which is the lunatic part of the xml spec - -- especially since ">" is permitted; otherwise we need a char - -- by char parser ... more something for later ... normally - -- entities will be used anyway. - - -- data = data:gsub(nothing done) is still a copy so we find first - - local function prepare(data,text) - -- pack (for backward compatibility) - if type(data) == "table" then - data = table.concat(data,"") - end - -- CDATA - if data:find("<!%[CDATA%[") then - data = data:gsub("<!%[CDATA%[(.-)%]%]>", function(txt) - text[#text+1] = txt or "" - return string.format("<@cd@>%s</@cd@>",#text) - end) - end - -- DOCTYPE - if data:find("<!DOCTYPE ") then - data = data:gsub("^(.-)(<[^!?])", function(a,b) - if a:find("<!DOCTYPE ") then -- ? - for _,v in ipairs(doctype_patterns) do - a = a:gsub(v, function(d) - text[#text+1] = d or "" - return string.format("<@dt@>%s</@dt@>",#text) - end) - end - end - return a .. b - end,1) - end - -- comment / does not catch doctype - if data:find("<!%-%-") then - data = data:gsub("<!%-%-(.-)%-%->", function(txt) - text[#text+1] = txt or "" - return string.format("<@cm@>%s</@cm@>",#text) - end) - end - -- processing instructions / altijd 1 - if data:find("<%?") then - data = data:gsub("<%?(.-)%?>", function(txt) - text[#text+1] = txt or "" - return string.format("<@pi@>%s</@pi@>",#text) - end) - end - return data, text - end - - -- maybe we will move the @tg@ stuff to a dedicated key, say 'st'; this will speed up - -- serializing and testing - - function xml.convert(data,no_root,collapse) - local crap = { } - data, crap = prepare(data, crap) - local nsremap = xml.xmlns - local remove = table.remove - local stack, top = {}, {} - local i, j, errorstr = 1, 1, nil - stack[#stack+1] = top - top.dt = { } - local dt = top.dt - local mt = { __tostring = xml.text } - local xmlns = { } - while true do - local ni, first, attributes, last, fulltag, resolved - ni, j, first, fulltag, attributes, last = data:find("<(/-)([^%s>/]+)%s*([^>]-)%s*(/-)>", j) - if not ni then break end - local namespace, tag = fulltag:match("^(.-):(.+)$") - if attributes ~= "" then - local t = {} - for ns, tag, _, value in attributes:gmatch("(.-):?(.+)=([\"\'])(.-)%3") do -- . was %w - if tag == "xmlns" then -- not ok yet - xmlns[#xmlns+1] = xml.resolvens(value) - t[tag] = value - elseif ns == "xmlns" then - xml.checkns(tag,value) - t["xmlns:" .. tag] = value - else - t[tag] = value - end - end - attributes = t - else - attributes = { } - end - if namespace then -- realtime remapping - resolved = nsremap[namespace] or namespace - else - namespace, tag = "", fulltag - resolved = xmlns[#xmlns] - end - local text = data:sub(i, ni-1) - if text == "" or (collapse and text:find("^%s*$")) then - -- no need for empty text nodes, beware, also packs <a>x y z</a> - -- so is not that useful unless used with empty elements - else - dt[#dt+1] = text - end - if first == "/" then - -- end tag - local toclose = remove(stack) -- remove top - top = stack[#stack] - if #stack < 1 then - errorstr = string.format("nothing to close with %s", tag) - break - elseif toclose.tg ~= tag then -- no namespace check - errorstr = string.format("unable to close %s with %s", toclose.tg, tag) - break - end - if tag:find("^@..@$") then - dt[1] = crap[tonumber(dt[1])] or "" - end - dt = top.dt - dt[#dt+1] = toclose - if attributes.xmlns then - remove(xmlns) -- ? - end - elseif last == "/" then - -- empty element tag - dt[#dt+1] = { ns = namespace, rn = resolved, tg = tag, dt = { }, at = attributes, __p__ = top } - setmetatable(top, mt) - else - -- begin tag - top = { ns = namespace, rn = resolved, tg = tag, dt = { }, at = attributes, __p__ = stack[#stack] } - setmetatable(top, mt) - dt = top.dt - stack[#stack+1] = top - end - i = j + 1 - end - if not errorstr then - local text = data:sub(i) - if dt and not text:find("^%s*$") then - dt[#dt+1] = text - end - if #stack > 1 then - errorstr = string.format("unclosed %s", stack[#stack].tg) - end - end - if errorstr then - stack = { { tg = "error", dt = { errorstr } } } - setmetatable(stack, mt) - end - if no_root then - return stack[1] - else - local t = { ns = "", tg = '@rt@', dt = stack[1].dt } - setmetatable(t, mt) - for k,v in ipairs(t.dt) do - if type(v) == "table" and v.tg ~= "@pi@" and v.tg ~= "@dt@" and v.tg ~= "@cm@" then - t.ri = k -- rootindex - break - end - end - return t - end - end - - end - - --~ Y a/b - --~ Y /a/b - --~ Y a/*/b - --~ Y a//b - --~ Y child:: - --~ Y .// - --~ Y .. - --~ N id("tag") - --~ Y parent:: - --~ Y child:: - --~ N preceding-sibling:: (same name) - --~ N following-sibling:: (same name) - --~ N preceding-sibling-of-self:: (same name) - --~ N following-sibling-or-self:: (same name) - --~ N ancestor:: - --~ N descendent:: - --~ N preceding:: - --~ N following:: - --~ N self::node() - --~ N node() == alles - --~ N a[position()=5] - --~ Y a[5] - --~ Y a[-5] - --~ N a[first()] - --~ N a[last()] - --~ Y a/(b|c|d)/e/f - --~ Y a/!(b|c|d)/e/f - --~ N (c/d|e) - --~ Y a/b[@bla] - --~ Y a/b[@bla='oeps'] - --~ Y a/b[@bla=='oeps'] - --~ Y a/b[@bla<>'oeps'] - --~ Y a/b[@bla!='oeps'] - --~ Y a/b/@bla - --~ Y a['string'] - --~ Y ^/a/c (root) - --~ Y ^^/a/c (docroot) - --~ Y root::a/c (docroot) - --~ no wild card functions (yet) - --~ s = "/a//b/*/(c|d|e)/(f|g)/h[4]/h/child::i/j/(a/b)/p[-1]/q[4]/ancestor::q/r/../s/./t[@bla='true']/k" - -- // == /**/ - -- / = ^ (root) - - do - - function analyze(str) - if not str then - return "" - else - local tmp, result, map, key = { }, { }, { }, str - str = str:gsub("(%b[])", function(s) tmp[#tmp+1] = s return '[['..#tmp..']]' end) - str = str:gsub("(%b())", function(s) tmp[#tmp+1] = s return '[['..#tmp..']]' end) - str = str:gsub("(%^+)([^/])", "%1/%2") - str = str:gsub("//+", "/**/") - str = str:gsub(".*root::", "^/") - str = str:gsub("child::", "") - str = str:gsub("parent::", "../") - str = str:gsub("self::", "./") - str = str:gsub("^/", "^/") - for s in str:gmatch("([^/]+)") do - s = s:gsub("%[%[(%d+)%]%]",function(n) return tmp[tonumber(n)] end) - result[#result+1] = s - end - return result - end - end - - function compose(result) - if not result or #result == 0 then - -- wildcard - return true - elseif #result == 1 then - local r = result[1][1] - if r == "14" or r == "15" then - -- wildcard - return true - elseif r == "12" then - -- root - return false - end - end - local map = { } - for r=1,#result do - local ri = result[r] - if ri == "." then - -- skip - elseif ri == ".." then - map[#map+1] = { 11 } - elseif ri == "^" then - map[#map+1] = { 12 } - elseif ri == "^^" then - map[#map+1] = { 13 } - elseif ri == "*" then - map[#map+1] = { 14 } - elseif ri == "**" then - map[#map+1] = { 15 } - else - local negate, m = ri:match("^(!*)%((.*)%)$") -- (a|b|c) - if m or ri:find('|') then - m = m or ri - if m:find("[%[%]%(%)/]") then -- []()/ - -- error - else - local t = { (negate and #negate>0 and 25) or 21 } - for s in m:gmatch("([^|]+)") do - local ns, tg = s:match("^(.-):?([^:]+)$") - if ns == "*" then ns = true end - t[#t+1] = ns - t[#t+1] = tg - end - map[#map+1] = t - end - else - local s, f = ri:match("^(.-)%[%s*(.+)%s*%]$") --aaa[bbb] - if s and f then - local ns, tg = s:match("^(.-):?([^:]+)$") - local at, op, vl = f:match("^@(.-)([!=<>]?)([^!=<>]+)$") -- [@a=='b'] - if ns == "*" then ns = true end - if vl then - if op and op ~= "" then - if op == '=' or op == '==' then - map[#map+1] = { 22, ns, tg, at, (vl:gsub("^([\'\"])(.*)%1$","%2")) } - elseif op == '<>' or op == '!=' then - map[#map+1] = { 23, ns, tg, at, (vl:gsub("^([\'\"])(.*)%1$","%2")) } - else - -- error - end - elseif vl ~= "" then -- [@whatever] - map[#map+1] = { 26, ns, tg, vl } - else - -- error - end - -- elseif f:find("^([%-%+%d]+)$") then -- [123] - elseif f:find("^([-+%d]+)$") then -- [123] - map[#map+1] = { 30, ns, tg, tonumber(f) } - else -- [whatever] - map[#map+1] = { 27, ns, tg, (f:gsub("^([\'\"])(.*)%1$","%2")) } - end - else - local pi = ri:match("^pi::(.-)$") - if pi then - map[#map+1] = { 40, pi } - else - local negate, ns, tg = ri:match("^(!-)(.-):?([^:]+)$") - map[#map+1] = { (negate and #negate>0 and 24) or 20, ns, tg } - end - end - end - end - end - -- if we have a symbol, we can prepend that to the string, which is faster - local mm = map[1] or { } - local r = mm[1] or 0 - if #map == 1 then - if r == 14 or r == 15 then - -- wildcard - return true - elseif r == 12 then - -- root - return false - end - end - if r ~= 11 and r ~= 12 and r ~= 13 and r ~= 14 and r ~= 15 then - table.insert(map, 1, { 16 }) - end - return map - end - - cache = { } - - function xml.lpath(pattern) - if type(pattern) == "string" then - local result = cache[pattern] - if not result then - result = compose(analyze(pattern)) - cache[pattern] = result - end - if xml.trace_lpath then - xml.lshow(result) - end - return result - else - return pattern - end - end - - end - -end |