Module:User:Theknightwho/preparser/core

This is a private module sandbox of Theknightwho, for their own experimentation. Items in this module may be added and removed at Theknightwho's discretion; do not rely on this module's stability.


local parent_frame = mw.getCurrentFrame()
local frame_factory = parent_frame:newChild{}

local function getNilParent(self)
	return nil
end

frame_factory.getParent = getNilParent

local function newCallbackParserValue(callback)
	local value = {}
	local cache
	function value:expand()
		if not cache then
			cache = callback()
		end
		return cache
	end
	return value
end

local function getArgument(self, opt)
	local name
	if type(opt) == "table" then
		name = opt.name
	else
		name = opt
	end

	return newCallbackParserValue(
		function ()
			return self.args[name]
		end
		)
end

local function getTitle(self)
	return self.title
end

local function newChild(self, opt)
	if type( opt ) ~= "table" then
		error("frame:newChild: the first parameter must be a table", 2)
	end
	
	local title, args
	if opt.title == nil then
		title = self.title
	else
		title = tostring(opt.title)
	end
	if opt.args == nil then
		args = {}
	elseif type(opt.args) ~= "table" then
		error("frame:newChild: args must be a table", 2)
	end
	
	local parent = self
	local child = frame_factory:newChild{}
	
	child.title = title
	child.args = args
	
	child.getArgument = getArgument
	child.newChild = newChild
	child.getTitle = getTitle
	
	function child:getParent()
		return parent
	end
	
	return child
end

parent_frame.title = parent_frame:getTitle()
parent_frame.getArgument = getArgument
parent_frame.getParent = getNilParent
parent_frame.newChild = newChild
parent_frame.getTitle = getTitle

local child_frame = parent_frame:newChild{}

local function parse()
	local templates = {
		["head"] = {"headword/templates", "head_t", {}},
		["l"] = {"links/templates", "l_term_t", {}},
		["m"] = {"links/templates", "l_term_t", {["face"] = "term"}},
		["t"] = {"translations", "show", {}},
		["t+"] = {"translations", "show", {["interwiki"] = "tpos"}}
	}
	local findTemplates = require("Module:templateparser").findTemplates
	local memo_key = require("Module:User:Theknightwho/preparser").memo_key
	local content = mw.title.getCurrentTitle():getContent()
	
	local output = {}
	if content then
		for template, args in findTemplates(content) do
			if templates[template] then
				local args_key = memo_key("Template:" .. template, args)
				if not output[args_key] then
					parent_frame.args = args
					child_frame.args = templates[template][3]
					child_frame.args["\255"] = true
					local ok, out = pcall(require("Module:" .. templates[template][1])[templates[template][2]], child_frame)
					if ok then
						output[args_key] = out
					end
				end
			end
		end
	end
	
	return output
end

return parse()