Module:Sandbox/RedWolf
Appearance
local p = {}
--local wd = require('Module:Wd')
-- Information about a mountain from Module arguments and Wikidata.
local Mountain = { rank, page, name, eid, elevation, elevation_wd,
prominence , range, fa, coords, notes }
-- Runtime options about what information to display
local Options = { showFA = false, showCoord = false, showTCoords = false,
showNotes = false, showRank = false, showRange = false}
-- Wikidata properties
local WD_PROPERTIES = {
elevation = "P2044",
prominence = "P2660",
mtn_range = "P4552",
coords = "P625",
sig_event = "P793",
pt_in_time = "P585"
}
local QID_FIRST_ASCENT = "Q1194369"
local errors
-- Split a string based on a separator
local function split(istring, sep)
-- if sep is null, set it as comma
if sep == nil then sep = ',' end
local t = {}
for str in string.gmatch(istring, '([^'..sep..']+)')
do
table.insert(t, str)
end
return t
end
-- Extract raw elevation/prominence value
local function extractRaw(value)
local i, i1, i2, n
if value == nil then return -1 end
i = string.find(value, " metre")
if i then
n = string.sub(value, 1, i-1):gsub(',', '')
else
n = -1
end
return n
end
-- Call {{elevation_cells} to format the values
local function getElevationCells(frame, elev, unit) --23
if frame.expandTemplate then
return frame:expandTemplate{title='elevation_cells', args= { elev, unit}}
end
return "{{elevation_cells|" .. elev .. "|" .. unit .. "}}"
end
local function getPage(name)
local parts = split(name,"|")
local page = parts[1]
local n = string.find(page, "%[%[")
if n then
page = string.sub(page,3)
end
n = string.find(page, "%]%]")
if n then
page = string.sub(page,1,n-1)
end
return page
end
-- Get an entity's property from Wikidata
local function getWDProperty(frame, eid, name, linked)
mw.log("eid=" .. eid .. " name=" .. name)
--[[ local stmts = mw.wikibase.getBestStatements(eid, name)
if stmts ~= nil then
mw.logObject(stmts)
for i=1,#stmts do
mw.log("stmts["..i.."]="..stmts[i]);
end
end ]]
if frame.preprocess then
local args = "property|"
if linked then args = args .. "linked|" end
args = args .. name .. "|eid=" .. eid
local invoke = "{{#invoke:Wd|" .. args .. "}}"
local value = frame:preprocess(invoke)
mw.log(invoke .. " => " .. value)
return value
end
return "{{Wikidata|property|" .. name .. "|eid=" .. eid .. "}}"
end
-- if frame.expandTemplate then
-- local args = { ['1'] = name, ['page'] = page }
-- return wd._property({eid, args})
-- local args = { ['1'] = 'property', ['2'] = name, ['page'] = page }
-- return frame:expandTemplate{title='Wikidata', args= args}
local function getCoords(frame, eid)
if frame.preprocess == nil then return "????" end
return getWDProperty(frame, eid, WD_PROPERTIES.coords, true)
end
local function getElevation(frame, eid)
if frame.preprocess == nil then return "????" end
value = getWDProperty(frame, eid, WD_PROPERTIES.elevation)
return extractRaw(value)
end
local function getFirstAscent(frame, eid)
if frame.preprocess == nil then return "????" end
local names = WD_PROPERTIES.sig_event .. "|" .. QID_FIRST_ASCENT .. "|" .. WD_PROPERTIES.pt_in_time
local value = frame:preprocess("{{#invoke:Wd|property|qualifier|" .. names .. "|eid=" .. eid .. "}}")
mw.log("FA value = " .. value)
if value == "" then
mw.log("No FA found for eid=" .. eid)
return " "
end
-- Find date such as: 10 July 1913
local i1, i2 = string.find(value, "%(%d+%s%a*%s%d%d%d%d%)")
if i1 then
--mw.log("i1="..i1)
local date = string.sub(value, i1+1, i2-1)
mw.log("FA date = " .. date)
local len = string.len(date)
local year = string.sub(date, len-4, len)
return year
end
-- Find date with just the year; e.g. (2025)
i1, i2 = string.find(value, "%(%d+%)")
if i1 then
local year = string.sub(value, i1+1, i2-1)
return year
end
return "FA date format unknown"
end
-- get prominence from wikidata
local function getProminence(frame, eid)
local prom = getWDProperty(frame, eid, WD_PROPERTIES.prominence, false)
return extractRaw(prom)
end
local function getRange(frame, eid)
return getWDProperty(frame, eid, WD_PROPERTIES.mtn_range, true)
end
-- generate table header
local function header(options, unit)
local unit_1, unit_2
if unit == nil or unit == "" then
unit = 'm'
end
if unit == 'm' then unit_1 = 'm'; unit_2 = 'ft'
else unit_1 = 'ft'; unit_2 = 'm'
end
local s = '{| class="wikitable sortable"\n!'
if options.showRank then s = s .. " align=\"left\" rowspan=2|Rank||" end
s = s .. "rowspan=2|Mountain/Peak ||colspan=2|Elevation ||colspan=2| Prominence "
if options.showRange then s = s .. "||rowspan=2| Subrange" end
if options.showFA then s = s .. "||rowspan=2| FA " end
if options.showCoord then s = s .. "||rowspan=2| Coordinates" end
if options.showNotes then s = s .. "||rowspan=2| Notes" end
s = s .. "\n|-\n"
s = s .. '!' .. unit_1 .. '||' .. unit_2 .. '||' .. unit_1 .. '||' .. unit_2 .. "\n"
return s
end
local function finish()
return "|}"
end
--[[ Process run options
rank - show ranking
range - show mountain range or subrange from WD
fa - show first ascent (year only) from WD
coords - show coordinates from WD
notes - show notes
]]
local function processOptions(runOptions)
local o = Options
if runOptions == nil then return o end
mw.log("runOptions=" .. runOptions)
local parts = split(runOptions, ",")
for i=1,#parts do
option = parts[i]
mw.log("option=" .. option)
if option == "rank" then o.showRank = true end
if option == "fa" then o.showFA = true end
if option == "coords" then o.showCoord = true end
if option == "range" then o.showRange = true end
if option == "notes" then o.showNotes = true end
end
return o
end
local function processLine(frame, options, line)
local parts, n
local name, elev, page, notes
-- argument contains elevation, page link and notes
parts = split(line, ",")
if #parts < 3 then
local m = "<br/>Bad format on argument (<nowiki>" .. line .. "</nowiki>) -- skipped"
errors = errors .. m
mw.log(m)
return nil
end
local mtn = Mountain
elev = parts[1]
name = parts[2]
if name then
page = getPage(name)
mw.log("name = " .. name .. ";page = " .. page)
else
mw.log("name is null")
return nil
end
mtn.name = name
mtn.page = page
mtn.elevation = elev;
if options.showNotes then
notes = parts[3]
n = string.find(notes, "\n")
if n then
notes = string.sub(notes, 1, n-1)
end
mtn.notes = notes
end
local eid = mw.wikibase.getEntityIdForTitle(page)
mw.log("page="..page .. ",eid=" .. eid)
mtn.eid = eid
mtn.elevation_wd = getElevation(frame, eid)
mtn.prominence = getProminence(frame, eid)
if options.showRange then
mtn.range = getRange(frame, eid)
end
if options.showFA then
mtn.fa = getFirstAscent(frame, eid)
end
if options.showCoord then
mtn.coords = getCoords(frame, eid)
end
return mtn
end
local function processRange(ranges, mtn)
local found = false;
local range = mtn.range
for k,v in pairs(ranges) do
if v == range then
found = true; break
end
end
if not found then
mw.log("Adding range " .. range)
table.insert(ranges, range)
else
local i1, i2 = string.find(range, "|")
if i1 then
name = string.sub(range, i1+1)
else
local len = string.len(range)
name = string.sub(range, 3, len-2)
end
mtn.range = name
end
end
function p.list(frame) -- 34
local debug = false
local rank_number = 0
local last_elev = ""
errors = ""
local unit = frame.args[1]
local options = processOptions(frame.args[2])
local output = header(options, unit)
local ranges = {}
for i=3,999,1 do
line = frame.args[i]
if line == nil then break end
mw.log("line=" .. line)
local mtn = processLine(frame, options, line)
if mtn then
if options.showRank and last_elev ~= mtn.elevation then
rank_number = rank_number + 1
mtn.rank = rank_number
last_elev = mtn.elevation
end
if options.showRange then
processRange(ranges, mtn)
end
elev_cells = getElevationCells(frame, mtn.elevation, unit)
prom = mtn.prominence
if prom ~= nil and prom ~= "-1" and prom ~= "" then
prom_cells = getElevationCells(frame, prom, unit)
else
prom_cells = " || "
end
mw.log("elev=" .. mtn.elevation ..";elev_wd="..mtn.elevation_wd)
if options.showNotes and mtn.elevation ~= mtn.elevation_wd then
local mm = "<br/><font color=green>Local/WD elevations mismatch: " .. "\"" .. mtn.elevation .. "\"".. "/\"" .. mtn.elevation_wd.. "\"</font>"
mtn.notes = mtn.notes .. mm
end
local s = "|-\n|"
if options.showRank then s = s .. "align=center|" .. mtn.rank .. "||" end
s = s .. mtn.name .. '\n|' .. elev_cells .. '\n|' .. prom_cells .. '\n|'
if options.showRange then s = s .. '|' .. mtn.range .. '\n' end
if options.showFA then s = s .. '|' .. mtn.fa .. '\n' end
if options.showNotes then s = s .. '|' .. mtn.notes .. '\n' end
output = output .. s
end
end -- for
output = output .. finish()
if debug then
output = "</br><nowiki>"..output.."</nowiki>".."\n"..output
end
if string.len(errors) > 0 then
output = output .. "<font color=red>" .. errors .. "</font>"
end
return output
end
--[[
Test via Preview Window Debug console
print(p.test())
]]
function p.test()
local frame = mw.getCurrentFrame()
-- if frame then mw.logObject(frame) end
-- local frame = {}
frame.args = {}
frame.args[1] = 'm'
frame.args[2] = "rank,range,fa,coords,xnotes"
frame.args[3] = "3954,[[Mount Robson]],Highest point in the Canadian Rockies\n"
frame.args[4] = "3747,[[Mount Columbia (Canada)|Mount Columbia]],Highest point in [[Alberta]]"
frame.args[5] = "3246,[[Apex Mountain (Chaba Icefield)|Apex Mountain]],Named for its location in the centre of the Clemenceau Icefield"
frame.args[6] = "3246,[[Mount Smythe (Alberta)|Mount Smythe]],Named for an English mountaineer"
frame.args[7] = ""
frame.args[8] = " "
return p.list(frame)
end
function p.test2()
local s = '<a href="/wiki/Rainbow_Range_(Rocky_Mountains)" title="Rainbow Range (Rocky Mountains)">Rainbow Range</a>'
--local i1,i2 = string.find(s,"%>(.*)%<%/a%>")
local i1,i2 = string.find(s,"%b><")
if i1 then
mw.log("i1=" .. i1 .. " i2=" .. i2)
mw.log(string.sub(s,i1+1,i2-1))
else
mw.log("not found")
end
end
return p
--[[
{| class="wikitable sortable"
|- bgcolor="#ffffcc"
! align="left" rowspan=2|Rank||rowspan=2|Mountain/Peak ||colspan=2|Elevation ||colspan=2| Prominence ||rowspan=2| Subrange
!rowspan=2| FA ||rowspan=2| Notes ||rowspan=2| References
|-
!m || ft || m || ft
|-
|align=center|1||Mount Robson
|{{elevation_cells|3,959|m}}|{{elevation_cells|2829|m}}||Rainbow Range
|1913||Highest point in the Canadian Rockies|| <ref name=robson/>
]]