Модуль:Wikidata: Розніца паміж версіямі

[недагледжаная версія][дагледжаная версія]
Змесціва выдалена Змесціва дададзена
Няма тлумачэння праўкі
Няма тлумачэння праўкі
Радок 1:
local i18n = {
-- vim: set noexpandtab ft=lua ts=4 sw=4:
["errors"] = {
require('Module:No globals')
["property-param-not-provided"] = "Не зададзены параметр уласцівасці",
["entity-not-found"] = "Сутнасць не знойдзена.",
["unknown-claim-type"] = "Невядомы тып заявы.",
["unknown-snak-type"] = "Невядомы тып снэка.",
["unknown-datavalue-type"] = "Невядомы тып значэння даных.",
["unknown-entity-type"] = "Невядомы тып сутнасці.",
["unknown-property-module"] = "Вы павінны ўсталяваць і property-module, і property-function.",
["unknown-claim-module"] = "Вы павінны ўсталяваць і claim-module, і claim-function.",
["unknown-value-module"] = "Вы павінны ўсталяваць і value-module, і value-function.",
["property-module-not-found"] = "Модуль для адлюстравання ўласцівасці не знойдзены",
["property-function-not-found"] = "Функцыя для адлюстравання ўласцівасці не знойдзена",
["claim-module-not-found"] = "Модуль для адлюстравання сцвярджэння не знойдзены.",
["claim-function-not-found"] = "Функцыя для адлюстравання сцвярджэння не знойдзена.",
["value-module-not-found"] = "Модуль для адлюстравання значэння не знойдзены.",
["value-function-not-found"] = "Функцыя для адлюстравання значэння не знойдзена."
},
["somevalue"] = "''невядома''",
["novalue"] = "",
["circa"] = 'каля ',
["presumably"] = '<span style="border-bottom: 1px dotted; cursor: help;" title="меркавана">мерк. </span>',
}
 
-- settings, may differ from project to project
local p = {}
local categoryLinksToEntitiesWithMissingLabel = '[[Катэгорыя:Вікіпедыя:Артыкулы са спасылкамі на элементы Вікідадзеных без подпісу]]';
local debug = false
local categoryLinksToEntitiesWithMissingLocalLanguageLabel = '[[Катэгорыя:Вікіпедыя:Артыкулы са спасылкамі на элементы Вікідадзеных без беларускага подпісу]]';
local categoryLocalValuePresent = '[[Катэгорыя:Вікіпедыя:Артыкулы з пераазначэннем значэння з Вікідадзеных]]';
local fileDefaultSize = '267x400px';
local outputReferences = true;
 
-- sources that shall be omitted if any preffered sources exists
local deprecatedSources = {
Q36578 = true, -- Gemeinsame Normdatei
Q63056 = true, -- Find a Grave
Q15222191 = true, -- BNF
};
local preferredSources = {
Q5375741 = true, -- Encyclop?dia Britannica Online
Q17378135 = true, -- Great Soviet Encyclopedia (1969—1978)
};
 
------------------------------------------------------------------------------
-- module local variables and functions
 
-- Спасылкі на якія выкарыстоўваюцца модулі, якія запатрабуюцца ў 99% выпадкаў загрузкі старонак (каб мець навідавоку пры пераназванні)
local wiki =
local moduleSources = require( 'Module:Sources' )
{
local WDS = require( 'Module:WikidataSelectors' );
langcode = mw.language.getContentLanguage().code
}
 
-- Канстанты
-- internationalisation
local contentLanguageCode = mw.getContentLanguage():getCode();
local i18n =
{
["errors"] =
{
["property-not-found"] = "Property not found.",
["entity-not-found"] = "Wikidata entity not found.",
["unknown-claim-type"] = "Unknown claim type.",
["unknown-entity-type"] = "Unknown entity type.",
["qualifier-not-found"] = "Qualifier not found.",
["site-not-found"] = "Wikimedia project not found.",
["unknown-datetime-format"] = "Unknown datetime format.",
["local-article-not-found"] = "Article is not yet available in this wiki."
},
["datetime"] =
{
-- $1 is a placeholder for the actual number
[0] = "$1 billion years", -- precision: billion years
[1] = "$100 million years", -- precision: hundred million years
[2] = "$10 million years", -- precision: ten million years
[3] = "$1 million years", -- precision: million years
[4] = "$100,000 years", -- precision: hundred thousand years
[5] = "$10,000 years", -- precision: ten thousand years
[6] = "$1 millennium", -- precision: millennium
[7] = "$1 century", -- precision: century
[8] = "$1s", -- precision: decade
-- the following use the format of #time parser function
[9] = "Y", -- precision: year,
[10] = "F Y", -- precision: month
[11] = "F j, Y", -- precision: day
[12] = "F j, Y ga", -- precision: hour
[13] = "F j, Y g:ia", -- precision: minute
[14] = "F j, Y g:i:sa", -- precision: second
["beforenow"] = "$1 BCE", -- how to format negative numbers for precisions 0 to 5
["afternow"] = "$1 CE", -- how to format positive numbers for precisions 0 to 5
["bc"] = '$1 "BCE"', -- how print negative years
["ad"] = "$1", -- how print positive years
-- the following are for function getDateValue() and getQualifierDateValue()
["default-format"] = "dmy", -- default value of the #3 (getDateValue) or
-- #4 (getQualifierDateValue) argument
["default-addon"] = "BC", -- default value of the #4 (getDateValue) or
-- #5 (getQualifierDateValue) argument
["prefix-addon"] = false, -- set to true for languages put "BC" in front of the
-- datetime string; or the addon will be suffixed
["addon-sep"] = " ", -- separator between datetime string and addon (or inverse)
["format"] = -- options of the 3rd argument
{
["mdy"] = "F j, Y",
["my"] = "F Y",
["y"] = "Y",
["dmy"] = "j F Y",
["ymd"] = "Y-m-d",
["ym"] = "Y-m"
}
},
["monolingualtext"] = '<span lang="%language">%text</span>',
["warnDump"] = "[[Category:Called function 'Dump' from module Wikidata]]",
["ordinal"] =
{
[1] = "st",
[2] = "nd",
[3] = "rd",
["default"] = "th"
}
}
 
local p = {}
-- Credit to http://stackoverflow.com/a/1283608/2644759
-- cc-by-sa 3.0
local function tableMerge(t1, t2)
for k,v in pairs(t2) do
if type(v) == "table" then
if type(t1[k] or false) == "table" then
tableMerge(t1[k] or {}, t2[k] or {})
else
t1[k] = v
end
else
t1[k] = v
end
end
return t1
end
 
local formatDatavalue, formatEntityId, formatRefs, formatSnak, formatStatement,
local function loadI18n()
formatStatementDefault, formatProperty, getSourcingCircumstances,
local exist, res = pcall(require, "Module:Wikidata/i18n")
getPropertyDatatype, getPropertyParams, throwError, toBoolean;
if exist and next(res) ~= nil then
tableMerge(i18n, res.i18n)
end
end
 
local function copyTo( obj, target )
loadI18n()
for k, v in pairs( obj ) do
 
target[k] = v
-- this function needs to be internationalised along with the above:
-- takes cardinal numer as a numeric and returns the ordinal as a string
-- we need three exceptions in English for 1st, 2nd, 3rd, 21st, .. 31st, etc.
local function makeOrdinal (cardinal)
local ordsuffix = i18n.ordinal.default
if cardinal % 10 == 1 then
ordsuffix = i18n.ordinal[1]
elseif cardinal % 10 == 2 then
ordsuffix = i18n.ordinal[2]
elseif cardinal % 10 == 3 then
ordsuffix = i18n.ordinal[3]
end
return target;
-- In English, 1, 21, 31, etc. use 'st', but 11, 111, etc. use 'th'
-- similarly for 12 and 13, etc.
if (cardinal % 100 == 11) or (cardinal % 100 == 12) or (cardinal % 100 == 13) then
ordsuffix = i18n.ordinal.default
end
return tostring(cardinal) .. ordsuffix
end
 
local function printErrorsplitISO8601(codestr)
if 'table' == type(str) then
return '<span class="error">' .. (i18n.errors[code] or code) .. '</span>'
if str.args and str.args[1] then
end
str = '' .. str.args[1]
 
local function parseDateValue(timestamp, date_format, date_addon)
local prefix_addon = i18n["datetime"]["prefix-addon"]
local addon_sep = i18n["datetime"]["addon-sep"]
local addon = ""
 
-- check for negative date
if string.sub(timestamp, 1, 1) == '-' then
timestamp = '+' .. string.sub(timestamp, 2)
addon = date_addon
end
local function d(f)
local year_suffix
local tstr = ""
local lang_obj = mw.language.new(wiki.langcode)
local f_parts = mw.text.split(f, 'Y', true)
for idx, f_part in pairs(f_parts) do
year_suffix = ''
if string.match(f_part, "x[mijkot]$") then
-- for non-Gregorian year
f_part = f_part .. 'Y'
elseif idx < #f_parts then
-- supress leading zeros in year
year_suffix = lang_obj:formatDate('Y', timestamp)
year_suffix = string.gsub(year_suffix, '^0+', '', 1)
end
tstr = tstr .. lang_obj:formatDate(f_part, timestamp) .. year_suffix
end
if addon ~= "" and prefix_addon then
return addon .. addon_sep .. tstr
elseif addon ~= "" then
return tstr .. addon_sep .. addon
else
return 'unknown argument type: ' .. type( str ) .. ': ' .. table.tostring( str )
return tstr
end
end
local Y, M, D = (function(str)
local _date_format = i18n["datetime"]["format"][date_format]
local pattern = "(%-?%d+)%-(%d+)%-(%d+)T"
if _date_format ~= nil then
local Y, M, D = mw.ustring.match( str, pattern )
return d(_date_format)
return tonumber(Y), tonumber(M), tonumber(D)
else
end) (str);
return printError("unknown-datetime-format")
local h, m, s = (function(str)
end
local pattern = "T(%d+):(%d+):(%d+)%Z";
local H, M, S = mw.ustring.match( str, pattern);
return tonumber(H), tonumber(M), tonumber(S);
end) (str);
local oh,om = ( function(str)
if str:sub(-1)=="Z" then return 0,0 end; -- ends with Z, Zulu time
-- matches ±hh:mm, ±hhmm or ±hh; else returns nils
local pattern = "([-+])(%d%d):?(%d?%d?)$";
local sign, oh, om = mw.ustring.match( str, pattern);
sign, oh, om = sign or "+", oh or "00", om or "00";
return tonumber(sign .. oh), tonumber(sign .. om);
end )(str)
return {year=Y, month=M, day=D, hour=(h+oh), min=(m+om), sec=s};
end
 
