Modul:dara kategoriyan

local export = {}

local m_utilities = require('Modul:utilities')
local inFundamental = mw.loadData("Modul:dara kategoriyan/dane")

local show_error, check_name, link_box, show_catfix, show_categories,
	show_editlink, show_pagelist, show_breadcrumbs, show_description,
	show_TOC


local function capitalize(text)
	return mw.getContentLanguage():ucfirst(text)
end

-- The main entry point.
-- This is the only function that can be invoked from a template.
function export.show(frame)
	local template = frame.args["template"]
	
	if not template or template == "" then
		error("Parametreya \"template\" nehatiye dayîn.")
	end
	
	if mw.title.getCurrentTitle().nsText == "Şablon" then
		local text = {}
		table.insert(text, "[[Kategorî:Şablonên kategorîkirinê|*]]Ev şablon tenê di rûpelên Kategorî: de tê bikaranîn.")
		table.insert(text, " Ji bo agahiyên zêdetir binêre [[Modul:dara kategoriyan]] û binmodulên wê [[Modul:dara kategoriyan/")
		table.insert(text, template .. "]].")
		if frame.args["useautocat"] then
			table.insert(text, " Dewsa bikaranîna vê şablonê şablona ")
			table.insert(text, require("Modul:template link").format_link({"katbike"}))
			table.insert(text, " (bêyî nivîsîna tiştekî din), bi kar bîne.")
		end
		return table.concat(text)
	elseif mw.title.getCurrentTitle().nsText ~= "Kategorî" then
		error("Ev şablon tenê di rûpelên bi Kategorî: dest pê dikin de tê bikaranîn.")
	end
	
	local submodule = require("Modul:dara kategoriyan/" .. template)
	
	-- Get all the parameters and the label data
	local current
	
	if submodule.new_main then
		current = submodule.new_main(frame)
	else
		local info = {}
		
		for key, val in pairs(frame.args) do
			if val ~= "" and key ~= "useautocat" then
				info[key] = val
			end
		end
	
		info.template = nil
		current = submodule.new(info, true)
	end
	
	local functions = {
		"getBreadcrumbName",
		"getDataModule",
		"canBeEmpty",
		"getDescription",
		"getParents",
		"getUmbrella",
	}
	
	if current then
		for i, functionName in pairs(functions) do
			if type(current[functionName]) ~= "function" then
				require("Modul:debug").track{ "dara kategoriyan/kêmasiya fonksîyonê", "dara kategoriyan/kêmasiya fonksîyonê/" .. functionName }
			end
		end
	end

	local boxes = {}
	local display = {}
	local categories = {}

	if template == "topic cat" then
		table.insert(categories, "[[Kategorî:topic cat]]")
	end
	
	-- Check if the category is empty
	local isEmpty = mw.site.stats.pagesInCategory(mw.title.getCurrentTitle().text, "all") == 0
	
	-- Are the parameters valid?
	if not current then
		table.insert(categories, "[[Kategorî:Kategoriyên bi etîketên şaş]]")
		table.insert(categories, isEmpty and "[[Kategorî:Kategoriyên vala]]" or nil)
		table.insert(display, show_error(
			"Etîketa di şablona " ..
			require("Modul:template link").format_link{template} ..
			" de naxebite. Dibe ku şaş be yan hîn nehatibe çêkirin. " ..
			"Ji bo lêzêdekirina etîketa nû ji kerema xwe binêre belgekirina şablonê."))
		
		-- Exit here, as all code beyond here relies on current not being nil
		return table.concat(categories, "") .. table.concat(display, "\n\n")
	end
	
		-- Does the category have the correct name?
	if mw.title.getCurrentTitle().text ~= current:getCategoryName() then
		table.insert(categories, "[[Kategorî:Kategoriyên bi navê şaş]]")
		table.insert(display, show_error(
			"Li gorî parametreyên şablona " ..
			require("Modul:template link").format_link{template} ..
			", navê vê kategoriyê divê '''[[:Kategorî:" .. current:getCategoryName() .. "]]''' be."))
	end
	
	-- Add cleanup category for empty categories
	local canBeEmpty = current:canBeEmpty()
	if isEmpty and not canBeEmpty then
		table.insert(categories, "[[Kategorî:Kategoriyên vala]]")
	end
	
	if current:isHidden() then
		table.insert(categories, "__HIDDENCAT__")
	end

	if canBeEmpty then
		table.insert(categories, " __EXPECTUNUSEDCATEGORY__")
	end
	
	table.insert(boxes, show_editlink(current))
	
	-- Generate the displayed information
	table.insert(display, show_breadcrumbs(current))
	table.insert(display, show_description(current))
	table.insert(display, show_TOC(current))
	table.insert(display, show_catfix(current))
	
	show_categories(current, categories)
	
	return table.concat(boxes, "\n") .. "\n" .. table.concat(display, "\n\n") .. table.concat(categories, "")
