Moduuli:Cs:Wikidata infobox
Siirry navigaatioon
Siirry hakuun
[ muokkaa ] wikiprojekti:wikidata/cswiki
|
require "Module:No globals"
local Wikidata = require 'Module:cs:Wikidata'
local lib = require 'Module:cs:Wikidata/lib'
local frame = mw.getCurrentFrame()
local args = frame and frame.args or {}
local title = args[1] and mw.text.trim(args[1]) or 'osoba' --TODO: better default box
local submodule = require ('Module:cs:Wikidata infobox/' .. title)
local t = submodule.layout
local requirements = submodule.requirements or {}
local colors = submodule.colors or {}
local parent = frame:getParent()
local params = parent and parent.args or {}
local entity = mw.wikibase.getEntityObject(params.id or nil)
local curr_title = mw.title.getCurrentTitle()
local pagename = curr_title.text
local namespace = curr_title.namespace
local Cats, Interwiki = {}, {}
local property_type = 1
local item_desc = 2
local param_name = 3
local prop_option = 4
local errors = {
["infobox-type-invalid"] = "Neplatný typ hodnoty na řádce %s: %s.",
}
-- TODO: mw.html
local layout_args = {
abovestyle = 'text-align:center; font-size:125%; ' .. (args.abovestyle or ''),
aboveclass = args.aboveclass or '',
bottomstyle = 'font-size:smaller; text-align:center; ' .. (args.bottomstyle or ''),
class = 'infobox ' .. (args.class or ''),
datastyle = args.datastyle or '',
headerstyle = 'text-align:center; ' .. (args.headerstyle or ''),
imagestyle = 'text-align:center; ' .. (args.imagestyle or ''),
labelstyle = 'text-align:left; white-space:nowrap; ' .. (args.labelstyle or ''),
style = 'text-align:left; font-size:88%; line-height:1.5em; width:' .. (args.width or '250px') .. '; ' .. (args.style or ''),
}
-- TODO: mw.html
local layout = { -- infobox table layout
[1] = '<table cellspacing="2" class="' .. layout_args.class .. '" style="' .. layout_args.style .. '">\n',
[2] = ' <tr><th colspan="2" class="' ..layout_args.aboveclass .. '" style="background-color:$1; ' .. layout_args.abovestyle .. '">$2</th></tr>\n', -- label
[4] = ' <tr><td colspan="2" style="' .. layout_args.imagestyle .. '">$1<br>$2</td></tr>\n', -- image
[7] = ' <tr><td colspan="2" align="center"><table border="0" width="100%"><tr>\n',-- begin of small image
[8] = ' <td align="center">$1</td>\n', -- small image
[11] = ' </tr></table></td></tr>\n', -- end of small image
[12] = ' <tr><th style="' .. layout_args.labelstyle .. '">$1</th><td style="' .. layout_args.datastyle .. '">$2\n</td></tr>', -- item
[15] = ' <tr><th style="' .. layout_args.labelstyle .. '">$1</th><td style="' .. layout_args.datastyle .. '">$2\n</td></tr>', -- string
[16] = ' <tr><th style="' .. layout_args.labelstyle .. '">$1</th><td style="' .. layout_args.datastyle .. '">$2\n</td></tr>', -- date
[17] = ' <tr><th style="' .. layout_args.labelstyle .. '">$1</th><td style="' .. layout_args.datastyle .. '">$2\n</td></tr>', -- number
[18] = ' <tr><th style="' .. layout_args.labelstyle .. '">$1</th><td style="' .. layout_args.datastyle .. '">$2\n</td></tr>', -- coord
[19] = ' <tr><td>$1</td><td>$2\n</td></tr>', -- taxa
[20] = ' <tr><td style="' .. layout_args.datastyle .. ' colspan="2">$1\n</td></tr>',
[21] = ' <tr><td style="' .. layout_args.datastyle .. ' colspan="2">[[Soubor:Commons-logo.svg|20px|Logo Wikimedia Commons]] <b>[[c:$1|multimédia]]</b> na [[Wikimedia Commons]]</td></tr>\n', -- link to commons
[22] = ' <tr><td style="' .. layout_args.datastyle .. ' colspan="2">[[Soubor:Wikisource-logo.svg|20px|Logo Wikizdrojů]] <b>[[s:$1|dokumenty]]</b> na [[Wikizdroje|Wikizdrojích]]</td></tr>\n', -- link to wikisource
[23] = ' <tr><td style="' .. layout_args.datastyle .. ' colspan="2">[[Soubor:Wikiquote-logo.svg|20px|Logo Wikicitátů]] <b>[[q:$1|citáty]]</b> na [[Wikicitáty|Wikicitátech]]</td></tr>\n', -- link to wikiquote
[90] = ' <tr><th colspan="2" style="background-color:$1; ' .. layout_args.headerstyle .. '">$2</th></tr>\n', -- group
[99] = ' <tr><td colspan="2" style="' .. layout_args.bottomstyle .. '">Data mohou pocházet z [[d:' .. (entity and entity.id or '') .. '|datové položky]].</td></tr>\n'
}
local function addCat(catname)
table.insert(Cats, '[[Kategorie:' .. catname .. '|' .. pagename .. ']]')
end
local function inMainWithEntityOrWithId()
if entity then
if params.id or namespace == 0 then
return true
end
end
return false
end
local function getOptions(line) -- get options for Wikidata.formatStatementsFromLua from infobox table line
local options = { entity = entity }
for a, b in pairs(t[line][prop_option]) do
options[a] = b
end
return options
end
local function getDesc(line)
local desc = t[line][item_desc]
local link = t[line].link
local text = params[t[line][param_name]] or ''
if t[line].pl then
if text ~= '' then
local IsList = require 'Module:cs:IsList'
if IsList.isList({ args = { text } }) then
desc = t[line].pl
end
elseif namespace == 0 and t[line][prop_option] and entity and entity.claims then
local options = getOptions(line)
local Statements = Wikidata.filterStatementsFromLua(entity, options)
if #Statements > 1 then desc = t[line].pl end
end
end
if link then
if desc ~= '' then
desc = '[[' .. link .. '|' .. desc .. ']]'
else
desc = '[[' .. link .. ']]'
end
end
return desc
end
local function getImageDescription(line, heading)
if t[line].param_desc then
if params[t[line].param_desc] and params[t[line].param_desc] ~= '' then
return params[t[line].param_desc]
end
end
return heading
end
local function makeImage(line, description)
local options
local image_options = {
description = description,
size = (t[line].param_size and params[t[line].param_size]) or (t[line].default_size and params[t[line].default_size]) or '200px'
}
local image_formatter = require 'Module:cs:ImageFormatter'
local image_local = params[t[line][param_name]]
local image_value
if t[line][prop_option] then
options = getOptions(line)
image_value = Wikidata.formatStatementsFromLua(options)
end
local placeholder_image
if submodule.placeholder_images then
placeholder_image = queryPairs(submodule.placeholder_images, entity)
placeholder_image = image_formatter.makeImage(placeholder_image, image_options)
end
if image_local then
local what = options.catbase or ('Vlastnost ' .. options.property:upper())
if image_local == '' or image_local == '-' or image_local == 'ne' then
if image_value and image_value ~= '' and tostring(t[line].over) ~= 'true' then
addCat( 'Údržba:' .. what .. ' dostupný na Wikidatech a chybí v článku' )
end
if image_local == '' and t[line].over and image_value and image_value ~= '' then
return image_formatter.makeImage(image_value, image_options)
end
return nil
else
local i18n = mw.loadData("Module:cs:Wikidata/i18n")
if image_value and image_value ~= '' then
if image_value == image_local then
addCat(mw.ustring.format(i18n.categories.same, what))
else
addCat(mw.ustring.format(i18n.categories.diff, what))
end
else
addCat(mw.ustring.format(i18n.categories["not"], what))
end
return image_formatter.makeImage(image_local, image_options)
end
elseif image_value and image_value ~= '' then
return lib.addWdClass(image_formatter.makeImage(image_value, image_options))
end
return placeholder_image
end
local function makeValue(line, type)
if t[line][prop_option] then
local options = getOptions(line)
if options.site then
return Wikidata.getSitelinkFromLua(options)
end
if params[t[line][param_name]] then
options.value = params[t[line][param_name]]
end
options.addclass = true
if type ~= 'smallimage' then --temp
options.compare = true
options.addlink = true
end
return Wikidata.formatStatementsFromLua(options)
end
return params[t[line][param_name]] or nil
end
local function queryPairs(data, entity)
local default = data.default or nil
for propId, values in pairs(data) do
if entity and entity.claims and entity.claims[propId] then
for Qid, value in pairs(values) do
local Statements = Wikidata.filterStatementsFromLua(entity, { property = propId })
for _, statement in pairs(Statements) do
if lib.getEntityIdFromValue(statement.mainsnak.datavalue.value) == value then
return values[Qid]
end
end
end
end
end
return default
end
local function checkParams()
local AllParams = { id = '' } -- default params
for _, line in pairs(t) do
if line[param_name] and line[param_name] ~= '' then
AllParams[line[param_name]] = '' -- empty value is enough
end
for param in pairs(line) do
if mw.ustring.find(param, '^param_') then
AllParams[line[param]] = ''
end
end
end
for param in pairs(params) do
if not AllParams[param] then
addCat('Údržba:Neznámý parametr v infoboxu ' .. title)
break
end
end
end
local function checkRequirements()
for prop, values in pairs(requirements) do
if entity.claims[prop:upper()] then
for i, id in pairs(values) do
local Statements = Wikidata.filterStatementsFromLua(entity, { property = prop })
for _, statement in pairs(Statements) do
if id == lib.getEntityIdFromValue(statement.mainsnak.datavalue.value) then
break
elseif i == #values then
addCat('Údržba:Chybná vlastnost ' .. prop .. ' na Wikidatech')
end
end
end
else
addCat('Údržba:Chybí vlastnost ' .. prop .. ' na Wikidatech')
end
end
end
local function formatTaxonId(id, entity)
local localised = mw.wikibase.label(id)
local taxon_name = Wikidata.formatStatementsFromLua{ entity = entity, limit = 1, property = 'P225', rank = 'best' }
local itemFormatter = require 'Module:cs:Wikidata/item'
if taxon_name then
if not localised or localised ~= taxon_name then
return itemFormatter.formatEntityId(id, {}) .. " (''" .. taxon_name .. "'')"
end
end
return itemFormatter.formatEntityId(id, {})
end
local function generateTaxaRows(entity, color, rows)
if entity and entity.claims then
local FilteredAbove = Wikidata.filterStatementsFromLua(entity, { property = 'P171', rank = 'best' })
for _, statement in pairs(FilteredAbove) do
local above_id = lib.getEntityIdFromValue(statement.mainsnak.datavalue.value)
local above_entity = mw.wikibase.getEntityObject(above_id)
if above_entity.claims then
local value = formatTaxonId(above_id, above_entity)
local above_rank, description
local color = color
local Ranks = Wikidata.filterStatementsFromLua(above_entity, { property = 'P105', rank = 'best' })
if #Ranks > 0 then
local itemFormatter = require 'Module:cs:Wikidata/item'
for _, statement in pairs(Ranks) do
above_rank = lib.getEntityIdFromValue(statement.mainsnak.datavalue.value)
description = itemFormatter.formatEntityId(above_rank, {}) or ''
if not color or color == colors.default then
color = queryPairs(colors, above_entity)
end
end
else
description = '(nezařazeno)'
end
local row = mw.ustring.gsub(mw.ustring.gsub(layout[19],'$1',lib.addWdClass(description)),'$2',lib.addWdClass(value))
local above_rows, above_color = generateTaxaRows(above_entity, color, row .. rows)
if above_rows then
return above_rows, above_color
else
return nil, nil
end
end
end
end
return rows, color
end
local function generateInterwiki()
local Properties = { 'P361', 'P460' }
if entity and entity.claims then
for _, prop in pairs(Properties) do
if entity.claims[prop] then
local Sitelinks = entity.sitelinks or {}
local Statements = Wikidata.filterStatementsFromLua(entity, { property = prop, rank = 'best' })
if #Statements == 1 then
local id = lib.getEntityIdFromValue(Statements[1].mainsnak.datavalue.value)
local entity = mw.wikibase.getEntityObject(id)
if entity and entity.sitelinks then
for site, sitelink in pairs(entity.sitelinks) do
if mw.ustring.find(site, 'wiki$') then
local code = mw.ustring.gsub(mw.ustring.gsub(site, '^(.+)wiki$', '%1'), '_', '-')
if code ~= 'wikidata' and code ~= 'commons' and code ~= 'mediawiki' and code ~= 'species' and code ~= 'meta' then
if not Sitelinks[site] then
if #Interwiki == 0 then
addCat('Monitoring:Infobox generující interwiki')
end
table.insert(Interwiki, '[[' .. code .. ':' .. sitelink.title .. ']]')
end
end
end
end
break
end
end
end
end
end
end
local function addMainCategory()
if entity.claims.P910 then
local Statements = entity:getBestStatements('P910')
for _, statement in pairs(Statements) do
if lib.IsSnakValue(statement.mainsnak) then
local sitelink = mw.wikibase.sitelink(lib.getEntityIdFromValue(statement.mainsnak.datavalue.value))
if sitelink then
table.insert(Cats, '[[' .. sitelink .. '| ]]')
break
end
end
end
end
end
local p = {}
function p.generateCode()
local table1 = '<pre>{{Infobox - ' .. title .. '\n'
local table2 = '<pre>\n'
for line = 1, #t do
if t[line][param_name] and t[line][param_name] ~= '' then
table1 = table1 .. '| ' .. t[line][param_name] .. ' = \n'
local options = {}
if t[line][prop_option] then
options = getOptions(line)
end
table2 = table2 .. mw.ustring.gsub(options.of or options.property or '','p(%d)','P%1') .. '\n'
end
for param in pairs(t[line]) do
if mw.ustring.find(param, '^param_') then
table1 = table1 .. '| ' .. t[line][param] .. ' = \n'
table2 = table2 .. '\n'
end
end
end
table1 = table1 .. '}}</pre>'
table2 = table2 .. '\n</pre>'
return '<table><tr><td>\n' .. table1 .. '</td>\n<td>\n' .. table2 .. '</td></tr></table>'
end
function p.infobox()
if params.id and not entity then
addCat('Údržba:Entita nebyla nalezena')
return error(lib.formatError('entity-not-found'))
end
if not entity and namespace == 0 then
addCat('Údržba:Článek bez propojení na Wikidatech')
end
local backgroundcolor, taxa_rows
if title == "taxobox" then
taxa_rows, backgroundcolor = generateTaxaRows(entity, nil, '')
taxa_rows = taxa_rows or ''
backgroundcolor = backgroundcolor or colors.default
else
backgroundcolor = queryPairs(colors, entity) or '#f0f0f0'
end
local heading
local label = inMainWithEntityOrWithId() and mw.wikibase.label(entity.id) or nil
if t[1][property_type] == 'begin' and params[t[1][param_name]] and params[t[1][param_name]] ~= '' then
heading = params[t[1][param_name]]
if label and heading ~= label then
addCat('Údržba:Wikidata mají jiný štítek')
end
elseif label then
heading = lib.addWdClass(label)
else
heading = pagename
if inMainWithEntityOrWithId() then
addCat('Údržba:Doplnit štítek na Wikidatech')
end
end
if entity and entity.claims and namespace == 0 then
addMainCategory()
checkRequirements()
end
local result, detail, previousgroup = '', '', ''
local open_image_group = false
for line = 1, #t do -- check all properties
if open_image_group and t[line][property_type] ~= 'smallimage' then
detail = detail .. layout[11]
open_image_group = false
end
if t[line][property_type] == 'begin' then
detail = detail .. layout[1] .. mw.ustring.gsub(mw.ustring.gsub(layout[2],'$1',backgroundcolor),'$2',heading)
-- image
elseif t[line][property_type] == 'image' then
local description = getImageDescription(line, heading)
local value = makeImage(line, description)
if value and value ~= '' then
detail = detail .. mw.ustring.gsub(mw.ustring.gsub(layout[4],'$1',value),'$2',description)
end
-- smallimage
elseif t[line][property_type] == 'smallimage' then
-- temp
local value = makeValue(line, t[line][property_type])
if value and value ~= '' then
if not open_image_group then
detail = detail .. layout[7]
open_image_group = true
end
detail = detail .. mw.ustring.gsub(layout[8],'$1',value)
end
-- item
elseif t[line][property_type] == 'item' then
local value = makeValue(line, t[line][property_type])
local description = getDesc(line)
if value and value ~= '' then
detail = detail .. mw.ustring.gsub(mw.ustring.gsub(layout[12],'$1',description),'$2',value)
end
-- string
elseif t[line][property_type] == 'string' then
local value = makeValue(line, t[line][property_type])
local description = getDesc(line)
if value and value ~= '' then
detail = detail .. mw.ustring.gsub(mw.ustring.gsub(layout[15],'$1',description),'$2',value)
end
-- date
elseif t[line][property_type] == 'date' then
local value = makeValue(line, t[line][property_type])
local description = getDesc(line)
if value and value ~= '' then
detail = detail .. mw.ustring.gsub(mw.ustring.gsub(layout[16],'$1',description),'$2',value)
end
-- number
elseif t[line][property_type] == 'number' then
local value = makeValue(line, t[line][property_type])
local description = getDesc(line)
if value and value ~= '' then
detail = detail .. mw.ustring.gsub(mw.ustring.gsub(layout[17],'$1',description),'$2',value)
end
-- coordinates
elseif t[line][property_type] == 'coord' then
local value = makeValue(line, t[line][property_type])
local description = getDesc(line)
if value and value ~= '' then
detail = detail .. mw.ustring.gsub(mw.ustring.gsub(layout[18],'$1',description),'$2',value)
end
-- taxa
elseif t[line][property_type] == 'taxa' then
detail = detail .. taxa_rows
elseif t[line][property_type] == 'long' then
local value = makeValue(line, t[line][property_type])
if value and value ~= '' then
if t[line].pattern then
value = mw.ustring.gsub(t[line].pattern,'$1',value)
end
detail = detail .. mw.ustring.gsub(layout[20],'$1',value)
end
-- sitelinks TODO
-- elseif t[line][property_type] == 'commons' then
-- detail = detail .. mw.ustring.gsub(layout[21],'$1',value)
-- elseif t[line][property_type] == 'source' then
-- detail = detail .. mw.ustring.gsub(layout[22],'$1',value)
-- elseif t[line][property_type] == 'quote' then
-- detail = detail .. mw.ustring.gsub(layout[23],'$1',value)
-- group
elseif t[line][property_type] == 'group' then
if open_image_group then
detail = detail .. layout[11]
open_image_group = false
end
if detail ~= "" then
result = result .. previousgroup .. detail
detail = ""
end
local description = function(line)
local description = t[line][item_desc]
if description == '' then
if params[t[line][param_name]] then
description = params[t[line][param_name]]
end
end
return description
end
if description(line) ~= '' then
previousgroup = mw.ustring.gsub(mw.ustring.gsub(layout[90],'$1',backgroundcolor),'$2',description(line))
else
previousgroup = ''
end
-- others / error
else
addCat('Údržba:Chyba v modulu Wikidata infobox')
return error(mw.ustring.format(errors["infobox-type-invalid"], line, t[line][property_type]))
end
end
if inMainWithEntityOrWithId() then
result = result .. layout[99]
end
checkParams()
if namespace == 0 then
generateInterwiki()
end
result = result .. '</table>' .. table.concat(Cats) .. table.concat(Interwiki)
return result
end
return p