local function parseTimeBoundaries( time, precision )
-- This local function combines the year/month/day/BC/BCE handling of parseDateValue{}
local s = splitISO8601( time );
-- with the millennium/century/decade handling of formatDate()
if (not s) then return nil; end
local function parseDateFull(timestamp, precision, date_format, date_addon)
local prefix_addon = i18n["datetime"]["prefix-addon"]
local addon_sep = i18n["datetime"]["addon-sep"]
local addon = ""
 
if ( precision >= 0 and precision <= 8 ) then
-- check for negative date
local powers = { 1000000000 , 100000000, 10000000, 1000000, 100000, 10000, 1000, 100, 10 }
if string.sub(timestamp, 1, 1) == '-' then
local power = powers[ precision + 1 ];
timestamp = '+' .. string.sub(timestamp, 2)
local left = s.year - ( s.year % power );
addon = date_addon
return { tonumber(os.time( {year=left, month=1, day=1, hour=0, min=0, sec=0} )) * 1000,
tonumber(os.time( {year=left + power - 1, month=12, day=31, hour=29, min=59, sec=58} )) * 1000 + 1999 };
end
 
if ( precision == 9 ) then
-- get the next four characters after the + (should be the year now in all cases)
return { tonumber(os.time( {year=s.year, month=1, day=1, hour=0, min=0, sec=0} )) * 1000,
-- ok, so this is dirty, but let's get it working first
tonumber(os.time( {year=s.year, month=12, day=31, hour=23, min=59, sec=58} )) * 1000 + 1999 };
local intyear = tonumber(string.sub(timestamp, 2, 5))
if intyear == 0 and precision <= 9 then
return ""
end
 
if ( precision == 10 ) then
-- precision is 10000 years or more
local lastDays = {31, 28.25, 31, 30, 31, 30, 31, 31, 30, 31, 30, 31};
if precision <= 5 then
local factorlastDay = 10 ^ ((5 - precision) + 4)lastDays[s.month];
return { tonumber(os.time( {year=s.year, month=s.month, day=1, hour=0, min=0, sec=0} )) * 1000,
local y2 = math.ceil(math.abs(intyear) / factor)
tonumber(os.time( {year=s.year, month=s.month, day=lastDay, hour=23, min=59, sec=58} )) * 1000 + 1999 };
local relative = mw.ustring.gsub(i18n.datetime[precision], "$1", tostring(y2))
if addon ~= "" then
-- negative date
relative = mw.ustring.gsub(i18n.datetime.beforenow, "$1", relative)
else
relative = mw.ustring.gsub(i18n.datetime.afternow, "$1", relative)
end
return relative
end
 
