Permanently protected module
From Wikipedia, the free encyclopedia


-- This module provides functions for making MediaWiki template invocations.



local checkType = require('libraryUtil').checkType



local p = {}



------------------------------------------------------------------------

--         Name:  p.name

--      Purpose:  Find a template invocation name from a page name or a

--                mw.title object.

--  Description:  This function detects whether a string or a mw.title

--                object has been passed in, and uses that to find a

--                template name as it is used in template invocations.

--   Parameters:  title - full page name or mw.title object for the

--                template (string or mw.title object)

--      Returns:  String

------------------------------------------------------------------------



function p.name(title)

	if type(title) == 'string' then

		title = mw.title.new(title)

		if not title then

			error("invalid title in parameter #1 of function 'name'", 2)

		end

	elseif type(title) ~= 'table' or type(title.getContent) ~= 'function' then

		error("parameter #1 of function 'name' must be a string or a mw.title object", 2)

	end

	if title.namespace == 10 then

		return title.text

	elseif title.namespace == 0 then

		return ':' .. title.prefixedText

	else

		return title.prefixedText

	end

end



------------------------------------------------------------------------

--         Name:  p.invocation

--      Purpose:  Construct a MediaWiki template invocation.

--  Description:  This function makes a template invocation from the

--                name and the arguments given. Note that it isn't

--                perfect: we have no way of knowing what whitespace was

--                in the original invocation, the named parameters will be

--                alphabetically sorted, and any parameters with duplicate keys

--                will be removed.

--   Parameters:  name - the template name, formatted as it will appear

--                    in the invocation. (string)

--                args - a table of template arguments. (table)

--                format - formatting options. (string, optional)

--                    Set to "nowiki" to escape, curly braces, pipes and

--                    equals signs with their HTML entities. The default

--                    is unescaped.

--      Returns:  String

------------------------------------------------------------------------



function p.invocation(name, args, format)

	checkType('invocation', 1, name, 'string')

	checkType('invocation', 2, args, 'table')

	checkType('invocation', 3, format, 'string', true)



	-- Validate the args table and make a copy to work from. We need to

	-- make a copy of the table rather than just using the original, as

	-- some of the values may be erased when building the invocation.

	local invArgs = {}

	for k, v in pairs(args) do

		local typek = type(k)

		local typev = type(v)

		if typek ~= 'string' and typek ~= 'number'

			or typev ~= 'string' and typev ~= 'number'

		then

			error("invalid arguments table in parameter #2 of " ..

			"'invocation' (keys and values must be strings or numbers)", 2)

		end

		invArgsk = v

	end



	-- Get the separators to use.

	local seps = {

		openb = '{{',

		closeb = '}}',

		pipe = '|',

		equals = '='

	}

	if format == 'nowiki' then

		for k, v in pairs(seps) do

			sepsk = mw.text.nowiki(v)

		end

	end



	-- Build the invocation body with numbered args first, then named.

	local ret = {}

	ret#ret + 1 = seps.openb

	ret#ret + 1 = name

	for k, v in ipairs(invArgs) do

		if type(v) == 'string' and v:find('=', 1, true) then

			-- Likely something like 1=foo=bar which needs to be displayed as a named arg.

		else

			ret#ret + 1 = seps.pipe

			ret#ret + 1 = v

			invArgsk = nil -- Erase the key so that we don't add the value twice

		end

	end

	local keys = {} -- sort parameter list; better than arbitrary order

	for k, _ in pairs(invArgs) do

		keys#keys + 1 = k

	end

	table.sort(keys, function (a, b)

			-- Sort with keys of type number first, then string.

			if type(a) == type(b) then

				return a < b

			elseif type(a) == 'number' then

				return true

			end

		end)

	for _, v in ipairs(keys) do -- Add named args based on sorted parameter list

		ret#ret + 1 = ' ' .. seps.pipe

		ret#ret + 1 = tostring(v)

		ret#ret + 1 = seps.equals

		ret#ret + 1 = invArgsv

	end

	ret#ret + 1 = seps.closeb



	return table.concat(ret)

end



return p