יחידה:PropertyLink

מתוך ויקיפדיה, האנציקלופדיה החופשית

יחידה זו משמשת כדי לקשר בוויקיפדיה לפי ויקינתונים. היחידה מיועדת לשימוש בעיקר בתבניות וכוללת את הפונקציות הבאות:

  • property או מאפיין - לקבלת קישור לפי "קביעה" מוויקינתונים
    • פרמטרים: שם המאפיין (property) המתאים (בצורה של P123). למשל בערך דמויי כלב:
      • {{#invoke:PropertyLink|property|p171}} - יחזיר "[[טורפים (סדרת יונקים)|טורפים]]" (טורפים), להבדיל מ־[[{{#property:p70}}]], שיחזיר "[[טורפים]]" (טורפים), שהוא דף פירושונים.
  • label או תווית: דומה לפונקציה הקודמת, רק שלא מחזיר קישור אלא ללא קישור - מחזיר את התווית (label) וללא תלות בקישור כלשהו שקיים או לא קיים בוויקיפדיה בעברית
    • פרמטרים: שם המאפיין (property) המתאים (בצורה של P123)
  • imageLink או תמונה: פונקציה שמחזירה תמונה שמתאימה לשילוב בתבנית מידע בערך.
    • פרמטרים:
      • פרמטר ראשון - (אופציונלי) אם לא מקבל פרמטר בכלל משתמש ב־d:Property:p18 (מאפיין כללי של תמונה), אחרת משתמש בפרמטר המאפיין המכיל את התמונה
      • width - גודל התמונה (אחרת 220px)
  • hasEntry או יש פריט: פונקציה שמחזירה "1" אם לערך יש פריט ויקינתונים; או "" אם אין.
    • פרמטרים: אין

הערות נוספות:

ייתכן שבעתיד תהיה תמיכה מובנית לפחות בחלק מהאפשרויות הנ"ל ראו בmeta:Wikidata/Notes/Inclusion_syntax#Items

local FEMALE_FORM_PROPERTY = 'P2521'
local Date = require('Module:תאריך')
local wikidataModule = require('Module:Wikidata')
local WDS = require('Module:WikidataSelectors')

--[[ 
Fetch the "as of date" property of a associated with a property
]]
function asOfDateQualifier(claim)
	local AS_OF_PROPERTY = 'P585'
	local value
	local error
	value, error = wikidataModule.getValueOfClaim(claim, AS_OF_PROPERTY, nil)
	if value then
		return ' (נכון ל־'..value ..')'
	end
	return ''
end

local function formatQuantity(property) 
	local propValue = property.mainsnak and property.mainsnak.datavalue
	local lang = mw.getContentLanguage()
	local langCode = lang:getCode()
	local asOfDate = asOfDateQualifier(property)
	local localAmount = lang:formatNum( tonumber(propValue.value.amount) )
	local unit = ''
	if propValue.value.unit and string.match( propValue.value.unit, 'http://www.wikidata.org/entity/' ) then
		local unitEntityId = string.gsub( propValue.value.unit, 'http://www.wikidata.org/entity/', '' )
		if unitEntityId and #unitEntityId>0 then
			-- name from label
			unit =  mw.wikibase.label( unitEntityId ) or ''
			local unitSymbol = mw.wikibase.getBestStatements(unitEntityId, 'P5061')
			--  name from properties
			if unitSymbol then
				local writingSystemElementId = 'Q33513' -- hebrew writing system
				local langElementId = 'Q9288' -- hebrew
				local labelFilter = 'P5061[language:'..langCode..'], P5061[P282:' .. writingSystemElementId .. ', P407:' .. langElementId .. ']'
				local labelClaims = WDS.filter( {['P5061']=unitSymbol }, labelFilter )
				for r, claim in pairs( labelClaims ) do
					if claim.mainsnak and claim.mainsnak.datavalue.type == 'monolingualtext' and claim.mainsnak.datavalue.value.text then
						unit = claim.mainsnak.datavalue.value.text
						break
					elseif claim.mainsnak and claim.mainsnak.datavalue and claim.mainsnak.datavalue.type == 'string' and claim.mainsnak.datavalue.value ~= '' then
						unit = claim.mainsnak.datavalue.value
						break
					end
				end
			end
		
			unit = ' ' .. unit
		end
    end	
	return localAmount .. unit .. asOfDate
end

function getPropertyQualifier(property, qualifier)
	local entity = mw.wikibase.getEntityIdForCurrentPage()
    if not entity then return end --the entity doesnt exist or have no claims
	
    local propertyVals = mw.wikibase.getAllStatements( entity, property )
    if not propertyVals or not propertyVals[1] then return end --no such property for this item
 	value, error = wikidataModule.getValueOfClaim(propertyVals[1], qualifier, nil)
	return value
end

local function missingLabelCategory(propertyName)
	return '[[קטגוריה:ויקינתונים:ערכים_חסרי_תווית_בעברית: ' .. (mw.wikibase.label( propertyName) or propertyName) .. ']][[קטגוריה:ויקינתונים:ערכים_חסרי_תווית_בעברית]]'
end

local function getFemaleLabelForEntityId( entityId )
	local femaleForm = mw.wikibase.getBestStatements(entityId, FEMALE_FORM_PROPERTY)
	
	if not femaleForm then return nil, false end
	
	local femLabels = WDS.filterByLanguage( femaleForm, 'he' )
	if femLabels ~= nil and
	   femLabels[1] and
	   femLabels[1].mainsnak and
	   femLabels[1].mainsnak.datavalue and
	   femLabels[1].mainsnak.datavalue.value and
	   femLabels[1].mainsnak.datavalue.value.text then
		return femLabels[1].mainsnak.datavalue.value.text
	end

	return nil, #femaleForm > 0
end

--[[
Get a link to specific entity. E.g sitelink|label.
* Missing label => use sitelink as fallback
* Missing sitelink => just show label
* Mssing gender form: adds category of missing gender label


@param {string} entityId - id of entity to link to (e.g Q42)
@param {string} genderAwareEntity - entity from which to fetch gender for gender form
@param {bool} noLinktoWikidata - if true, returns without the link to Wikidata
@returns {string, bool} formattedValue, missingTranslation - the formatted value along with indicator of missing translation
]]
function formatEntity(entityId, genderAwareEntity, noLinktoWikidata)
	local linkTarget = mw.wikibase.sitelink( entityId )
    local localLabel, langLabel, missingFemaleForm
    local formattedValue
    local missingTranslation = false
    local fallbackLanguage = false
    if genderAwareEntity then
    	local gender = mw.wikibase.getBestStatements(genderAwareEntity, 'P21') -- P21 - gender
    	local isFemale = gender and
    	                 gender[1] and
    	                 gender[1].mainsnak and
    	                 gender[1].mainsnak.datavalue and
    	                 gender[1].mainsnak.datavalue.value and
    	                 (gender[1].mainsnak.datavalue.value["numeric-id"] == 6581072
    	               or gender[1].mainsnak.datavalue.value["numeric-id"] == 1052281
    	               or gender[1].mainsnak.datavalue.value["numeric-id"] == 15145779)

    	if isFemale then
    		localLabel, missingFemaleForm = getFemaleLabelForEntityId( entityId )
    		langLabel = 'he'
    	end
    	-- if we dont have/need female form label,  use regular label
    	if localLabel == nil then
    		localLabel, langLabel = mw.wikibase.getLabelWithLang( entityId )
    	end
    else
    	-- use Hebrew label
    	localLabel, langLabel = mw.wikibase.getLabelWithLang( entityId )
    end
    
    local isLocalLabel = langLabel=='he'
    -- fallback if there is target but no label, use target as label
    if linkTarget and not isLocalLabel then
    	localLabel = linkTarget
    	isLocalLabel = true
    end
    if localLabel and isLocalLabel then
			if linkTarget and localLabel and linkTarget == localLabel then
				formattedValue = mw.ustring.format( "[[%s]]", linkTarget )
			else
    			formattedValue = linkTarget and localLabel and mw.ustring.format( "[[%s|%s]]", linkTarget, localLabel ) or localLabel
    		end
    		if missingFemaleForm then
    			mw.log(mw.ustring.format('חסרה צורת הנקבה ל"%s" (%s)', formattedValue, entityId))
    			formattedValue = formattedValue .. missingLabelCategory( FEMALE_FORM_PROPERTY )
    		end
    else
		missingTranslation = true
		-- in that case we would unfourtanly can show only the entity id which is meaningless for users
		 if langLabel=='en' then
		 	fallbackLanguage = true
    		formattedValue = mw.ustring.format('<span lang="en" dir="ltr">%s</span>', localLabel)
    	else
    		if noLinktoWikidata then
    			formattedValue = 'בפסקה זו רשומה אחת נוספת שטרם תורגמה'
			else
				formattedValue = mw.ustring.format( "[[:d:%s|%s]]", entityId, entityId )
			end
		end
    end
    return formattedValue, missingTranslation, fallbackLanguage
end

function formatOptionalQualifiers(property, qualifiers, qualifiersSep, defaultValue, addParenthesis)
	if (qualifiers==nil) or (#qualifiers == 0) or (not property.qualifiers) then return '' end
	qualifiersSep = qualifiersSep or ', '
	
	local formmatedQualifiers = {}
	local warnings = ''
	local defaultIsOn = true
	
	for _, optionalQualifier in pairs( qualifiers ) do
		-- handling case of "first or default" qualifier (e.g.: for 'P1/P2' take P1 if exists, otherwise - P2)
		local was_found = false
		for selectableQualifier in string.gmatch(optionalQualifier, '[^/]+') do
			if selectableQualifier and property.qualifiers[selectableQualifier] then
				local optionalQualifierVal = mw.wikibase.formatValues(property.qualifiers[selectableQualifier])
				local isQualLocalLabel = true
				if optionalQualifierVal and property.qualifiers[selectableQualifier][1] and property.qualifiers[selectableQualifier][1]['datatype']=='wikibase-item' then 
					for i, optionalQValues in ipairs(property.qualifiers[selectableQualifier]) do
						local qualLabel, qualLang = mw.wikibase.getLabelWithLang( optionalQValues['datavalue']['value']['id'] )
						isQualLocalLabel = isQualLocalLabel and (qualLang=='he')
					end
				end
				if optionalQualifierVal then
					local formattedValue = '<span title="'.. mw.wikibase.label(selectableQualifier)..'" class="propertylink-wikidata-qualifier">'..mw.wikibase.formatValues(property.qualifiers[selectableQualifier]) ..'</span>'
					table.insert(formmatedQualifiers, formattedValue)
					was_found = true
					defaultIsOn = false
					break -- found first available value
				end
			elseif string.sub(selectableQualifier, 1, 1) ~= 'P' then
				table.insert(formmatedQualifiers, selectableQualifier)
				was_found = true
				defaultIsOn = false
				break -- found first available value
			end
		end
		if not was_found then
			table.insert(formmatedQualifiers, defaultValue)
		end
	end
	local res = ""
	if not defaultIsOn then
		res = table.concat( formmatedQualifiers, qualifiersSep)
		if #formmatedQualifiers > 0 and addParenthesis then
			res = mw.ustring.format('<span style="font-size:0.9em"> (%s)</span>', res)
		end
	end
	return res .. warnings
end

--[[ 
Fetch property from wikidata and format it:
* if the entity or the claim doesn't exist - nil
* Formating rules:
	- for entity reference - returns link to entity (using sitelink) with label as text, otherwise wikidata label as text
	- for string - returns the string
	- for quantity - returns the amount
	- for time - returns the time as string
	- for image - returns image inclusion with 250px size
* Multivalues:
	Multivalue is supported with allowMulti. seperator between values defined by multiSeperator
	
@param {string} propertyName - name of property (e.g P123)
@param {bool} allowMulti - whether only first statement should be fetched are all statements.
@param {bool} allowNA - whether if is valid to fetch somevalue snaks: Default: nil/false
@param {string} entityId - Qid of the entity for which we fetch the data. Default: nil (page entity)
@param {string} multiSeperator - seperator between multiple values. Default: ,
@param {string} optionalQualifier - Property id of optional extra qualifier (e.g P123). will be formatted as propertyName (optionalQualifier)
@param {bool} genderAware - Fetch gender form instead of regular label
]]
function getProperty( propertyName, allowMulti, allowNA, entityId, multiSeperator, optionalQualifier, genderAware )
	if propertyName==nil or #propertyName==0 then return end -- no property specified
	entityId = entityId or mw.wikibase.getEntityIdForCurrentPage()
	if entityId == nil then return end -- entity doesnt exist
	options = {
		['allowMulti'] = allowMulti,
		['allowNA'] = allowNA,
		['seperator'] = multiSeperator or ', ',
		['qualifier'] = optionalQualifier,
		['entity-gender-aware'] = genderAware
	}
	if optionalQualifier then
		options['qualifiers'] = {optionalQualifier}
	end
	
	return getPropertyByOptions(propertyName, entityId, options)
end

function property( frame )
    if frame.args['entity']==nil and frame.args['title'] and #frame.args['title']>0  then
        frame.args['entity'] = mw.wikibase.getEntityIdForTitle( frame.args['title'] )
        if frame.args['entity']==nil then return end
    end
    return getProperty(string.upper(frame.args[1]), (frame.args[2] and string.len(frame.args[2])>0) or false, true, frame.args['entity'], frame.args['sep'], frame.args['q'])
end

function propertyWithGender(frame)
	return getProperty(string.upper(frame.args[1]), (frame.args[2] and string.len(frame.args[2])>0) or false, true, frame.args['entity'], ', ', '', true)
end

-- formatted reference for statement. Only for non imported statements
function refStatement(statement)
	if not statement.references or #statement.references == 0 then return '' end -- no reference
	local formattedReferences = {}
	local frame = mw.getCurrentFrame()
	for j, curRef in ipairs(statement.references) do
		local isImportedRef = curRef.snaks and (curRef.snaks['P143'] or curRef.snaks['P4656'])
		if not isImportedRef then
			if curRef.snaks['P854'] then
				table.insert(formattedReferences, frame:extensionTag{  name = 'ref', content = mw.wikibase.renderSnak(curRef.snaks['P854'][1])})
			elseif curRef.snaks['P2699'] then
				table.insert(formattedReferences, frame:extensionTag{  name = 'ref', content = mw.wikibase.renderSnak(curRef.snaks['P2699'][1])})
			else
				table.insert(formattedReferences, frame:extensionTag{  name = 'ref', content = mw.wikibase.formatValues(curRef.snaks)})
			end
		end
	end
	return table.concat(formattedReferences, '')
end

--[[ 
Fetch property from specified entity.

@param {string} propertyName - name of property (e.g P123)
@param {string} entityId - Qid of the entity for which we fetch the data. Default: nil (page entity)
@param {table} options - table with following supported parameters:
	- seperator - seperator between multiple values. Default: ,
	- allowMulti - whether only first statement should be fetched are all statements.
	- allowNA - whether if is valid to fetch somevalue snaks: Default: nil/false
	- entity-gender-aware - Fetch gender form instead of regular label 
	- qualifiers - list of optional qualifers to append to property value (Example {'P1', 'P2'))
	- qualifiers-sep - seperator between optional qualifiers
	- img-width - width of image
]]
function getPropertyByOptions( propertyName, entityId, options )
	-- verify entity exists
	if entityId == nil then entityId = mw.wikibase.getEntityIdForCurrentPage() end
	if entityId==nil then return end
	
	-- defaults
	options = options or {}
	options['seperator'] = options['seperator'] or ', '
	options['allowMulti'] = options['allowMulti'] or false
	options['allowNA'] = options['allowNA'] or false
	options['entity-gender-aware'] = options['entity-gender-aware'] or false -- Fetch gender form instead of regular label
	options['qualifiers'] = options['qualifiers'] or {} -- fetch optional qualifiers
	options['qualifiers-sep'] = options['qualifiers-sep'] or ', '
	options['img-width'] = options['img-width'] or '250px'
	options['source'] = options['source'] or false
	options['filter'] = options['filter'] or nil
	options['sort'] = options['sort'] or { 'P1545' }
	options['default-value'] = options['default-value'] or nil

    local propertyVals = mw.wikibase.getBestStatements(entityId, propertyName)
    if (not propertyVals) or (#propertyVals==0) then return end --no such property for this item
    local resTable = {}
    local missingTranslation = 0
    local hasFallbackTransation = false

	local sortByQualifier = function(t1, t2)
	    if t1 and t2 then
	        local q1 = t1.qualifiers
	        local q2 = t2.qualifiers
	
	        if q1 and q2 then
	            for _, prop in ipairs(options['sort']) do
	                local c1, c2
	
	                if q1[prop] and q1[prop][1] and q1[prop][1].datavalue and q1[prop][1].datavalue.value then
	                    local datavalue = q1[prop][1].datavalue
	                    if datavalue.type == 'string' then
	                        c1 = datavalue.value
	                    elseif datavalue.type == 'quantity' then
	                        c1 = datavalue.value.amount
	                    elseif datavalue.type == 'time' then
	                        c1 = datavalue.value.time
	                    end
	                end
	
	                if q2[prop] and q2[prop][1] and q2[prop][1].datavalue and q2[prop][1].datavalue.value then
	                    local datavalue = q2[prop][1].datavalue
	                    if datavalue.type == 'string' then
	                        c2 = datavalue.value
	                    elseif datavalue.type == 'quantity' then
	                        c2 = datavalue.value.amount
	                    elseif datavalue.type == 'time' then
	                        c2 = datavalue.value.time
	                    end
	                end
	
	                if c1 and c2 then
	                    if c1 < c2 then
	                        return true
	                    elseif c1 > c2 then
	                        return false
	                    end
	                elseif c1 then
	                    return true
	                elseif c2 then
	                    return false
	                end
	            end
	        elseif q1 then
	            return true
	        elseif q2 then
	            return false
	        end
	    else
	        if t1 then
	            return true
	        end
	        if t2 then
	            return false
	        end
	    end
	    return false
	end
    if options['sort'] then
    	table.sort(propertyVals, sortByQualifier)
    end

	if options['filter'] then
		propertyVals = options['filter'](propertyVals)
	end

    for i, property in ipairs(propertyVals) do
	    local propValue = property.mainsnak and property.mainsnak.datavalue
	    if not propValue then 
	    	if options['allowNA'] and (property.mainsnak and property.mainsnak.snaktype)=='somevalue' then
	    		return 'לא ידוע'
	    	else
	    		--property doesnt exist
	    		return 
			end
	    end 
	    
		local isImage = (property.mainsnak.datatype == 'commonsMedia')
	    if propValue['type'] == 'wikibase-entityid' then
	    	local formattedValue, valueMissingTranslation, fallbackLang = formatEntity( propValue.value['id'], options['entity-gender-aware'] and entityId)
	        if not valueMissingTranslation or fallbackLang then
	        	hasFallbackTransation = hasFallbackTransation or fallbackLang
	        	if formattedValue then
	        		formattedValue = formattedValue .. formatOptionalQualifiers(property, options['qualifiers'], options['qualifiers-sep'], options['default-value'], true)
	        	end
	        	if options['source'] and property.references then
		    		formattedValue  = formattedValue.. refStatement(property)
		    	end
        		table.insert(resTable, formattedValue)
	        else
	        	missingTranslation = missingTranslation + 1
	        end
	    elseif propValue['type'] == 'string' then
	    	if isImage then
	    		table.insert(resTable, mw.ustring.format( '[[File:%s|%s]]', propValue.value, options['img-width'] ))
	    	else
	    		local formattedValue = propValue.value
	        	if formattedValue then
	        		formattedValue = formattedValue .. formatOptionalQualifiers(property, options['qualifiers'], options['qualifiers-sep'], options['default-value'], true)
	        	end
        		table.insert(resTable, formattedValue)
	    	end
    	elseif propValue['type'] == 'monolingualtext' then
    		-- for monolingualtext print the language as title
    		local formattedValue = mw.ustring.format('<span lang="%s" title="%s">%s</span>', propValue.value.language, 
    											     mw.language.fetchLanguageName( propValue.value.language , 'he'), propValue.value.text)
    		table.insert(resTable, formattedValue)
	    elseif propValue['type'] == 'quantity' then
	    	local formattedValue = formatQuantity(property)
	    	if options['source'] and property.references then
	    		formattedValue  = formattedValue.. refStatement(property)
	    	end
	    	if formattedValue then
        		formattedValue = formattedValue .. formatOptionalQualifiers(property, options['qualifiers'], options['qualifiers-sep'], options['default-value'], true)
        	end
	    	table.insert(resTable, formattedValue)
	    elseif propValue['type'] == 'time' then
	    	local timeValue = Date.newFromWikidataValue( property.mainsnak.datavalue.value ):toHebrewString()
	    	local timeWarning = property['qualifiers'] and property['qualifiers']['P1480'] and property['qualifiers']['P1480'][1] 
	    						and property['qualifiers']['P1480'][1].datavalue  and property['qualifiers']['P1480'][1].datavalue.value
	    	if timeWarning then
	    		timeWarning = timeWarning and timeWarning['id']
	    		if timeWarning == 'Q5727902' then
	    			timeValue = timeValue .. '[[Circa|?]]'
	    		else
	    			local circu = mw.wikibase.getLabelByLang( timeWarning, 'he' )
	    			if circu then
	    				timeValue = timeValue .. ' ' .. circu
	    			end
	    		end
	    	end
	    	--local timeValue = mw.wikibase.renderSnak( property.mainsnak )
	    	timeValue = mw.ustring.gsub(timeValue, '^(%d+ %a+) (%d+)$', '[[%1]] [[%2]]') 
	    	table.insert(resTable, timeValue)
	    elseif propValue['type'] == 'globecoordinate' then
	    	local frame = mw.getCurrentFrame()
	    	local formattedValue
	    	local globe = propValue.value.globe
	    	if globe == 'http://www.wikidata.org/entity/Q2' then globe = nil
	    	else
	    		local globeMapping = require('Module:Wikidata/Globes')
	    		if globeMapping[globe] then
	    			globe = 'globe:' .. globeMapping[globe]
	    		else
	    			globe = nil
	    		end
			end
	    	if globe then
	    		local northSouth = (propValue.value.latitude>=0 and 'N') or 'S'
	    		local eastWest = (propValue.value.longitude>=0) and 'E' or  'W'
	    		formattedValue = frame:expandTemplate{ title = 'Coord', args = { math.abs(propValue.value.latitude), northSouth, math.abs(propValue.value.longitude), eastWest, globe, display = options['coord-display'] or 'inline' } }
	    	else
	    		formattedValue = frame:expandTemplate{ title = 'Coord', args = { propValue.value.latitude, propValue.value.longitude, display = options['coord-display'] or 'inline' } }
	    	end
	    	table.insert(resTable, formattedValue)
	    else
	    	table.insert(resTable, mw.wikibase.formatValue( property.mainsnak ))
	    end
	    if not options['allowMulti'] then
	    	break
	    end
	end
	
	if missingTranslation > 0 and #resTable> 0 then
		if missingTranslation == 1 then
	    	table.insert(resTable, 'בפסקה זו רשומה אחת נוספת שטרם תורגמה')
		else
	    	table.insert(resTable, 'בפסקה זו '..missingTranslation..' רשומות נוספות שטרם תורגמו')
		end
	end
	
	-- bidi isolation - properly show mix or RTL and LTR statements
	if #resTable>1 then
		local isolateValues = {}
		local needIsolation = false
		for k,v in pairs(resTable) do
			needIsolation = needIsolation or string.find( v, '[a-zA-Z]')
			table.insert(isolateValues, mw.ustring.format('<span style="unicode-bidi:isolate">%s</span>', v))
		end
		if needIsolation then resTable = isolateValues end
	end
	local result = ''
	-- special case * - listify 
	if options['seperator'] == '*' and #resTable>1 then
		result = '*' .. table.concat( resTable, '\n*' )
	else
		result = table.concat( resTable, options['seperator'] )
	end
	if hasFallbackTransation or (missingTranslation > 0 ) then
		result = result .. missingLabelCategory( propertyName )
	end
	return result
end

function getLabel( propertyName, entityId )
    local entity = entityId or mw.wikibase.getEntityIdForCurrentPage()
    if not entity then return end--the entity doesnt exist or have no claims
    local property =  mw.wikibase.getBestStatements(entity, propertyName)
    if not property or not property[1] then return end --no such property for this item
    
    property = property[1]
    local propValue = property.mainsnak.datavalue
    if not propValue then return '' end --property doesnt exist

    if propValue['type'] == 'wikibase-entityid' then
        local label, lang = mw.wikibase.label( propValue.value['id'] )
        return label
    elseif propValue['type'] == 'string' then
        return propValue.value
    end
end

-- Return the label for property, or the label of the linked entiy of that property
function label( frame )
    return getLabel( string.upper(frame.args[1] ))
end

function getItem( propertyName, entityId )
    local entity = entityId or mw.wikibase.getEntityIdForCurrentPage()
    if not entity then return end--the entity doesnt exist or have no claims
    local property =  mw.wikibase.getBestStatements(entity, propertyName)
    if not property or not property[1] then return end --no such property for this item
    
    property = property[1]
    local propValue = property.mainsnak.datavalue
    if not propValue then return '' end --property doesnt exist

    return propValue.value['id']
end

-- Return the Item for property, or the item of the linked entiy of that property
function item( frame )
    return getItem( string.upper(frame.args[1] ))
end

function getImageLink( propName, width, align, description, border, entityId)
	if not entityId then entityId = mw.wikibase.getEntityIdForCurrentPage() end -- entityId wasn't provided explicitly
    if not entityId then return end --the entity doesnt exist or have no claims
    local property = mw.wikibase.getBestStatements(entityId, propName or 'P18')
    if property and property[1] then
    	if property[1].mainsnak and property[1].mainsnak.snaktype=='novalue' then
    		return '[[d:'..mw.wikibase.getEntityIdForCurrentPage()..'#'..(propName or "P18")..'|' ..'לא ידוע]]'
    	end
    	if (description == nil) or (description == "") then
    		for i, v1 in ipairs(property) do
    			if v1.qualifiers then
	    			for _, v2 in pairs(v1.qualifiers) do
	    				for j, v3 in ipairs(v2) do
		    				if v3['property'] == 'P2096' then
			    				local current_description = v3["datavalue"]["value"]
			    				if current_description["language"] == 'he' then
			    					description = current_description["text"]
			    				end
		    				end
	    				end
	    			end
    			end
    		end
    	end
        local width = width or "220"
        local extraParameters = width..'px'
        if align then extraParameters = extraParameters .. '|' .. align end
        if description and (description ~= "") then extraParameters = extraParameters .. '|' .. description end
        if border and (#border > 0) then extraParameters =extraParameters..'|' ..'border' end
        return mw.ustring.format( '[[File:%s|%s]]', property[1].mainsnak.datavalue.value, extraParameters ), description
    end
end
    
--use this function to get associated image to be used in the article
function imageLink( frame )
    return getImageLink(string.upper(frame.args[1] or 'P18'), frame.args["width"], frame.args["align"], frame.args["description"], frame.args["גבול"])
end

-- returns "1" if the page has an associated wikidata entry, "" otherwise
function hasEntry()
    local entity = mw.wikibase.getEntityIdForCurrentPage()
    --if not entity or not entity.claims then return end --the entity doesnt exist or have no claims
    if not entity then return end --the entity doesnt exist or have no claims
    return 1
end

-- returns the wikidata Qid, if exists, "" otherwise
function getPageEntry(frame)
	return mw.wikibase.getEntityIdForTitle(string.upper(frame.args[1] ))
end

function getSitelinksFromQid(frame)
	resTable = mw.wikibase.getEntity(string.upper(frame.args[1] ))
	resTable = resTable["sitelinks"]
	s= "<table>\n"
		for k,v in pairs(resTable) do
			if  v.title then
				s=s.."<tr>".. "<td>" .. k.."</td>".. "<td>" .. v.title.."</td>".."</tr>" .. "\n"
		end 
	end
	return s .. "</table>"
end 

local function createInterwikiForQid(frame)
	local raw = mw.wikibase.getEntity( string.upper( frame.args[1] ) )["sitelinks"]
	local interwikis = ''
	for site, val in pairs(raw) do
		truncated, found = string.gsub(site, 'wiki$', '')
		truncated = string.gsub(truncated, '_', '-')
		if found == 1 and truncated ~= 'he' and truncated ~= 'commons' then interwikis = interwikis .. '[[' .. truncated .. ':' .. val.title .. ']]' end
	end
	return interwikis
end


return {
    imageLink = imageLink,
    ['תמונה'] = imageLink,
    label = label,
    ['תווית'] = label,
    item = item,
    ['פריט'] = item,
    formatEntity = formatEntity,
    property = property,
    propertyWithGender = propertyWithGender,
    ['מאפיין'] = property,
    getProperty = getProperty,
    getPropertyByOptions = getPropertyByOptions,
    getPropertyQualifier = getPropertyQualifier,
    getItem = getItem,
    getImageLink = getImageLink,
    getLabel = getLabel,
    hasEntry = hasEntry,
    getPageEntry = getPageEntry,
    getSitelinksFromQid = getSitelinksFromQid,
    createInterwikiForQid = createInterwikiForQid,
    ['יש פריט'] = hasEntry
}