--if ( precision is== decades11 (8), centuries (7) and millennia (6)then
return { tonumber(os.time( {year=s.year, month=s.month, day=s.day, hour=0, min=0, sec=0} )) * 1000,
local era, card
tonumber(os.time( {year=s.year, month=s.month, day=s.day, hour=23, min=59, sec=58} )) * 1000 + 1999 };
if precision == 6 then
card = math.floor((intyear - 1) / 1000) + 1
era = mw.ustring.gsub(i18n.datetime[6], "$1", makeOrdinal(card))
end
 
if precision == 7 then
if ( precision == 12 ) then
card = math.floor((intyear - 1) / 100) + 1
return { tonumber(os.time( {year=s.year, month=s.month, day=s.day, hour=s.hour, min=0, sec=0} )) * 1000,
era = mw.ustring.gsub(i18n.datetime[7], "$1", makeOrdinal(card))
tonumber(os.time( {year=s.year, month=s.month, day=s.day, hour=s.hour, min=59, sec=58} )) * 1000 + 19991999 };
end
 
if precision == 8 then
if ( precision == 13 ) then
era = mw.ustring.gsub(i18n.datetime[8], "$1", tostring(math.floor(math.abs(intyear) / 10) * 10))
return { tonumber(os.time( {year=s.year, month=s.month, day=s.day, hour=s.hour, min=s.min, sec=0} )) * 1000,
tonumber(os.time( {year=s.year, month=s.month, day=s.day, hour=s.hour, min=s.min, sec=58} )) * 1000 + 1999 };
end
 
if era then
if addon( precision ~== 14 "") then
local t = tonumber(os.time( {year=s.year, month=s.month, day=s.day, hour=s.hour, min=s.min, sec=0} ) );
era = mw.ustring.gsub(mw.ustring.gsub(i18n.datetime.bc, '"', ""), "$1", era)
return { t * 1000, t * 1000 + 999 };
else
era = mw.ustring.gsub(mw.ustring.gsub(i18n.datetime.ad, '"', ""), "$1", era)
end
return era
end
 
error('Unsupported precision: ' .. precision );
local _date_format = i18n["datetime"]["format"][date_format]
end
if _date_format ~= nil then
 
-- check for precision is year and override supplied date_format
--[[
if precision == 9 then
Пераўтворыць радок у булева значэнне
_date_format = i18n["datetime"][9]
end
local year_suffix
local tstr = ""
local lang_obj = mw.language.new(wiki.langcode)
local f_parts = mw.text.split(_date_format, 'Y', true)
for idx, f_part in pairs(f_parts) do
year_suffix = ''
if string.match(f_part, "x[mijkot]$") then
-- for non-Gregorian year
f_part = f_part .. 'Y'
elseif idx < #f_parts then
-- supress leading zeros in year
year_suffix = lang_obj:formatDate('Y', timestamp)
year_suffix = string.gsub(year_suffix, '^0+', '', 1)
end
tstr = tstr .. lang_obj:formatDate(f_part, timestamp) .. year_suffix
end
local fdate
if addon ~= "" and prefix_addon then
fdate = addon .. addon_sep .. tstr
elseif addon ~= "" then
fdate = tstr .. addon_sep .. addon
else
fdate = tstr
end
 
Прымае: радковае значэнне (можа адсутнічаць)
return fdate
Вяртае: булева значэнне true ці false, калі атрымліваецца распазнаць значэнне, ці defaultValue ва ўсіх астатніх выпадках
else
]]
return printError("unknown-datetime-format")
local function toBoolean( valueToParse, defaultValue )
end
if ( valueToParse ~= nil ) then
if valueToParse == false or valueToParse == '' or valueToParse == 'false' or valueToParse == '0' then
return false
end
return true
end
return defaultValue;
end
 
--[[
-- the "qualifiers" and "snaks" field have a respective "qualifiers-order" and "snaks-order" field
Функцыя для атрымання сутнасці (еntity) для бягучай старонкі
-- use these as the second parameter and this function instead of the built-in "pairs" function
Падрабязней пра сутнасці гл. d:Wikidata:Glossary/ru
-- to iterate over all qualifiers and snaks in the intended order.
local function orderedpairs(array, order)
if not order then return pairs(array) end
 
Прымае: радковы ідэнтыфікатар (тыпу P18, Q42)
-- return iterator function
Вяртае: аб'ект табліцу, элементы якой індэксуюцца з нуля
local i = 0
]]
return function()
local function getEntityFromId( id )
i = i + 1
if order[i]id then
return mw.wikibase.getEntityObject( id )
return order[i], array[order[i]]
end
return mw.wikibase.getEntityObject();
end
end
 
--[[
-- precision: 0 - billion years, 1 - hundred million years, ..., 6 - millennia, 7 - century, 8 - decade, 9 - year, 10 - month, 11 - day, 12 - hour, 13 - minute, 14 - second
Внутрення функцыя для фарміравання паведамлення пра памылку
local function normalizeDate(date)
date = mw.text.trim(date, "+")
Прымае: ключ элемента ў табліцы i18n (напрыклад entity-not-found)
-- extract year
Вяртае: радок паведамлення
local yearstr = mw.ustring.match(date, "^\-?%d+")
]]
local year = tonumber(yearstr)
local function throwError( key )
-- remove leading zeros of year
error( i18n.errors[key] );
return year .. mw.ustring.sub(date, #yearstr + 1), year
end
 
--[[
local function formatDate(date, precision, timezone)
Функцыя для атрымання ідэнтыфікатара сутнасцяў
precision = precision or 11
local date, year = normalizeDate(date)
if year == 0 and precision <= 9 then return "" end
 
Прымае: аб'ект табліцу сутнасці
-- precision is 10000 years or more
Вяртае: радковы ідэнтыфікатар (тыпу P18, Q42)
if precision <= 5 then
]]
local factor = 10 ^ ((5 - precision) + 4)
local function getEntityIdFromValue( value )
local y2 = math.ceil(math.abs(year) / factor)
local prefix = ''
local relative = mw.ustring.gsub(i18n.datetime[precision], "$1", tostring(y2))
if yearvalue['entity-type'] <== 0'item' then
prefix = 'Q'
relative = mw.ustring.gsub(i18n.datetime.beforenow, "$1", relative)
elseif value['entity-type'] == 'property' then
else
prefix = 'P'
relative = mw.ustring.gsub(i18n.datetime.afternow, "$1", relative)
else
end
throwError( 'unknown-entity-type' )
return relative
end
return prefix .. value['numeric-id']
end
 
-- праверка на наяўнасць специилизированной функцыі ў опцыях
-- precision is decades, centuries and millennia
local function getUserFunction( options, prefix, defaultFunction )
local era
-- праверка на ўказанне спецыялізаваных апрацоўнікаў у параметрах,
if precision == 6 then era = mw.ustring.gsub(i18n.datetime[6], "$1", tostring(math.floor((math.abs(year) - 1) / 1000) + 1)) end
-- перададзеных пры выкліку
if precision == 7 then era = mw.ustring.gsub(i18n.datetime[7], "$1", tostring(math.floor((math.abs(year) - 1) / 100) + 1)) end
if options[ prefix .. '-module' ] or options[ prefix .. '-function' ] then
if precision == 8 then era = mw.ustring.gsub(i18n.datetime[8], "$1", tostring(math.floor(math.abs(year) / 10) * 10)) end
-- праверка на пустыя радкі ў параметрах ці іх адсутнасць
if era then
if not options[ prefix .. '-module' ] or not options[ prefix .. '-function' ] then
if year < 0 then era = mw.ustring.gsub(mw.ustring.gsub(i18n.datetime.bc, '"', ""), "$1", era)
throwError( 'unknown-' .. prefix .. '-module' );
elseif year > 0 then era = mw.ustring.gsub(mw.ustring.gsub(i18n.datetime.ad, '"', ""), "$1", era) end
end
return era
-- дынамічная загруза модуля з апрацоўнікам паказаным у параметры
end
local formatter = require ('Module:' .. options[ prefix .. '-module' ]);
if formatter == nil then
throwError( prefix .. '-module-not-found' )
end
local fun = formatter[ options[ prefix .. '-function' ] ]
if fun == nil then
throwError( prefix .. '-function-not-found' )
end
return fun;
end
 
return defaultFunction;
-- precision is year
end
if precision == 9 then
return year
end
 
-- Выбірае ўласцівасці па property id, дадаткова фільтруючы іх па рангу
-- precision is less than years
local function selectClaims( context, options, propertySelector )
if precision > 9 then
if ( not context ) then error( 'context not specified' ); end;
--[[ the following code replaces the UTC suffix with the given negated timezone to convert the global time to the given local time
if ( not options ) then error( 'options not specified' ); end;
timezone = tonumber(timezone)
if ( not options.entity ) then error( 'options.entity is missing' ); end;
if timezone and timezone ~= 0 then
if ( not propertySelector ) then error( 'propertySelector not specified' ); end;
timezone = -timezone
timezone = string.format("%.2d%.2d", timezone / 60, timezone % 60)
if timezone[1] ~= '-' then timezone = "+" .. timezone end
date = mw.text.trim(date, "Z") .. " " .. timezone
end
]]--
 
result = WDS.filter( options.entity.claims, propertySelector );
local formatstr = i18n.datetime[precision]
 
if year == 0 then formatstr = mw.ustring.gsub(formatstr, i18n.datetime[9], "")
if ( not result or #result == 0 ) then
elseif year < 0 then
return nil;
-- Mediawiki formatDate doesn't support negative years
end
date = mw.ustring.sub(date, 2)
 
formatstr = mw.ustring.gsub(formatstr, i18n.datetime[9], mw.ustring.gsub(i18n.datetime.bc, "$1", i18n.datetime[9]))
elseif if yearoptions.limit >and 0options.limit ~= '' and i18noptions.datetime.adlimit ~= "$1"'-' then
local limit = tonumber( options.limit, 10 );
formatstr = mw.ustring.gsub(formatstr, i18n.datetime[9], mw.ustring.gsub(i18n.datetime.ad, "$1", i18n.datetime[9]))
while #result > limit do
table.remove( result );
end
return mw.language.new(wiki.langcode):formatDate(formatstr, date)
end
 
return result;
end
 
--[[
local function printDatavalueEntity(data, parameter)
Функцыя для атрымання значэння ўласцівасці элемента ў зададзены момант часу.
-- data fields: entity-type [string], numeric-id [int, Wikidata id]
local id
 
Прымае: кантэкст, элемент, часавыя межы, табліца ID уласцівасці
if data["entity-type"] == "item" then id = "Q" .. data["numeric-id"]
Вяртае: табліцу адпаведных значэнняў уласцівасці
elseif data["entity-type"] == "property" then id = "P" .. data["numeric-id"]
]]
else return printError("unknown-entity-type")
local function getPropertyInBoundaries( context, entity, boundaries, propertyIds )
local results = {};
 
if not propertyIds or #propertyIds == 0 then
return results;
end
 
if parameterentity.claims then
for _, propertyId in ipairs( propertyIds ) do
if parameter == "link" then
local filteredClaims = WDS.filter( entity.claims, propertyId .. '[rank:preferred, rank:normal]' );
local linkTarget = mw.wikibase.sitelink(id)
if filteredClaims then
local linkName = mw.wikibase.label(id)
for _, claim in pairs( filteredClaims ) do
if linkTarget then
if not boundaries or not propertyIds or #propertyIds == 0 then
-- if there is a local Wikipedia article link to it using the label or the article title
table.insert( results, claim.mainsnak );
return "[[" .. linkTarget .. "|" .. (linkName or linkTarget) .. "]]"
else
local startBoundaries = getTimeBoundariesFromQualifiers( context, claim, 'P580' );
-- if there is no local Wikipedia article output the label or link to the Wikidata object to let the user input a proper label
local endBoundaries = getTimeBoundariesFromQualifiers( context, claim, 'P582' );
if linkName then return linkName else return "[[:d:" .. id .. "|" .. id .. "]]" end
if ( (startBoundaries == nil or ( startBoundaries[2] <= boundaries[1]))
and (endBoundaries == nil or ( endBoundaries[1] >= boundaries[2]))) then
table.insert( results, claim.mainsnak );
end
end
end
end
 
if #results > 0 then
break;
end
else
return data[parameter]
end
else
return mw.wikibase.label(id) or id
end
end
 
return results;
local function printDatavalueTime(data, parameter)
-- data fields: time [ISO 8601 time], timezone [int in minutes], before [int], after [int], precision [int], calendarmodel [wikidata URI]
-- precision: 0 - billion years, 1 - hundred million years, ..., 6 - millennia, 7 - century, 8 - decade, 9 - year, 10 - month, 11 - day, 12 - hour, 13 - minute, 14 - second
-- calendarmodel: e.g. http://www.wikidata.org/entity/Q1985727 for the proleptic Gregorian calendar or http://www.wikidata.org/wiki/Q11184 for the Julian calendar]
if parameter then
if parameter == "calendarmodel" then data.calendarmodel = mw.ustring.match(data.calendarmodel, "Q%d+") -- extract entity id from the calendar model URI
elseif parameter == "time" then data.time = normalizeDate(data.time) end
return data[parameter]
else
return formatDate(data.time, data.precision, data.timezone)
end
end
 
--[[
local function printDatavalueMonolingualText(data, parameter)
Функцыя для атрымання меткі элемента ў зададзены момант часу.
-- data fields: language [string], text [string]
 
if parameter then
Прымае: кантэкст, элемент, часавыя межы
return data[parameter]
Вяртае: тэкставую метку элемента, мова меткі
else
]]
local result = mw.ustring.gsub(mw.ustring.gsub(i18n.monolingualtext, "%%language", data["language"]), "%%text", data["text"])
function getLabelWithLang( context, options, entity, boundaries, propertyIds )
return result
if not entity then
return nil;
end
end
 
local lang = mw.language.getContentLanguage();
local function findClaims(entity, property)
local langCode = lang:getCode();
if not property or not entity or not entity.claims then return end
 
-- name from label
if mw.ustring.match(property, "^P%d+$") then
local label = nil;
-- if the property is given by an id (P..) access the claim list by this id
if ( options.text and options.text ~= '' ) then
return entity.claims[property]
label = options.text;
else
else
-- otherwise, iterate over all properties, fetch their labels and compare this to the given property name
label, langCode = entity:getLabelWithLang();
for k, v in pairs(entity.claims) do
if mw.wikibase.label(k) == property then return v end
if not langCode then
return nil;
end
if not propertyIds then
propertyIds = {
'P1813[language:' .. langCode .. ']',
'P1448[language:' .. langCode .. ']',
'P1705[language:' .. langCode .. ']'
};
end
-- name from properties
local results = getPropertyInBoundaries( context, entity, boundaries, propertyIds );
for _, result in pairs( results ) do
if result.datavalue and result.datavalue.value then
if result.datavalue.type == 'monolingualtext' and result.datavalue.value.text then
label = result.datavalue.value.text;
lang = result.datavalue.value.language;
break;
elseif result.datavalue.type == 'string' then
label = result.datavalue.value;
break;
end
end
end
return
end
end
 
return label, langCode;
local function getSnakValue(snak, parameter)
if snak.snaktype == "value" then
-- call the respective snak parser
if snak.datavalue.type == "string" then return snak.datavalue.value
elseif snak.datavalue.type == "globecoordinate" then return printDatavalueCoordinate(snak.datavalue.value, parameter)
elseif snak.datavalue.type == "quantity" then return printDatavalueQuantity(snak.datavalue.value, parameter)
elseif snak.datavalue.type == "time" then return printDatavalueTime(snak.datavalue.value, parameter)
elseif snak.datavalue.type == "wikibase-entityid" then return printDatavalueEntity(snak.datavalue.value, parameter)
elseif snak.datavalue.type == "monolingualtext" then return printDatavalueMonolingualText(snak.datavalue.value, parameter)
end
end
return mw.wikibase.renderSnak(snak)
end
 
--[[
local function getQualifierSnak(claim, qualifierId)
Функцыя для афармлення сцвярджэнняў (statement)
-- a "snak" is Wikidata terminology for a typed key/value pair
Падрабязней пра сцвярджэнні гл. d:Wikidata:Glossary/ru
-- a claim consists of a main snak holding the main information of this claim,
 
-- as well as a list of attribute snaks and a list of references snaks
Прымае: табліцу параметраў
if qualifierId then
Вяртае: радок аформленага тэксту, прызначанага для адлюстравання ў артыкуле
-- search the attribute snak with the given qualifier as key
]]
if claim.qualifiers then
local function formatProperty( options )
local qualifier = claim.qualifiers[qualifierId]
-- Атрыманне сутнасці па ідэнтыфікатары
if qualifier then return qualifier[1] end
local entity = getEntityFromId( options.entityId )
end
if not entity then
return nil, printError("qualifier-not-found")
return -- throwError( 'entity-not-found' )
else
end
-- otherwise return the main snak
-- праверка на прысутнасць у сутнасці заяў (claim)
return claim.mainsnak
-- падрабязней пра заявы гл. d:Вікідадзеныя:Гласарый
if (entity.claims == nil) then
return '' --TODO error?
end
 
-- improve options
options.frame = g_frame;
options.entity = entity;
options.extends = function( self, newOptions )
return copyTo( newOptions, copyTo( self, {} ) )
end
end
 
if ( options.i18n ) then
local function getValueOfClaim(claim, qualifierId, parameter)
options.i18n = copyTo( options.i18n, copyTo( i18n, {} ) );
local error
local snak
snak, error = getQualifierSnak(claim, qualifierId)
if snak then
return getSnakValue(snak, parameter)
else
options.i18n = i18n;
return nil, error
end
end
 
-- create context
local function getReferences(frame, claim)
local resultcontext = ""{
entity = options.entity,
-- traverse through all references
formatSnak = formatSnak,
for ref in pairs(claim.references or {}) do
formatPropertyDefault = formatPropertyDefault,
local refparts
formatStatementDefault = formatStatementDefault }
-- traverse through all parts of the current reference
context.cloneOptions = function( options )
for snakkey, snakval in orderedpairs(claim.references[ref].snaks or {}, claim.references[ref]["snaks-order"]) do
local entity = options.entity;
if refparts then refparts = refparts .. ", " else refparts = "" end
options.entity = nil;
-- output the label of the property of the reference part, e.g. "imported from" for P143
 
refparts = refparts .. tostring(mw.wikibase.label(snakkey)) .. ": "
newOptions = mw.clone( options );
-- output all values of this reference part, e.g. "German Wikipedia" and "English Wikipedia" if the referenced claim was imported from both sites
options.entity = entity;
for snakidx = 1, #snakval do
newOptions.entity = entity;
if snakidx > 1 then refparts = refparts .. ", " end
 
refparts = refparts .. getSnakValue(snakval[snakidx])
return newOptions;
end;
context.formatProperty = function( options )
local func = getUserFunction( options, 'property', context.formatPropertyDefault );
return func( context, options )
end;
context.formatStatement = function( options, statement ) return formatStatement( context, options, statement ) end;
context.formatSnak = function( options, snak, circumstances ) return formatSnak( context, options, snak, circumstances ) end;
context.formatRefs = function( options, statement ) return formatRefs( context, options, statement ) end;
context.parseTimeFromSnak = function( snak )
if ( snak and snak.datavalue and snak.datavalue.value and snak.datavalue.value.time ) then
return tonumber(os.time( splitISO8601( tostring( snak.datavalue.value.time ) ) ) ) * 1000;
end
return nil;
end
context.parseTimeBoundariesFromSnak = function( snak )
if refparts then result = result .. frame:extensionTag("ref", refparts) end
if ( snak and snak.datavalue and snak.datavalue.value and snak.datavalue.value.time and snak.datavalue.value.precision ) then
end
return parseTimeBoundaries( snak.datavalue.value.time, snak.datavalue.value.precision );
return result
end
return nil;
end
context.getSourcingCircumstances = function( statement ) return getSourcingCircumstances( statement ) end;
context.selectClaims = function( options, propertyId ) return selectClaims( context, options, propertyId ) end;
 
return context.formatProperty( options );
end
 
function formatPropertyDefault( context, options )
if ( not context ) then error( 'context not specified' ); end;
if ( not options ) then error( 'options not specified' ); end;
if ( not options.entity ) then error( 'options.entity missing' ); end;
 
local claims;
------------------------------------------------------------------------------
if options.property then -- TODO: Чаму тут можа не быць property?
-- module global functions
claims = context.selectClaims( options, options.property );
end
if claims == nil then
return '' --TODO error?
end
 
-- Абыход усіх заяў сцвярджэння і з накапленнем оформленых пераважных
if debug then
-- заяў у табліцы
function p.inspectI18n(frame)
local valformattedClaims = i18n{}
 
for _, key in pairs(frame.args) do
for i, claim in ipairs(claims) do
key = mw.text.trim(key)
local formattedStatement = context.formatStatement( options, claim )
val = val[key]
-- тут можа вярнуцца або аформлены тэкст заявы
-- або радок памылкі nil здаецца ніколі не вяртаецца
if (formattedStatement) then
formattedStatement = '<span class="wikidata-claim" data-wikidata-property-id="' .. string.upper( options.property ) .. '" data-wikidata-claim-id="' .. claim.id .. '">' .. formattedStatement .. '</span>'
table.insert( formattedClaims, formattedStatement )
end
end
 
-- стварэнне тэкставага радка са спісам оформленых заяў з табліцы
local out = mw.text.listToText( formattedClaims, options.separator, options.conjunction )
if out ~= '' then
if options.before then
out = options.before .. out
end
if options.after then
out = out .. options.after
end
return val
end
end
 
return out
function p.descriptionIn(frame)
local langcode = frame.args[1]
local id = frame.args[2] -- "id" must be nil, as access to other Wikidata objects is disabled in Mediawiki configuration
-- return description of a Wikidata entity in the given language or the default language of this Wikipedia site
return mw.wikibase.getEntityObject(id).descriptions[langcode or wiki.langcode].value
end
 
--[[
function p.labelIn(frame)
Функцыя для афармлення аднаго сцвярджэння (statement)
local langcode = frame.args[1]
local id = frame.args[2] -- "id" must be nil, as access to other Wikidata objects is disabled in Mediawiki configuration
-- return label of a Wikidata entity in the given language or the default language of this Wikipedia site
return mw.wikibase.getEntityObject(id).labels[langcode or wiki.langcode].value
end
 
Прымае: аб'ект-табліцу сцвярджэнне і табліцу параметраў
-- This is used to get a value, or a comma separated list of them if multiple values exist
Вяртае: радок аформленага тэксту з заявай (claim)
p.getValue = function(frame)
]]
local propertyID = mw.text.trim(frame.args[1] or "")
function formatStatement( context, options, statement )
local input_parm = mw.text.trim(frame.args[2] or "")
if ( not statement ) then
local delimdefault = ", " -- **internationalise later**
error( 'statement is not specified or nil' );
local delim = frame.args.delimiter or ""
delim = string.gsub(delim, '"', '')
if #delim == 0 then
delim = delimdefault
end
if not statement.type or statement.type ~= 'statement' then
local qid = frame.args.qid
throwError( 'unknown-claim-type' )
if qid and (#qid == 0) then qid = nil end
end
if input_parm == "FETCH_WIKIDATA" then
local entity = mw.wikibase.getEntityObject(qid)
local claims
if entity and entity.claims then
claims = entity.claims[propertyID]
end
if claims then
-- if wiki-linked value output as link if possible
if (claims[1] and claims[1].mainsnak.snaktype == "value" and claims[1].mainsnak.datavalue.type == "wikibase-entityid") then
local out = {}
for k, v in pairs(claims) do
local sitelink = mw.wikibase.sitelink("Q" .. v.mainsnak.datavalue.value["numeric-id"])
local label = mw.wikibase.label("Q" .. v.mainsnak.datavalue.value["numeric-id"])
if label == nil then label = "Q" .. v.mainsnak.datavalue.value["numeric-id"] end
 
local functionToCall = getUserFunction( options, 'claim', context.formatStatementDefault );
if sitelink then
return functionToCall( context, options, statement );
out[#out + 1] = "[[" .. sitelink .. "|" .. label .. "]]"
else
out[#out + 1] = "[[:d:Q" .. v.mainsnak.datavalue.value["numeric-id"] .. "|" .. label .. "]]<abbr title='" .. i18n["errors"]["local-article-not-found"] .. "'>[*]</abbr>"
end
end
return table.concat(out, delim)
else
-- just return best values
return entity:formatPropertyValues(propertyID).value
end
else
return ""
end
else
return input_parm
end
end
 
function getSourcingCircumstances( statement )
-- Same as above, but uses the short name property for label if available.
if (not statement) then error('statement is not specified') end;
p.getValueShortName = function(frame)
local propertyID = mw.text.trim(frame.args[1] or "")
local input_parm = mw.text.trim(frame.args[2] or "")
if input_parm == "FETCH_WIKIDATA" then
local entity = mw.wikibase.getEntityObject()
local claims
if entity and entity.claims then
claims = entity.claims[propertyID]
end
if claims then
-- if wiki-linked value output as link if possible
if (claims[1] and claims[1].mainsnak.snaktype == "value" and claims[1].mainsnak.datavalue.type == "wikibase-entityid") then
local out = {}
for k, v in pairs(claims) do
local sitelink = mw.wikibase.sitelink("Q" .. v.mainsnak.datavalue.value["numeric-id"])
local label
local claimEntity = mw.wikibase.getEntity("Q" .. v.mainsnak.datavalue.value["numeric-id"])
if claimEntity ~= nil then
if claimEntity.claims.P1813 then
for k2, v2 in pairs(claimEntity.claims.P1813) do
if v2.mainsnak.datavalue.value.language == "en" then
label = v2.mainsnak.datavalue.value.text
end
end
end
end
if label == nil or label == "" then label = mw.wikibase.label("Q" .. v.mainsnak.datavalue.value["numeric-id"]) end
if label == nil then label = "Q" .. v.mainsnak.datavalue.value["numeric-id"] end
 
local circumstances = {};
if sitelink then
if ( statement.qualifiers
out[#out + 1] = "[[" .. sitelink .. "|" .. label .. "]]"
and statement.qualifiers.P1480 ) then
else
for i, qualifier in pairs( statement.qualifiers.P1480 ) do
out[#out + 1] = "[[:d:Q" .. v.mainsnak.datavalue.value["numeric-id"] .. "|" .. label .. "]]<abbr title='" .. i18n["errors"]["local-article-not-found"] .. "'>[*]</abbr>"
if ( qualifier
end
and qualifier.datavalue
and qualifier.datavalue.type == 'wikibase-entityid'
and qualifier.datavalue.value
and qualifier.datavalue.value["entity-type"] == 'item' ) then
local circumstance = 'Q' .. qualifier.datavalue.value["numeric-id"];
if ( 'Q5727902' == circumstance ) then
circumstances.circa = true;
end
if ( 'Q18122778' == circumstance ) then
circumstances.presumably = true;
end
return table.concat(out, ", ")
else
-- just return best vakues
return entity:formatPropertyValues(propertyID).value
end
else
return ""
end
else
return input_parm
end
return circumstances;
end
 
--[[
-- This is used to get a value, or a comma separated list of them if multiple values exist
Функцыя для афармлення аднаго сцвярджэння (statement)
-- from an arbitrary entry by using its QID.
-- Use : {{#invoke:Wikidata|getValueFromID|<ID>|<Property>|FETCH_WIKIDATA}}
-- E.g.: {{#invoke:Wikidata|getValueFromID|Q151973|P26|FETCH_WIKIDATA}} - to fetch value of 'spouse' (P26) from 'Richard Burton' (Q151973)
-- Please use sparingly - this is an *expensive call*.
p.getValueFromID = function(frame)
local itemID = mw.text.trim(frame.args[1] or "")
local propertyID = mw.text.trim(frame.args[2] or "")
local input_parm = mw.text.trim(frame.args[3] or "")
if input_parm == "FETCH_WIKIDATA" then
local entity = mw.wikibase.getEntity(itemID)
local claims
if entity and entity.claims then
claims = entity.claims[propertyID]
end
if claims then
-- if wiki-linked value output as link if possible
if (claims[1] and claims[1].mainsnak.snaktype == "value" and claims[1].mainsnak.datavalue.type == "wikibase-entityid") then
local out = {}
for k, v in pairs(claims) do
local sitelink = mw.wikibase.sitelink("Q" .. v.mainsnak.datavalue.value["numeric-id"])
local label = mw.wikibase.label("Q" .. v.mainsnak.datavalue.value["numeric-id"])
if label == nil then label = "Q" .. v.mainsnak.datavalue.value["numeric-id"] end
 
Прымае: аб'ект-табліцу сцвярджэнне, табліцу параметраў,
if sitelink then
аб'ект-функцыю афармлення ўнутраных структур сцвярджэння (snak) і
out[#out + 1] = "[[" .. sitelink .. "|" .. label .. "]]"
аб'ект-функцыю афармлення спасылкі на крыніцы (reference)
else
Вяртае: радок аформленага тэксту з заявай (claim)
out[#out + 1] = "[[:d:Q" .. v.mainsnak.datavalue.value["numeric-id"] .. "|" .. label .. "]]<abbr title='" .. i18n["errors"]["local-article-not-found"] .. "'>[*]</abbr>"
]]
end
function formatStatementDefault( context, options, statement )
end
if (not context) then error('context is not specified') end;
return table.concat(out, ", ")
if (not options) then error('options is not specified') end;
else
if (not statement) then error('statement is not specified') end;
return entity:formatPropertyValues(propertyID).value
 
end
local circumstances = context.getSourcingCircumstances( statement );
else
 
return ""
if statement.qualifiers then
end
options.qualifiers = statement.qualifiers;
else
return input_parm
end
 
if ( options.references ) then
return context.formatSnak( options, statement.mainsnak, circumstances ) .. context.formatRefs( options, statement );
else
return context.formatSnak( options, statement.mainsnak, circumstances );
end
end
 
--[[
p.getQualifierValue = function(frame)
Функцыя для афармлення часткі сцвярджэнні (snak)
local propertyID = mw.text.trim(frame.args[1] or "")
Падрабязней о snak гл. d:Вікідадзеныя:Гласарый
local qualifierID = mw.text.trim(frame.args[2] or "")
 
local input_parm = mw.text.trim(frame.args[3] or "")
Прымае: табліцу snak аб'екта (main snak ці ж snak ад кваліфікатара) і табліцу опцый
if input_parm == "FETCH_WIKIDATA" then
Вяртае: радок аформленага вікітэксту
local entity = mw.wikibase.getEntityObject()
]]
if entity.claims[propertyID] ~= nil then
function formatSnak( context, options, snak, circumstances )
local out = {}
circumstances = circumstances or {};
for k, v in pairs(entity.claims[propertyID]) do
local hash = '';
for k2, v2 in pairs(v.qualifiers[qualifierID]) do
local mainSnakClass = '';
if v2.snaktype == 'value' then
if ( snak.hash ) then
if (mw.wikibase.sitelink("Q" .. v2.datavalue.value["numeric-id"])) then
hash = ' data-wikidata-hash="' .. snak.hash .. '"';
out[#out + 1] = "[[" .. mw.wikibase.sitelink("Q" .. v2.datavalue.value["numeric-id"]) .. "]]"
else
out[#out + 1] = "[[:d:Q" .. v2.datavalue.value["numeric-id"] .. "|" .. mw.wikibase.label("Q" .. v2.datavalue.value["numeric-id"]) .. "]]<abbr title='" .. i18n["errors"]["local-article-not-found"] .. "'>[*]</abbr>"
end
end
end
end
return table.concat(out, ", ")
else
return ""
end
else
mainSnakClass = ' wikidata-main-snak';
return input_parm
end
end
 
local before = '<span class="wikidata-snak ' .. mainSnakClass .. '"' .. hash .. '>'
-- This is used to get a value like 'male' (for property p21) which won't be linked and numbers without the thousand separators
local after = '</span>'
p.getRawValue = function(frame)
local propertyID = mw.text.trim(frame.args[1] or "")
local input_parm = mw.text.trim(frame.args[2] or "")
local qid = frame.args.qid
if qid and (#qid == 0) then qid = nil end
if input_parm == "FETCH_WIKIDATA" then
local entity = mw.wikibase.getEntityObject(qid)
local claims
if entity and entity.claims then claims = entity.claims[propertyID] end
if claims then
local result = entity:formatPropertyValues(propertyID, mw.wikibase.entity.claimRanks).value
 
if snak.snaktype == 'somevalue' then
-- if number type: remove thousand separators, bounds and units
if ( options['somevalue'] and options['somevalue'] ~= '' ) then
if (claims[1] and claims[1].mainsnak.snaktype == "value" and claims[1].mainsnak.datavalue.type == "quantity") then
return before .. options['somevalue'] .. after;
result = mw.ustring.gsub(result, "(%d),(%d)", "%1%2")
end
result = mw.ustring.gsub(result, "(%d)±.*", "%1")
return before .. options.i18n['somevalue'] .. after;
end
elseif snak.snaktype == 'novalue' then
return result
if ( options['novalue'] and options['novalue'] ~= '' ) then
else
return before .. options['novalue'] .. after;
return ""
end
return before .. options.i18n['novalue'] .. after;
elseif snak.snaktype == 'value' then
if ( circumstances.presumably ) then
before = before .. options.i18n.presumably;
end
if ( circumstances.circa ) then
else
before = before .. options.i18n.circa;
return input_parm
end
 
return before .. formatDatavalue( context, options, snak.datavalue, snak.datatype ) .. after;
else
throwError( 'unknown-snak-type' );
end
end
 
--[[
-- This is used to get the unit name for the numeric value returned by getRawValue
Функцыя для афармлення аб'ектаў-значэнняў з геаграфічнымі каардынатамі
p.getUnits = function(frame)
 
local propertyID = mw.text.trim(frame.args[1] or "")
Прымае: аб'ект-значэнне і табліцу параметраў,
local input_parm = mw.text.trim(frame.args[2] or "")
Вяртае: радок аформленага тэксту
local qid = frame.args.qid
]]
if qid and (#qid == 0) then qid = nil end
function formatGlobeCoordinate( value, options )
if input_parm == "FETCH_WIKIDATA" then
-- праверка на патрабаванне ў параметрах выкліку на зварот сырога значэння
local entity = mw.wikibase.getEntityObject(qid)
if options['subvalue'] == 'latitude' then -- шыроты
local claims
return value['latitude']
if entity and entity.claims then claims = entity.claims[propertyID] end
elseif options['subvalue'] == 'longitude' then -- даўготы
if claims then
return value['longitude']
local result = entity:formatPropertyValues(propertyID, mw.wikibase.entity.claimRanks).value
elseif options['nocoord'] and options['nocoord'] ~= '' then
if (claims[1] and claims[1].mainsnak.snaktype == "value" and claims[1].mainsnak.datavalue.type == "quantity") then
-- калі перададзены параметр nocoord, тое не выводзіць каардынаты
result = mw.ustring.sub(result, mw.ustring.find(result, " ")+1, -1)
-- звычайна гэта робіцца пры выкарыстанні некалькіх картак на старонцы
end
return result''
else
-- у адваротным выпадку фарміруюцца параметры для выкліку шаблону {{coord}}
return ""
-- трэба дапісаць у дакументацыі шаблону, што ён адгэтуль выклікаецца, і што
end
-- любое изменние яго парамеров павінна быць узгоднена з кодам тут
else
local eps = 0.0000001 -- < 1/360000
return input_parm
local globe = options.globe or '' -- TODO
end
local lat = {}
lat['abs'] = math.abs(value['latitude'])
lat['ns'] = value['latitude'] >= 0 and 'N' or 'S'
lat['d'] = math.floor(lat['abs'] + eps)
lat['m'] = math.floor((lat['abs'] - lat['d']) * 60 + eps)
lat['s'] = math.max(0, ((lat['abs'] - lat['d']) * 60 - lat['m']) * 60 + eps)
local lon = {}
lon['abs'] = math.abs(value['longitude'])
lon['ew'] = value['longitude'] >= 0 and 'E' or 'W'
lon['d'] = math.floor(lon['abs'] + eps)
lon['m'] = math.floor((lon['abs'] - lon['d']) * 60 + eps)
lon['s'] = math.max(0, ((lon['abs'] - lon['d']) * 60 - lon['m']) * 60 + eps)
-- TODO: round seconds with precision
local coord = '{{coord'
if (value['precision'] == nil) or (value['precision'] < 1/60) then -- па змоўчанні з дакладнасцю да секунды
coord = coord .. '|' .. lat['d'] .. '|' .. lat['m'] .. '|' .. lat['s'] .. '|' .. lat['ns']
coord = coord .. '|' .. lon['d'] .. '|' .. lon['m'] .. '|' .. lon['s'] .. '|' .. lon['ew']
elseif value['precision'] < 1 then
coord = coord .. '|' .. lat['d'] .. '|' .. lat['m'] .. '|' .. lat['ns']
coord = coord .. '|' .. lon['d'] .. '|' .. lon['m'] .. '|' .. lon['ew']
else
coord = coord .. '|' .. lat['d'] .. '|' .. lat['ns']
coord = coord .. '|' .. lon['d'] .. '|' .. lon['ew']
end
coord = coord .. '|globe:' .. globe
if options['type'] and options['type'] ~= '' then
coord = coord .. '|type=' .. options.type
end
if options['display'] and options['display'] ~= '' then
coord = coord .. '|display=' .. options.display
else
coord = coord .. '|display=title'
end
coord = coord .. '}}'
 
return g_frame:preprocess(coord)
end
end
 
--[[
-- This is used to get the unit's QID to use with the numeric value returned by getRawValue
Функцыя для афармлення аб'ектаў-значэнняў з выявамі з Вікісховішча
p.getUnitID = function(frame)
 
local propertyID = mw.text.trim(frame.args[1] or "")
Прымае: аб'ект-значэнне і табліцу параметраў,
local input_parm = mw.text.trim(frame.args[2] or "")
Вяртае: радок аформленага тэксту
if input_parm == "FETCH_WIKIDATA" then
]]
local entity = mw.wikibase.getEntityObject()
function formatCommonsMedia( value, options )
local claims
local image = '[[File:' .. value
if entity and entity.claims then claims = entity.claims[propertyID] end
if options['border'] and options['border'] ~= '' then
if claims then
image = image .. '|border'
local result
end
if (claims[1] and claims[1].mainsnak.snaktype == "value" and claims[1].mainsnak.datavalue.type == "quantity") then
 
-- get the url for the unit entry on Wikidata:
local size = options['size']
result = claims[1].mainsnak.datavalue.value.unit
if size and size ~= '' then
-- and just reurn the last bit from "Q" to the end (which is the QID):
if not string.match( size, 'px$' )
result = mw.ustring.sub(result, mw.ustring.find(result, "Q"), -1)
and not string.match( size, 'пкс$' ) -- TODO: выкарыстоўваць пераклад для мовы вікі
end
then
return result
size = size .. 'px'
else
end
return ""
end
else
size = fileDefaultSize;
return input_parm
end
image = image .. '|' .. size
 
if options['alt'] and options['alt'] ~= '' then
image = image .. '|' .. options['alt']
end
image = image .. ']]'
if options['caption'] and options['caption'] ~= '' then
image = image .. '<br>' .. options['caption']
elseif options['description'] and options['description'] ~= '' then
image = image .. '<br>' .. options['description']
end
return image
end
 
--[[
p.getRawQualifierValue = function(frame)
Функцыя для афармлення знешніх ідэнтыфікатараў
local propertyID = mw.text.trim(frame.args[1] or "")
 
local qualifierID = mw.text.trim(frame.args[2] or "")
Прымае: аб'ект-значэнне і табліцу параметраў,
local input_parm = mw.text.trim(frame.args[3] or "")
Вяртае: радок аформленага тэксту
if input_parm == "FETCH_WIKIDATA" then
]]
local entity = mw.wikibase.getEntityObject()
local function formatExternalId( value, options )
if entity.claims[propertyID] ~= nil then
local outformatter = {}options.formatter
for k, v in pairs(entity.claims[propertyID]) do
if not formatter or formatter == '' then
for k2, v2 in pairs(v.qualifiers[qualifierID]) do
local entity = mw.wikibase.getEntity( options.property:upper() )
if v2.snaktype == 'value' then
if v2.datavalue.value["numeric-id"]entity then
local statements = entity:getBestStatements( 'P1630' )
out[#out + 1] = mw.wikibase.label("Q" .. v2.datavalue.value["numeric-id"])
for _, statement in pairs( statements ) do
else
if statement.mainsnak.snaktype == 'value' then
out[#out + 1] = v2.datavalue.value
formatter = statement.mainsnak.datavalue.value
end
endbreak
end
end
local ret = table.concat(out, ", ")
return string.upper(string.sub(ret, 1, 1)) .. string.sub(ret, 2)
else
return ""
end
else
return input_parm
end
end
 
if formatter and formatter ~= '' then
-- This is used to get a date value for date_of_birth (P569), etc. which won't be linked
local link = mw.ustring.gsub( formatter, '$1', value )
-- Dates and times are stored in ISO 8601 format (sort of).
 
-- At present the local formatDate(date, precision, timezone) function doesn't handle timezone
local title = options.title
-- So I'll just supply "Z" in the call to formatDate below:
if not title or title == '' then
p.getDateValue = function(frame)
title = '$1'
local propertyID = mw.text.trim(frame.args[1] or "")
local input_parm = mw.text.trim(frame.args[2] or "")
local date_format = mw.text.trim(frame.args[3] or i18n["datetime"]["default-format"])
local date_addon = mw.text.trim(frame.args[4] or i18n["datetime"]["default-addon"])
if input_parm == "FETCH_WIKIDATA" then
local entity = mw.wikibase.getEntityObject()
if entity.claims[propertyID] ~= nil then
local out = {}
for k, v in pairs(entity.claims[propertyID]) do
if v.mainsnak.datavalue.type == 'time' then
local timestamp = v.mainsnak.datavalue.value.time
local dateprecision = v.mainsnak.datavalue.value.precision
-- A year can be stored like this: "+1872-00-00T00:00:00Z",
-- which is processed here as if it were the day before "+1872-01-01T00:00:00Z",
-- and that's the last day of 1871, so the year is wrong.
-- So fix the month 0, day 0 timestamp to become 1 January instead:
timestamp = timestamp:gsub("%-00%-00T", "-01-01T")
out[#out + 1] = parseDateFull(timestamp, dateprecision, date_format, date_addon)
end
end
return table.concat(out, ", ")
else
return ""
end
title = mw.ustring.gsub( title, '$1', value )
else
 
return input_parm
return '[' .. link .. ' ' .. title .. ']'
end
 
return value
end
 
--[[
p.getQualifierDateValue = function(frame)
Функцыя для афармлення лікавых значэнняў
local propertyID = mw.text.trim(frame.args[1] or "")
 
local qualifierID = mw.text.trim(frame.args[2] or "")
Прымае: аб'ект-значэнне і табліцу параметраў,
local input_parm = mw.text.trim(frame.args[3] or "")
Вяртае: радок аформленага тэксту
local date_format = mw.text.trim(frame.args[4] or i18n["datetime"]["default-format"])
]]
local date_addon = mw.text.trim(frame.args[5] or i18n["datetime"]["default-addon"])
local function formatQuantity( value, options )
if input_parm == "FETCH_WIKIDATA" then
-- дыяпазон значэнняў
local entity = mw.wikibase.getEntityObject()
local amount = string.gsub( value['amount'], '^%+', '' );
if entity.claims[propertyID] ~= nil then
local lang = mw.language.getContentLanguage();
local out = {}
local langCode = lang:getCode();
for k, v in pairs(entity.claims[propertyID]) do
for k2, v2 in pairs(v.qualifiers[qualifierID]) do
local function formatNum( number )
if v2.snaktype == 'value' then
-- акругленне да 13 знакаў пасля коскі, на 14-м узнікае памылка ў дакладнасці
local timestamp = v2.datavalue.value.time
local mult = 10^13
out[#out + 1] = parseDateValue(timestamp, date_format, date_addon)
number = math.floor( number * mult + 0.5 ) / mult
end
 
end
return lang:formatNum( number )
end
return table.concat(out, ", ")
else
return ""
end
else
return input_parm
end
end
local out = formatNum( tonumber( amount ) );
if value.upperBound then
local diff = tonumber( value.upperBound ) - tonumber( amount )
if diff > 0 then -- часавая провека, пакуль у большасці значэнняў не будзе прыбрана ±0
out = out .. '±' .. formatNum( diff )
end
end
 
if options.unit and options.unit ~= '' then
-- This is used to fetch all of the images with a particular property, e.g. image (P18), Gene Atlas Image (P692), etc.
if options.unit ~= '-' then
-- Parameters are | propertyID | value / FETCH_WIKIDATA / nil | separator (default=space) | size (default=frameless)
out = out .. ' ' .. options.unit
-- It will return a standard wiki-markup [[File:Filename | size]] for each image with a selectable size and separator (which may be html)
end
-- e.g. {{#invoke:Wikidata|getImages|P18|FETCH_WIKIDATA}}
elseif value.unit and string.match( value.unit, 'http://www.wikidata.org/entity/' ) then
-- e.g. {{#invoke:Wikidata|getImages|P18|FETCH_WIKIDATA|<br>|250px}}
local unitEntityId = string.gsub( value.unit, 'http://www.wikidata.org/entity/', '' );
-- If a property is chosen that is not of type "commonsMedia", it will return empty text.
local unitEntity = mw.wikibase.getEntity( unitEntityId );
p.getImages = function(frame)
if unitEntity then
local propertyID = mw.text.trim(frame.args[1] or "")
local writingSystemElementId = 'Q8209';
local input_parm = mw.text.trim(frame.args[2] or "")
local langElementId = 'Q7737';
local sep = mw.text.trim(frame.args[3] or " ")
local label = getLabelWithLang( context, options, unitEntity, nil, {
local imgsize = mw.text.trim(frame.args[4] or "frameless")
'P558[P282:' .. writingSystemElementId .. ', P407:' .. langElementId .. ']',
if input_parm == "FETCH_WIKIDATA" then
'P558[!P282][!P407]'
local entity = mw.wikibase.getEntityObject()
local } claims);
if entity and entity.claims then
out = out .. ' ' .. label;
claims = entity.claims[propertyID]
end
end
if claims then
 
if (claims[1] and claims[1].mainsnak.datatype == "commonsMedia") then
return out;
local out = {}
for k, v in pairs(claims) do
local filename = v.mainsnak.datavalue.value
out[#out + 1] = "[[File:" .. filename .. "|" .. imgsize .. "]]"
end
return table.concat(out, sep)
else
return ""
end
else
return ""
end
else
return input_parm
end
end
 
--[[
-- This is used to get the TA98 (Terminologia Anatomica first edition 1998) values like 'A01.1.00.005' (property P1323)
Get property datatype by ID.
-- which are then linked to http://www.unifr.ch/ifaa/Public/EntryPage/TA98%20Tree/Entity%20TA98%20EN/01.1.00.005%20Entity%20TA98%20EN.htm
-- uses the newer mw.wikibase calls instead of directly using the snaks
@param string Property ID, e.g. 'P123'.
-- formatPropertyValues returns a table with the P1323 values concatenated with ", " so we have to split them out into a table in order to construct the return string
@return string Property datatype, e.g. 'commonsMedia', 'time' or 'url'.
p.getTAValue = function(frame)
]]
local ent = mw.wikibase.getEntityObject()
local function getPropertyDatatype( propertyId )
local props = ent:formatPropertyValues('P1323')
if not propertyId or not string.match( propertyId, '^P%d+$' ) then
local out = {}
return nil;
local t = {}
for k, v in pairs(props) do
if k == 'value' then
t = mw.text.split( v, ", ")
for k2, v2 in pairs(t) do
out[#out + 1] = "[http://www.unifr.ch/ifaa/Public/EntryPage/TA98%20Tree/Entity%20TA98%20EN/" .. string.sub(v2, 2) .. "%20Entity%20TA98%20EN.htm " .. v2 .. "]"
end
end
end
local ret = table.concat(out, "<br> ")
local propertyEntity = mw.wikibase.getEntity( propertyId );
if #ret == 0 then
if not propertyEntity then
ret = "Invalid TA"
return nil;
end
 
return ret
return propertyEntity.datatype;
end
 
local function getDefaultValueFunction( datavalue, datatype )
--[[
-- выклік апрацоўнікаў па змоўчанні для вядомых тыпаў значэнняў
This is used to return an image legend from Wikidata
if datavalue.type == 'wikibase-entityid' then
image is property P18
-- Entity ID
image legend is property P2096
return function( context, options, value ) return formatEntityId( context, options, getEntityIdFromValue( value ) ) end;
elseif datavalue.type == 'string' then
-- String
if datatype and datatype == 'commonsMedia' then
-- Media
return function( context, options, value )
if ( not options.caption or options.caption == '' )
and ( not options.description or options.description == '' )
and options.qualifiers and options.qualifiers.P2096 then
for i, qualifier in pairs( options.qualifiers.P2096 ) do
if ( qualifier
and qualifier.datavalue
and qualifier.datavalue.type == 'monolingualtext'
and qualifier.datavalue.value
and qualifier.datavalue.value.language == contentLanguageCode ) then
options.caption = qualifier.datavalue.value.text
options.description = qualifier.datavalue.value.text
break
end
end
end
return formatCommonsMedia( value, options )
end;
elseif datatype and datatype == 'external-id' then
-- External ID
return function( context, options, value )
return formatExternalId( value, options )
end
elseif datatype and datatype == 'url' then
-- URL
return function( context, options, value )
local moduleUrl = require( 'Module:URL' )
if not options.length or options.length == '' then
options.length = 25
end
return moduleUrl.formatUrlSingle( context, options, value );
end
end
return function( context, options, value ) return value end;
elseif datavalue.type == 'monolingualtext' then
-- монамоўны тэкст (радок з указаннем мовы)
return function( context, options, value )
if ( options.monolingualLangTemplate == 'lang' ) then
return options.frame:expandTemplate{ title = 'lang-' .. value.language, args = { value.text } };
elseif ( options.monolingualLangTemplate == 'ref' ) then
return '<span class="lang" lang="' .. value.language .. '">' .. value.text .. '</span>' .. options.frame:expandTemplate{ title = 'ref-' .. value.language };
else
return '<span class="lang" lang="' .. value.language .. '">' .. value.text .. '</span>';
end
end;
elseif datavalue.type == 'globecoordinate' then
-- геаграфічныя каардынаты
return function( context, options, value ) return formatGlobeCoordinate( value, options ) end;
elseif datavalue.type == 'quantity' then
return function( context, options, value ) return formatQuantity( value, options ) end;
elseif datavalue.type == 'time' then
return function( context, options, value )
local moduleDate = require( 'Module:Wikidata/date' )
return moduleDate.formatDate( context, options, value );
end;
else
-- ва ўсіх стальных выпадках вяртаем памылку
throwError( 'unknown-datavalue-type' )
end
end
 
--[[
Call as {{#invoke:Wikidata |getImageLegend | <PARAMETER> | lang=<ISO-639code> |id=<QID>}}
Функцыя для афармлення значэнняў (value)
Returns PARAMETER, unless it is equal to "FETCH_WIKIDATA", from Item QID (expensive call)
Падрабязней пра значэнні гл. d:Wikidata:Glossary/ru
If QID is omitted or blank, the current article is used (not an expensive call)
If lang is omitted, it uses the local wiki language, otherwise it uses the provided ISO-639 language code
ISO-639: https://docs.oracle.com/cd/E13214_01/wli/docs92/xref/xqisocodes.html#wp1252447
 
Прымае: аб'ект-значэнне і табліцу параметраў,
Ranks are: 'preferred' > 'normal'
Вяртае: радок аформленага тэксту
This returns the label from the first image with 'preferred' rank
Or the label from the first image with 'normal' rank if preferred returns nothing
Ranks: https://www.mediawiki.org/wiki/Extension:Wikibase_Client/Lua
]]
function formatDatavalue( context, options, datavalue, datatype )
if ( not context ) then error( 'context not specified' ); end;
if ( not options ) then error( 'options not specified' ); end;
if ( not datavalue ) then error( 'datavalue not specified' ); end;
if ( not datavalue.value ) then error( 'datavalue.value is missng' ); end;
 
-- праверка на ўказанне спецыялізаваных апрацоўнікаў у параметрах,
p.getImageLegend = function(frame)
-- перададзеных пры выкліку
-- look for named parameter id; if it's blank make it nil
context.formatValueDefault = getDefaultValueFunction( datavalue, datatype );
local id = frame.args.id
local functionToCall = getUserFunction( options, 'value', context.formatValueDefault );
if id and (#id == 0) then
return functionToCall( context, options, datavalue.value );
id = nil
end
 
--[[
-- look for named parameter lang
Функцыя для афармлення ідэнтыфікатара сутнасці
-- it should contain a two-character ISO-639 language code
-- if it's blank fetch the language of the local wiki
local lang = frame.args.lang
if (not lang) or (#lang < 2) then
lang = mw.language.getContentLanguage().code
end
 
Прымае: радок ідэнтыфікатара (тыпу Q42) і табліцу параметраў,
-- first unnamed parameter is the local parameter, if supplied
Вяртае: радок аформленага тэксту
local input_parm = mw.text.trim(frame.args[1] or "")
]]
if input_parm == "FETCH_WIKIDATA" then
function formatEntityId( context, options, entityId )
local ent = mw.wikibase.getEntityObject(id)
-- атрыманне лакалізаванай назвы
local imgs
local entity = mw.wikibase.getEntity( entityId )
if ent and ent.claims then
local label, labelLanguageCode = getLabelWithLang( context, options, entity )
imgs = ent.claims.P18
end
-- вызначэнне адпаведнай паказванаму элементу катэгорыі
local imglbl
local category = ''
if imgs then
if ( options['category'] ) then
-- look for an image with 'preferred' rank
local claims = WDS.filter( entity.claims, options['category'] );
for k1, v1 in pairs(imgs) do
if ( claims ) then
if v1.rank == "preferred" and v1.qualifiers and v1.qualifiers.P2096 then
for _, claim in pairs( claims ) do
local imglbls = v1.qualifiers.P2096
if ( claim.mainsnak
for k2, v2 in pairs(imglbls) do
and claim.mainsnak
if v2.datavalue.value.language == lang then
imglbland = v2claim.mainsnak.datavalue.value.text
and claim.mainsnak.datavalue.type == "wikibase-entityid" ) then
break
local catEntityId = 'Q' .. claim.mainsnak.datavalue.value["numeric-id"];
end
local catEntity = mw.wikibase.getEntity( catEntityId );
end
if ( catEntity and catEntity:getSitelink() ) then
end
category = '[[' .. catEntity:getSitelink() .. ']]';
end
-- if we don't find one, look for an image with 'normal' rank
if (not imglbl) then
for k1, v1 in pairs(imgs) do
if v1.rank == "normal" and v1.qualifiers and v1.qualifiers.P2096 then
local imglbls = v1.qualifiers.P2096
for k2, v2 in pairs(imglbls) do
if v2.datavalue.value.language == lang then
imglbl = v2.datavalue.value.text
break
end
end
end
end
end
end
return imglbl
else
return input_parm
end
end
 
-- атрыманне спасылкі па ідэнтыфікатары
-- This is used to get the QIDs of all of the values of a property, as a comma separated list if multiple values exist
local link = mw.wikibase.sitelink( entityId )
-- Usage: {{#invoke:Wikidata |getPropertyIDs |<PropertyID> |FETCH_WIKIDATA}}
if link then
-- Usage: {{#invoke:Wikidata |getPropertyIDs |<PropertyID> |<InputParameter> |qid=<QID>}}
if label then
if ( contentLanguageCode ~= labelLanguageCode ) then
return '[[' .. link .. '|' .. label .. ']]' .. categoryLinksToEntitiesWithMissingLocalLanguageLabel .. category;
else
return '[[' .. link .. '|' .. label .. ']]' .. category;
end
else
return '[[' .. link .. ']]' .. category;
end
end
 
if label then
-- чырвоная спасылка
-- TODO: разабрацца, чаму не заўсёды ёсць options.frame
if not mw.title.new( label ).exists and options.frame then
return '[[' .. label .. ']]<sup>[[:d:' .. entityId .. '|[d]]]</sup>' .. category;
end
 
-- TODO: перанесці да праверкі на існаванне артыкула
p.getPropertyIDs = function(frame)
local sup = '';
local propertyID = mw.text.trim(frame.args[1] or "")
if ( not options.format or options.format ~= 'text' )
local input_parm = mw.text.trim(frame.args[2] or "")
and entityId ~= 'Q6581072' and entityId ~= 'Q6581097' -- TODO: перапісаць на format=text
-- can take a named parameter |qid which is the Wikidata ID for the article. This will not normally be used.
then
local qid = frame.args.qid
sup = '<sup class="plainlinks noprint">[//www.wikidata.org/wiki/' .. entityId .. '?uselang=' .. contentLanguageCode .. ' [d&#x5d;]</sup>'
if qid and (#qid == 0) then qid = nil end
if input_parm == "FETCH_WIKIDATA" then
local entity = mw.wikibase.getEntityObject(qid)
local propclaims
if entity and entity.claims then
propclaims = entity.claims[propertyID]
end
 
if propclaims then
-- аднайменны артыкул ужо існуе - выводзіцца тэкст і спасылка на ВД
-- if wiki-linked value collect the QID in a table
return '<span class="iw" data-title="' .. label .. '">' .. label
if (propclaims[1] and propclaims[1].mainsnak.snaktype == "value" and propclaims[1].mainsnak.datavalue.type == "wikibase-entityid") then
.. sup
local out = {}
.. '</span>' .. category
for k, v in pairs(propclaims) do
end
out[#out + 1] = "Q" .. v.mainsnak.datavalue.value["numeric-id"]
-- паведамленне пра отсутвии лакалізаванай назвы
end
-- not good, but better than nothing
return table.concat(out, ", ")
return '[[:d:' .. entityId .. '|' .. entityId .. ']]<span style="border-bottom: 1px dotted; cursor: help; white-space: nowrap" title="У Вікідадзеных няма беларускага подпісу да элемента. Вы можаце дапамагчы, паказаўшы рускі варыянт подпісу.">?</span>' .. categoryLinksToEntitiesWithMissingLabel .. category;
else
-- not a wikibase-entityid, so return empty
return ""
end
else
-- no claim, so return empty
return ""
end
else
return input_parm
end
end
 
--[[
-- returns the page id (Q...) of the current page or nothing of the page is not connected to Wikidata
Функцыя для афармлення сцвярджэнняў (statement)
function p.pageId(frame)
Падрабязней пра сцвярджэнні гл. d:Wikidata:Glossary/ru
local entity = mw.wikibase.getEntityObject()
 
if not entity then return nil else return entity.id end
Прымае: табліцу параметраў
Вяртае: радок аформленага тэксту, прызначанага для адлюстравання ў артыкуле
]]
-- састарэлае імя, не выкарыстоўваць
function p.formatStatements( frame )
return p.formatProperty( frame );
end
 
--[[
function p.claim(frame)
Атрыманне параметраў, якія звычайна выкарыстоўваюцца для высновы ўласцівасці.
local property = frame.args[1] or ""
]]
local id = frame.args["id"] -- "id" must be nil, as access to other Wikidata objects is disabled in Mediawiki configuration
function getPropertyParams( propertyId, datatype, params )
local qualifierId = frame.args["qualifier"]
local config = require( 'Module:Wikidata/config' );
local parameter = frame.args["parameter"]
if not config then
local list = frame.args["list"]
return {};
local references = frame.args["references"]
end
local showerrors = frame.args["showerrors"]
local default = frame.args["default"]
if default then showerrors = nil end
 
-- Розныя ўзроўні настройкі параметраў, па змяншэнні прыярытэту
-- get wikidata entity
local propertyParams = {};
local entity = mw.wikibase.getEntityObject(id)
 
if not entity then
-- 1. Параметры, паказаныя відавочна пры выкліку
if showerrors then return printError("entity-not-found") else return default end
if params then
local tplParams = mw.clone( params );
for key, value in pairs( tplParams ) do
if value ~= '' then
propertyParams[key] = value;
end
end
end
 
-- fetch the first claim of satisfying the given property
-- 2. Настройкі пэўнага параметру
local claims = findClaims(entity, property)
if config['properties'] and config['properties'][propertyId] then
if not claims or not claims[1] then
local selfParams = mw.clone( config['properties'][propertyId] );
if showerrors then return printError("property-not-found") else return default end
for key, value in pairs( selfParams ) do
if propertyParams[key] == nil then
propertyParams[key] = value;
end
end
end
 
-- 3. Паказаны прасэт настроек
-- get initial sort indices
if propertyParams['preset'] and config['presets']
local sortindices = {}
and config['presets'][propertyParams['preset']] then
for idx in pairs(claims) do
local presetParams = mw.clone( config['presets'][propertyParams['preset']] );
sortindices[#sortindices + 1] = idx
for key, value in pairs( presetParams ) do
end
if propertyParams[key] == nil then
-- sort by claim rank
propertyParams[key] = value;
local comparator = function(a, b)
end
local rankmap = { deprecated = 2, normal = 1, preferred = 0 }
end
local ranka = rankmap[claims[a].rank or "normal"] .. string.format("%08d", a)
local rankb = rankmap[claims[b].rank or "normal"] .. string.format("%08d", b)
return ranka < rankb
end
table.sort(sortindices, comparator)
 
-- 4. Настройкі для тыпу даных
local result
if datatype and config['datatypes'] and config['datatypes'][datatype] then
local error
local datatypeParams = mw.clone( config['datatypes'][datatype] );
if list then
for key, value in pairs( datatypeParams ) do
local value
if propertyParams[key] == nil then
-- iterate over all elements and return their value (if existing)
propertyParams[key] = value;
result = {}
end
for idx in pairs(claims) do
local claim = claims[sortindices[idx]]
value, error = getValueOfClaim(claim, qualifierId, parameter)
if not value and showerrors then value = error end
if value and references then value = value .. getReferences(frame, claim) end
result[#result + 1] = value
end
result = table.concat(result, list)
else
-- return first element
local claim = claims[sortindices[1]]
result, error = getValueOfClaim(claim, qualifierId, parameter)
if result and references then result = result .. getReferences(frame, claim) end
end
 
-- 5. Агульныя настройкі для ўсіх уласцівасцяў
if result then return result else
if config['global'] then
if showerrors then return error else return default end
local globalParams = mw.clone( config['global'] );
for key, value in pairs( globalParams ) do
if propertyParams[key] == nil then
propertyParams[key] = value;
end
end
end
 
return propertyParams;
end
 
function p.formatProperty( frame )
-- look into entity object
local args = frame.args
function p.ViewSomething(frame)
 
local f = (frame.args[1] or frame.args.id) and frame or frame:getParent()
-- праверка на адсутнасць абавязковага параметру property
local id = f.args.id
if id and (#id ==if not 0)args.property then
throwError( 'property-param-not-provided' )
id = nil
end
local propertyId = mw.language.getContentLanguage():ucfirst( string.gsub( args.property, '%[.*$', '' ) )
local data = mw.wikibase.getEntityObject(id)
local datatype = getPropertyDatatype( propertyId );
if not data then
args = getPropertyParams( propertyId, datatype, args );
return nil
 
-- пракід усіх параметраў з шаблону {wikidata}
local p_frame = frame:getParent();
if p_frame and p_frame:getTitle() == mw.site.namespaces[10].name .. ':Wikidata' then
copyTo( p_frame.args, args );
end
 
args.plain = toBoolean( args.plain, false );
local i = 1
args.nocat = toBoolean( args.nocat, false );
while true do
args.references = toBoolean( args.references, true );
local index = f.args[i]
 
if not index then
-- калі значэнне перададзена ў параметрах выкліку то выводны толькі яго
if type(data) == "table" then
if args.value and args.value ~= '' then
return mw.text.jsonEncode(data, mw.text.JSON_PRESERVE_KEYS + mw.text.JSON_PRETTY)
-- спецыяльнае значэнне для ўтойвання Вікідадзеных
else
if args.value == '-' then
return tostring(data)
return ''
end
end
local value = args.value
 
-- опцыя, якая забараняе афармленне значэння, таму ніяк не чапаем
if args.plain then
return value
end
 
-- апрацоўнікі паводле тыпу значэнні
local wrapperExtraArgs = ''
if args['value-module'] and args['value-function'] and not string.find( value, '[%[%]%{%}]' ) then
local func = getUserFunction( args, 'value' );
value = func( {}, args, value );
elseif datatype == 'commonsMedia' and not string.find( value, '[%[%]%{%}]' ) then
value = formatCommonsMedia( value, args );
elseif datatype == 'external-id' and not string.find( value, '[%[%]%{%}]' ) then
wrapperExtraArgs = wrapperExtraArgs .. ' data-wikidata-external-id="' .. mw.text.encode( value ).. '"';
value = formatExternalId( value, args );
elseif datatype == 'url' then
local moduleUrl = require( 'Module:URL' );
value = moduleUrl.formatUrlSingle( nil, args, value );
end
 
-- абарочваны ў тэг для JS-функцый
data = data[index] or data[tonumber(index)]
if string.match( propertyId, '^P%d+$' ) then
if not data then
value = mw.text.trim( value )
return
 
-- значэнняў з блокавымі тэгамі застаюцца блокам, тэкст убудоўваем у радок
if ( string.match( value, '\n' )
or string.match( value, '<t[dhr][ >]' )
or string.match( value, '<div[ >]' ) ) then
value = '<div class="no-wikidata"' .. wrapperExtraArgs
.. ' data-wikidata-property-id="' .. propertyId .. '">\n'
.. value .. '</div>'
else
value = '<span class="no-wikidata"' .. wrapperExtraArgs
.. ' data-wikidata-property-id="' .. propertyId .. '">'
.. value .. '</span>'
end
end
 
-- дадаваны катэгорыю-маркер
if not args.nocat then
value = value .. categoryLocalValuePresent;
end
 
return value
i = i + 1
end
end
 
if ( args.plain ) then -- выкліку стандартнага апрацоўніка без афармлення, калі перададзена опцыя plain
-- getting sitelink of a given wiki
return frame:callParserFunction( '#property', propertyId );
function p.getSiteLink(frame)
end
local f = frame.args[1]
 
local entity = mw.wikibase.getEntity()
g_frame = frame
if not entity then
-- пасля праверкі ўсіх аргументаў -- выклік функцыі афармлення для ўласцівасці (набору сцвярджэнняў)
return
return formatProperty( args )
end
local link = entity:getSitelink( f )
if not link then
return
end
return link
end
 
--[[
function p.Dump(frame)
Функцыя афармлення спасылак на крыніцы (reference)
local f = (frame.args[1] or frame.args.id) and frame or frame:getParent()
Падрабязней пра спасылкі на крыніцы гл. d:Wikidata:Glossary/ru
local data = mw.wikibase.getEntityObject(f.args.id)
 
if not data then
Экспартуецца ў якасці зарэзерваванага пункта для выкліку з функцый-пашырэнні віду claim-module/claim-function праз context
return i18n.warnDump
Выклік з іншых модуляў непасрэдны ажыццяўляцца не павінен (выкарыстоўвайце frame:expandTemplate разам з адным са специлизированных шаблонаў высновы значэння ўласцівасці).
 
Прымае: аб'ект-табліцу сцвярджэнне
Вяртае: радок аформленых спасылак для адлюстравання ў артыкуле
]]
function formatRefs( context, options, statement )
if ( not context ) then error( 'context not specified' ); end;
if ( not options ) then error( 'options not specified' ); end;
if ( not options.entity ) then error( 'options.entity missing' ); end;
if ( not statement ) then error( 'statement not specified' ); end;
 
if ( not outputReferences ) then
return '';
end
 
local iresult = 1'';
if ( statement.references ) then
while true do
local index = f.args[i]
if not index then
return "<pre>"..mw.dumpObject(data).."</pre>".. i18n.warnDump
end
 
local allReferences = statement.references;
data = data[index] or data[tonumber(index)]
local hasPreferred = false;
if not data then
for _, reference in pairs( statement.references ) do
return i18n.warnDump
if ( reference.snaks
and reference.snaks.P248
and reference.snaks.P248[1]
and reference.snaks.P248[1].datavalue
and reference.snaks.P248[1].datavalue.value["numeric-id"] ) then
local entityId = "Q" .. reference.snaks.P248[1].datavalue.value["numeric-id"];
if ( preferredSources[entityId] ) then
hasPreferred = true;
end
end
end
 
for _, reference in pairs( statement.references ) do
i = i + 1
local display = true;
if ( hasPreferred ) then
if ( reference.snaks
and reference.snaks.P248
and reference.snaks.P248[1]
and reference.snaks.P248[1].datavalue
and reference.snaks.P248[1].datavalue.value["numeric-id"] ) then
local entityId = "Q" .. reference.snaks.P248[1].datavalue.value["numeric-id"];
if ( deprecatedSources[entityId] ) then
display = false;
end
end
end
if ( display ) then
result = result .. moduleSources.renderReference( g_frame, options.entity, reference );
end
end
end
return result
end