Module:smallest discussions

From Wiktionary, the free dictionary
Jump to navigation Jump to search

This module generates contents for Template:smallest discussions.


local export = {}

local shortLinkLength = 24
local columns = 4

local function parseLink(frame, page, section, format)

	if mw.ustring.find(section, "{") then
		section = frame:preprocess(section)
	end
	section = section:gsub("%[%[:", "[[")
	section = section:gsub("%[%[[^|%]]-|", "")
	section = section:gsub("%[%[", "")
	section = section:gsub("%]%]", "")

	local display = section
	if format == "box" and mw.ustring.len(display) > shortLinkLength then
		display = mw.ustring.sub(display, 1, shortLinkLength):gsub(" +$", "") .. "..."
	end

	result = "[[" .. page .. "#" .. mw.uri.anchorEncode(section) .. "|" .. display .. "]]"
	result = result:gsub("%<.-%>", "")

	return result
end

local function parsePage(frame, page, maxItems, format)
	local pageObject = mw.title.new(page)
	if pageObject.isRedirect then
		pageObject = pageObject.redirectTarget
		if format == "full" then
			page = pageObject.nsText .. ":" .. pageObject.text
		end
	end
	local pageText = pageObject:getContent()
	local pageLength = string.len(pageText)

	local pageResults = ""

	local discussionCount = 0
	local discussions = {}

	for line, newlines in pageText:gmatch('([^\n]*)(\n*)') do
		local m = line:match('^== *%f[^ =](.*)%f[ =] *==$')
		if m then
			discussionCount = discussionCount + 1
			discussions[discussionCount] = {title = m, length = newlines:len()}
		elseif discussionCount > 0 then
			discussions[discussionCount].length = discussions[discussionCount].length + line:len() + newlines:len()
		end
	end
	pageText = nil -- use less memory

	table.sort(discussions, function (a, b) return a.length < b.length end)

	if format == "full" then
		pageResults = pageResults .. "<h2>[[" .. page .. "]]</h2>"
		pageResults = pageResults .. "<small>Discussions: ".. discussionCount .. "</small><br/><small>Bytes: ".. pageLength .. "</small>"
		pageResults = pageResults .. '<div style="column-count:' .. columns .. '; -moz-column-count:' .. columns .. '; -webkit-column-count:' .. columns .. '">'
	elseif format == "box" then
		pageResults = pageResults .. "[[" .. page .. "]]"
	end

	pageResults = pageResults .. "<ol>"
	for i, discussion in ipairs(discussions) do
		if i > maxItems then
			break
		end
		pageResults = pageResults .. '<li>' .. parseLink(frame, page, discussion.title, format) .. ' <small dir="ltr">(' .. discussion.length .. ')</small></li>'
	end
	pageResults = pageResults .. "</ol>"

	if format == "full" then
		pageResults = pageResults .. '</div>'
	end

	return pageResults
end

local box_pre = [=[
<div class="toc" style="clear:right; float:right; width:auto; min-width:15em; border-top: none;">
<div class="mw-collapsible mw-collapsed"><strong>[[Wiktionary:Smallest discussions|Smallest discussions]]</strong>
<div class="mw-collapsible-content" style="margin-top: 10px; display:none;">
]=]

local function allPages(frame, pages, maxItems, format)
	local resultText = ""

	if format == "box" then
		resultText = resultText .. box_pre
	end

	for k, v in pairs(pages) do
		resultText = resultText .. parsePage(frame, v, maxItems, format)
	end

	if format == "box" then
		resultText = resultText .. '</div></div></div>'
	end

	return resultText
end

function export.show(frame, maxItems)
	local args = frame:getParent().args
	local format = args[1]
	local maxItems = tonumber(args[2])
	local pages = {}
	local i = 3
	while args[i] do
		table.insert(pages, args[i])
		i = i + 1
	end
	return allPages(frame, pages, maxItems, format)
end

return export