Bug fixed and more refactoring

This commit is contained in:
perro tuerto 2023-03-28 13:25:02 -07:00
parent 80892f0f28
commit 8bdc6035a8
3 changed files with 359 additions and 343 deletions

384
dist/lin.lua vendored
View File

@ -6461,7 +6461,7 @@ local nat = {}
function nat.get(str)
return str
end
----------------------------------- LITERATE ----------------------------------
---------------------------------- LITERATE ----------------------------------
-- Variable for all literate stuff
local lit = {}
@ -6491,193 +6491,6 @@ lit.metastruct = {
},
}
function lit.stringify(content)
if pandoc.utils.type(content) == "Inlines" then
return pandoc.utils.stringify(content:walk {
Quoted = function(quoted)
local quote = (quoted.quotetype == SingleQuoted and '"' or "'")
quoted = pandoc.utils.stringify(quoted.content)
return pandoc.Str(quote .. quoted .. quote)
end,
RawInline = function(rawinline)
return pandoc.Str(rawinline.text:gsub("\\n", "\n"):gsub("\\t", "\t"))
end,
Inline = function(inline)
return pandoc.utils.stringify(inline)
end,
})
else
return pandoc.utils.stringify(content)
end
end
function lit.meta2table(meta)
for k, v in pairs(meta) do
if pandoc.utils.type(v) == "table" then
meta[k] = lit.meta2table(v)
else
v = lit.stringify(v)
print(v)
if v == "true" or v == "false" then
v = v == "true"
-- WARN!!
elseif tonumber(v) then
v = tonumber(v)
end
meta[k] = v
end
end
return meta
end
-- Messages for the user
lit.msg = lit.meta2table(pandoc.read([[---
INFO:
parsing:
en: Parsing:\n#1
es: Realizando análisis sintáctico:\n#1
WARNING:
foo:
en: bar
es: baz
ERROR:
invalid_key:
en: Invalid key '#1' with value '#2'
es: Clave '#1' inválida con valor '#2'
invalid_path:
en: Invalid path '#1' in key '#2'
es: Ruta '#1' inválida en clave '#2'
invalid_type:
en: Invalid type '#1' in key '#2'
es: Tipo '#1' inválido en clave '#2'
invalid_value:
en: Invalid value '#1' in key '#2'
es: Valor '#1' inválido en clave '#2'
no_key:
en: Key '#1' not found
es: Clave '#1' no encontrada
aborted:
en: Aborted due previous errors
es: Abortado debido a previos errores
yaml_empty:
en: Empty YAML
es: YAML vacío
yaml_invalid:
en: Invalid YAML
es: YAML inválido
...
]]).meta)
function lit.debuglevel(str)
if str == "ERROR" then
lit.status = false
return 2
elseif str == "WARNING" then
return 1
else
return 0
end
end
function lit.setmsg(msg, ...)
local lang = os.lang()
msg = (msg[lang] ~= nil and msg[lang] or msg)
for i, str in ipairs({...}) do
msg = msg:gsub("#" .. i, str)
end
return msg
end
function lit.getmsg(key, ...)
local levelname = "INFO"
local level = 0
for mtype, msgs in pairs(lit.msg) do
if msgs[key] ~= nil then
key = lit.setmsg(msgs[key], ...)
levelname, level = mtype, lit.debuglevel(mtype)
break
end
end
return key, levelname, level
end
function lit.puts(key, ...)
local verbosity = lit.debuglevel(PANDOC_STATE.verbosity)
local msg, levelname, level = lit.getmsg(key, ...)
if level >= verbosity then
print("[" .. levelname .. "] [LIT] " .. msg)
end
end
function lit.getmetaval(meta, key)
local mtype = pandoc.utils.type(meta[key])
local mval = meta[key]
if mtype == "Inlines" then
mval = pandoc.utils.stringify(mval)
mtype = pandoc.utils.type(mval)
end
return mval, mtype
end
function lit.checkmetaextra(meta)
for key, val in pairs(meta) do
local missing1 = lit.metastruct["mandatory"][key] == nil
local missing2 = lit.metastruct["optional"][key] == nil
local mval = lit.getmetaval(meta, key)
if missing1 and missing2 then
lit.puts("invalid_key", key, mval)
end
end
end
function lit.checkmetatype(type, meta, key)
local mval, mtype = lit.getmetaval(meta, key)
if type ~= mtype then
if type == "path" then
if not(pandoc.path.directory(mval):isdir()) then
lit.puts("invalid_path", mval, key)
end
else
lit.puts("invalid_type", mtype, key)
end
end
end
-- TODO: has bug
function lit.checkmetatable(table, meta, key)
local mval = lit.getmetaval(meta, key)
for _, pattern in pairs(table) do
if mval:match("^" .. pattern .. "$") == nil then
lit.puts("invalid_value", mval, key)
end
end
end
function lit.checkmeta(meta, kind)
for key, val in pairs(lit.metastruct[kind]) do
if meta[key] == nil then
if kind == "mandatory" then
lit.puts("no_key", key)
end
else
if type(val) == "table" then
lit.checkmetatable(val, meta, key)
else
lit.checkmetatype(val, meta, key)
end
end
end
end
function lit.setmeta(meta)
lit.checkmeta(meta, "mandatory")
lit.checkmeta(meta, "optional")
lit.checkmetaextra(meta)
-- TODO checks for 2) duplicates
-- Set defaults if lit.status = true
return meta
end
-- Grammars
lit.g = {}
@ -6718,6 +6531,200 @@ function lit.eval(code)
end
]]--
function lit.stringify_quoted(quoted)
local quote = (quoted.quotetype == SingleQuoted and '"' or "'")
quoted = pandoc.utils.stringify(quoted.content)
return pandoc.Str(quote .. quoted .. quote)
end
function lit.stringify_rawinline(rawinline)
local str = rawinline.text
str = str:gsub("\\n", "\n"):gsub("\\t", "\t")
return pandoc.Str(str)
end
function lit.stringify(content)
if pandoc.utils.type(content) == "Inlines" then
return pandoc.utils.stringify(content:walk {
Quoted = function(e) return lit.stringify_quoted(e) end,
RawInline = function(e) return lit.stringify_rawinline(e) end,
Inline = function(inline) return pandoc.utils.stringify(inline) end,
})
else
return pandoc.utils.stringify(content)
end
end
function lit.string2other(str)
if str == "true" or str == "false" then
return str == "true"
-- WARN "1" always num; cfr. https://pandoc.org/lua-filters.html#type-metavalue
elseif tonumber(str) then
return tonumber(str)
else
return str
end
end
function lit.meta2table(meta)
for k, v in pairs(meta) do
if pandoc.utils.type(v) == "table" then
meta[k] = lit.meta2table(v)
else
meta[k] = lit.string2other(lit.stringify(v))
end
end
return meta
end
function lit.debuglevel(str)
if str == "ERROR" then
lit.status = false
return 2
elseif str == "WARNING" then
return 1
else
return 0
end
end
function lit.setmsg(msg, ...)
local lang = os.lang()
msg = (msg[lang] ~= nil and msg[lang] or msg)
for i, str in ipairs({...}) do
msg = msg:gsub("#" .. i, str)
end
return msg
end
function lit.getmsg(key, ...)
local msg = lit.meta2table(pandoc.read([[---
INFO:
parsing:
en: Parsing:\n#1
es: Realizando análisis sintáctico:\n#1
WARNING:
foo:
en: bar
es: baz
ERROR:
invalid_key:
en: Invalid key '#1'
es: Clave '#1' inválida
invalid_path:
en: Invalid path '#1' in key '#2'
es: Ruta '#1' inválida en clave '#2'
invalid_type:
en: Invalid type '#1' in key '#2'
es: Tipo '#1' inválido en clave '#2'
invalid_value:
en: Invalid value '#1' in key '#2'
es: Valor '#1' inválido en clave '#2'
no_key:
en: Key '#1' not found
es: Clave '#1' no encontrada
aborted:
en: Aborted due previous errors
es: Abortado debido a previos errores
yaml_empty:
en: Empty YAML
es: YAML vacío
yaml_invalid:
en: Invalid YAML
es: YAML inválido
...
]]).meta)
local levelname, level = "INFO", 0
for mtype, msgs in pairs(msg) do
if msgs[key] ~= nil then
key = lit.setmsg(msgs[key], ...)
levelname, level = mtype, lit.debuglevel(mtype)
break
end
end
return key, levelname, level
end
function lit.puts(key, ...)
local verbosity = lit.debuglevel(PANDOC_STATE.verbosity)
local msg, levelname, level = lit.getmsg(key, ...)
if level >= verbosity then
print("[" .. levelname .. "] [LIT] " .. msg)
end
end
function lit.getmetaval(meta, key)
local mtype = pandoc.utils.type(meta[key])
local mval = meta[key]
if mtype == "Inlines" then
mval = pandoc.utils.stringify(mval)
mtype = pandoc.utils.type(mval)
end
return mval, mtype
end
function lit.checkextra(meta)
for key, val in pairs(meta) do
local missing1 = lit.metastruct["mandatory"][key] == nil
local missing2 = lit.metastruct["optional"][key] == nil
local mval = lit.getmetaval(meta, key)
if missing1 and missing2 then
lit.puts("invalid_key", key)
end
end
end
function lit.checkmeta_type(type, meta, key)
local mval, mtype = lit.getmetaval(meta, key)
if type ~= mtype then
if type == "path" then
if not(pandoc.path.directory(mval):isdir()) then
lit.puts("invalid_path", mval, key)
end
else
lit.puts("invalid_type", mtype, key)
end
end
end
function lit.checkmeta_match(table, mval, key)
for _, pattern in pairs(table) do
if mval:match("^" .. pattern .. "$") then
return ""
end
end
return key
end
function lit.checkmeta_table(table, meta, key)
local mval = lit.getmetaval(meta, key)
local err = lit.checkmeta_match(table, mval, key)
if not(err:isempty()) then
lit.puts("invalid_value", mval, err)
end
end
function lit.checkmeta(meta, kind)
for key, val in pairs(lit.metastruct[kind]) do
if meta[key] == nil and kind == "mandatory" then
lit.puts("no_key", key)
elseif meta[key] and type(val) == "table" then
lit.checkmeta_table(val, meta, key)
elseif meta[key] then
lit.checkmeta_type(val, meta, key)
end
end
end
function lit.setmeta(meta)
lit.checkmeta(meta, "mandatory")
lit.checkmeta(meta, "optional")
lit.checkextra(meta)
-- TODO checks for 2) duplicates
-- Set defaults if lit.status = true
return meta
end
-- TODO
function lit.assert(e, status)
if status == false then
@ -6728,6 +6735,7 @@ function lit.assert(e, status)
end
function lit.parseyaml(rawyaml)
-- TODO io.try
local yaml = io.popen("pandoc -t json <<<\"" .. rawyaml .. "\" 2>&1")
if yaml:read("*l"):sub(1, 1) == "{" then
yaml = pandoc.read(rawyaml).meta