end

function show_error(text)
	return  mw.getCurrentFrame():expandTemplate{title = "maintenance box", args = {
		"red",
		image = "[[File:Ambox warning pn.svg|50px]]",
		title = "Xeletî di vê kategoriyê de hene.",
		text = text,
		}}
end

-- Check the name of the current page, and return an error if it's not right.
function check_name(current, template, info)
	local errortext = nil
	local category = nil
	
	if not current then
		errortext =
			"Etîketa \"" .. (info.label or "") .. "\" di şablona " ..
			require("Modul:template link").format_link{template} .. " de naxebite. " ..
			"Dibe ku şaş be yan hîn nehatibe çêkirin. Ji bo lêzêdekirina etîketa nû ji kerema xwe binêre belgekirina şablonê."
		category = "[[Kategorî:Kategoriyên bi etîketa şaş]]"
	else
		
	end
	
	if errortext then
		return (category or "") .. show_error(errortext)
	else
		return nil
	end
end

function show_catfix(current)
	if current._lang and not (current._info and current._info.no_catfix) then
		return m_utilities.catfix(current._lang,
			(current._info and current._info.sc
				and require("Modul:scripts").getByCode(current._info.sc) or nil))
	else
		return nil
	end
end

-- Show the parent categories that the current category should be placed in.
function show_categories(current, categories)
	local parents = current:getParents()
	
	if not parents then
		return
	end
	
	for _, parent in ipairs(parents) do
		if type(parent.name) == "string" then
			if not (current._lang and current:getCategoryName() == capitalize(current._lang:getCategoryName())) and not (current._sc and current:getCategoryName():find(capitalize(current._sc:getCategoryName()), nil, true)) and current:getInfo().code then
				require("Modul:debug").track("category tree/string")
			end
			
			table.insert(categories, "[[" .. parent.name .. "|" .. parent.sort .. "]]")
		else
			table.insert(categories, "[[Kategorî:" .. parent.name:getCategoryName() .. "|" .. parent.sort .. "]]")
		end
	end
	
	-- Also put the category in its corresponding "umbrella" or "by language" category.
	local umbrella = current:getUmbrella()
	local naveModule = current:getDataModule()

	if umbrella then
		local sort
		if current._lang then
			sort = current._lang:getCanonicalName()
		elseif naveModule == "Modul:dara kategoriyan/malbatkatbike" then 
			sort = mw.ustring.gsub(current:getCategoryName(), "Zimanên ", "")
		else
			sort = current:getCategoryName()
		end
		
		if type(umbrella) == "string" then
			table.insert(categories, "[[" .. umbrella .. "|" .. sort .. "]]")
		else
			table.insert(categories, "[[Kategorî:" .. umbrella:getCategoryName() .. "|" .. sort .. "]]")
		end
	end
end

function link_box(content)
	return "<div class=\"noprint plainlinks\" style=\"float: right; clear: both; margin: 0 0 .5em 1em; background: #f9f9f9; border: 1px #aaaaaa solid; margin-top: -1px; padding: 5px; font-weight: bold;\">"
		.. content .. "</div>"
end

function show_editlink(current)
	return link_box(
		"[" .. tostring(mw.uri.fullUrl(current:getDataModule(), "action=edit"))
		.. " Daneya kategoriyê biguhêre]")
end

-- Show navigational "breadcrumbs" at the top of the page.
function show_breadcrumbs(current)
	local steps = {}
	
	-- Start at the current label and move our way up the "chain" from child to parent, until we can't go further.
	while current do
		local category = nil
		local display_name = nil
		
		if type(current) == "string" then
			category = current
			display_name = current:gsub("^Kategorî:", "")
		else
			category = "Kategorî:" .. current:getCategoryName()
			display_name = current:getBreadcrumbName()
		end
		
		display_name = capitalize(display_name)
		table.insert(steps, 1, "[[:" .. category .. "|" .. display_name .. "]]")
		
		-- Move up the "chain" by one level.
		if type(current) == "string" then
			current = nil
		else
			current = current:getParents()
		end
		
		if current then
			current = current[1].name
		elseif inFundamental[category] then ---fundamental li ser Wîkîferhengê !Serkategorî ye
			current = "Kategorî:!Serkategorî"
		end	
	end
	
	steps = table.concat(steps, " » ")
	
	return "<small>" .. steps .. "</small>"
end

-- Show a short description text for the category.
function show_description(current)
	return (current:getDescription() or "")
end

-- Show a table of contents with links to each letter in the language's script.
function show_TOC(current)
	local code = current:getInfo().code
	
	if code and not require("Modul:ziman").getByCode(code) then
		return nil
	end
	
	if not code then
		code = "ku"
	end
	
	local etiket = current:getInfo().label
	if etiket == "werger" or etiket == "daxwazên peyvan" then
		code = "ku"
	end
	-- If category can be empty, then it only contains subcategories.
	local hasPages = not current:canBeEmpty()
	
	local titleText = mw.title.getCurrentTitle().text
	
	local inCategory

	if hasPages then
		inCategory = mw.site.stats.pagesInCategory(titleText, "pages")
	else
		inCategory = mw.site.stats.pagesInCategory(titleText, "subcats")
	end
	
	-- No need for a TOC if all pages or subcategories can fit on one page.
	if inCategory > 200 then
		
		-- This category is very large, see if there is an "extended" version of the TOC.
		if inCategory > 1000 then
			local TOC_template_extended = mw.title.new("Şablon:" .. code .. "-KategorîTOC dirêj")
			local TOC_template = mw.title.new("Şablon:".. code .. "-KategorîTOC" )			
			if TOC_template_extended.exists then
				return mw.getCurrentFrame():expandTemplate{title = TOC_template_extended.text, args = {}}
			elseif TOC_template.exists then
				return mw.getCurrentFrame():expandTemplate{title = TOC_template.text, args = {}}
			else 
				return "[[Kategorî:Naverok hewce ye|" .. code .. "]]"
			end
		end
		local TOC_template = mw.title.new("Şablon:".. code .. "-KategorîTOC" )			
		if TOC_template.exists then
			return mw.getCurrentFrame():expandTemplate{title = TOC_template.text, args = {}}
		else 
			return "[[Kategorî:Naverok hewce ye|" .. code .. "]]"

		end
	end
	
	return nil
end

function export.test(frame)
	local template = frame.args[1]
	local submodule = require("Modul:dara kategoriyan/" .. template)
	
	if submodule.new_main then
		current = submodule.new_main(frame)
	else
		local info = {}
		
		for key, val in pairs(frame.args) do
			info[key] = val; if info[key] == "" then info[key] = nil end
		end
	
		info.template = nil
		current = submodule.new(info, true)
	end
end

return export