View File

@ -1,4 +1,4 @@
----------------------------------- LITERATE ----------------------------------
---------------------------------- LITERATE ----------------------------------
-- Variable for all literate stuff
local lit = {}
@ -28,158 +28,6 @@ lit.metastruct = {
},
}
function lit.stringify(content)
if pandoc.utils.type(content) == "Inlines" then
return pandoc.utils.stringify(content:walk {
Quoted = function(quoted)
local quote = (quoted.quotetype == SingleQuoted and '"' or "'")
quoted = pandoc.utils.stringify(quoted.content)
return pandoc.Str(quote .. quoted .. quote)
end,
RawInline = function(rawinline)
return pandoc.Str(rawinline.text:gsub("\\n", "\n"):gsub("\\t", "\t"))
end,
Inline = function(inline)
return pandoc.utils.stringify(inline)
end,
})
else
return pandoc.utils.stringify(content)
end
end
function lit.meta2table(meta)
for k, v in pairs(meta) do
if pandoc.utils.type(v) == "table" then
meta[k] = lit.meta2table(v)
else
v = lit.stringify(v)
print(v)
if v == "true" or v == "false" then
v = v == "true"
-- WARN!!
elseif tonumber(v) then
v = tonumber(v)
end
meta[k] = v
end
end
return meta
end
-- Messages for the user
lit.msg = lit.meta2table(pandoc.read([[#locale()]]).meta)
function lit.debuglevel(str)
if str == "ERROR" then
lit.status = false
return 2
elseif str == "WARNING" then
return 1
else
return 0
end
end
function lit.setmsg(msg, ...)
local lang = os.lang()
msg = (msg[lang] ~= nil and msg[lang] or msg)
for i, str in ipairs({...}) do
msg = msg:gsub("#" .. i, str)
end
return msg
end
function lit.getmsg(key, ...)
local levelname = "INFO"
local level = 0
for mtype, msgs in pairs(lit.msg) do
if msgs[key] ~= nil then
key = lit.setmsg(msgs[key], ...)
levelname, level = mtype, lit.debuglevel(mtype)
break
end
end
return key, levelname, level
end
function lit.puts(key, ...)
local verbosity = lit.debuglevel(PANDOC_STATE.verbosity)
local msg, levelname, level = lit.getmsg(key, ...)
if level >= verbosity then
print("[" .. levelname .. "] [LIT] " .. msg)
end
end
function lit.getmetaval(meta, key)
local mtype = pandoc.utils.type(meta[key])
local mval = meta[key]
if mtype == "Inlines" then
mval = pandoc.utils.stringify(mval)
mtype = pandoc.utils.type(mval)
end
return mval, mtype
end
function lit.checkmetaextra(meta)
for key, val in pairs(meta) do
local missing1 = lit.metastruct["mandatory"][key] == nil
local missing2 = lit.metastruct["optional"][key] == nil
local mval = lit.getmetaval(meta, key)
if missing1 and missing2 then
lit.puts("invalid_key", key, mval)
end
end
end
function lit.checkmetatype(type, meta, key)
local mval, mtype = lit.getmetaval(meta, key)
if type ~= mtype then
if type == "path" then
if not(pandoc.path.directory(mval):isdir()) then
lit.puts("invalid_path", mval, key)
end
else
lit.puts("invalid_type", mtype, key)
end
end
end
-- TODO: has bug
function lit.checkmetatable(table, meta, key)
local mval = lit.getmetaval(meta, key)
for _, pattern in pairs(table) do
if mval:match("^" .. pattern .. "$") == nil then
lit.puts("invalid_value", mval, key)
end
end
end
function lit.checkmeta(meta, kind)
for key, val in pairs(lit.metastruct[kind]) do
if meta[key] == nil then
if kind == "mandatory" then
lit.puts("no_key", key)
end
else
if type(val) == "table" then
lit.checkmetatable(val, meta, key)
else
lit.checkmetatype(val, meta, key)
end
end
end
end
function lit.setmeta(meta)
lit.checkmeta(meta, "mandatory")
lit.checkmeta(meta, "optional")
lit.checkmetaextra(meta)
-- TODO checks for 2) duplicates
-- Set defaults if lit.status = true
return meta
end
-- Grammars
lit.g = {}
@ -220,6 +68,165 @@ function lit.eval(code)
end
]]--
function lit.stringify_quoted(quoted)
local quote = (quoted.quotetype == SingleQuoted and '"' or "'")
quoted = pandoc.utils.stringify(quoted.content)
return pandoc.Str(quote .. quoted .. quote)
end
function lit.stringify_rawinline(rawinline)
local str = rawinline.text
str = str:gsub("\\n", "\n"):gsub("\\t", "\t")
return pandoc.Str(str)
end
function lit.stringify(content)
if pandoc.utils.type(content) == "Inlines" then
return pandoc.utils.stringify(content:walk {
Quoted = function(e) return lit.stringify_quoted(e) end,
RawInline = function(e) return lit.stringify_rawinline(e) end,
Inline = function(inline) return pandoc.utils.stringify(inline) end,
})
else
return pandoc.utils.stringify(content)
end
end
function lit.string2other(str)
if str == "true" or str == "false" then
return str == "true"
-- WARN "1" always num; cfr. https://pandoc.org/lua-filters.html#type-metavalue
elseif tonumber(str) then
return tonumber(str)
else
return str
end
end
function lit.meta2table(meta)
for k, v in pairs(meta) do
if pandoc.utils.type(v) == "table" then
meta[k] = lit.meta2table(v)
else
meta[k] = lit.string2other(lit.stringify(v))
end
end
return meta
end
function lit.debuglevel(str)
if str == "ERROR" then
lit.status = false
return 2
elseif str == "WARNING" then
return 1
else
return 0
end
end
function lit.setmsg(msg, ...)
local lang = os.lang()
msg = (msg[lang] ~= nil and msg[lang] or msg)
for i, str in ipairs({...}) do
msg = msg:gsub("#" .. i, str)
end
return msg
end
function lit.getmsg(key, ...)
local msg = lit.meta2table(pandoc.read([[#locale()]]).meta)
local levelname, level = "INFO", 0
for mtype, msgs in pairs(msg) do
if msgs[key] ~= nil then
key = lit.setmsg(msgs[key], ...)
levelname, level = mtype, lit.debuglevel(mtype)
break
end
end
return key, levelname, level
end
function lit.puts(key, ...)
local verbosity = lit.debuglevel(PANDOC_STATE.verbosity)
local msg, levelname, level = lit.getmsg(key, ...)
if level >= verbosity then
print("[" .. levelname .. "] [LIT] " .. msg)
end
end
function lit.getmetaval(meta, key)
local mtype = pandoc.utils.type(meta[key])
local mval = meta[key]
if mtype == "Inlines" then
mval = pandoc.utils.stringify(mval)
mtype = pandoc.utils.type(mval)
end
return mval, mtype
end
function lit.checkextra(meta)
for key, val in pairs(meta) do
local missing1 = lit.metastruct["mandatory"][key] == nil
local missing2 = lit.metastruct["optional"][key] == nil
local mval = lit.getmetaval(meta, key)
if missing1 and missing2 then
lit.puts("invalid_key", key)
end
end
end
function lit.checkmeta_type(type, meta, key)
local mval, mtype = lit.getmetaval(meta, key)
if type ~= mtype then
if type == "path" then
if not(pandoc.path.directory(mval):isdir()) then
lit.puts("invalid_path", mval, key)
end
else
lit.puts("invalid_type", mtype, key)
end
end
end
function lit.checkmeta_match(table, mval, key)
for _, pattern in pairs(table) do
if mval:match("^" .. pattern .. "$") then
return ""
end
end
return key
end
function lit.checkmeta_table(table, meta, key)
local mval = lit.getmetaval(meta, key)
local err = lit.checkmeta_match(table, mval, key)
if not(err:isempty()) then
lit.puts("invalid_value", mval, err)
end
end
function lit.checkmeta(meta, kind)
for key, val in pairs(lit.metastruct[kind]) do
if meta[key] == nil and kind == "mandatory" then
lit.puts("no_key", key)
elseif meta[key] and type(val) == "table" then
lit.checkmeta_table(val, meta, key)
elseif meta[key] then
lit.checkmeta_type(val, meta, key)
end
end
end
function lit.setmeta(meta)
lit.checkmeta(meta, "mandatory")
lit.checkmeta(meta, "optional")
lit.checkextra(meta)
-- TODO checks for 2) duplicates
-- Set defaults if lit.status = true
return meta
end
-- TODO
function lit.assert(e, status)
if status == false then
@ -230,6 +237,7 @@ function lit.assert(e, status)
end
function lit.parseyaml(rawyaml)
-- TODO io.try
local yaml = io.popen("pandoc -t json <<<\"" .. rawyaml .. "\" 2>&1")
if yaml:read("*l"):sub(1, 1) == "{" then
yaml = pandoc.read(rawyaml).meta

View File

@ -9,8 +9,8 @@ WARNING:
es: baz
ERROR:
invalid_key:
en: Invalid key '#1' with value '#2'
es: Clave '#1' inválida con valor '#2'
en: Invalid key '#1'
es: Clave '#1' inválida
invalid_path:
en: Invalid path '#1' in key '#2'
es: Ruta '#1' inválida en clave '#2'