Difference between revisions of "Module:Set page header"

From Yugipedia
Jump to: navigation, search
(SMW is not liking us using "Region" as the property name. Switching to "Locality" unless a better name is brought forward.)
(Making the region and edition matching more dynamic, less dependent on the "CG" in the page name)
 
(7 intermediate revisions by the same user not shown)
Line 40: Line 40:
 
medium = {},
 
medium = {},
 
edition = nil,
 
edition = nil,
releaseDate = nil
+
releaseDate = nil,
 +
isParentSet = nil,
 
}
 
}
  
 
local function getRegion( pagename )
 
local function getRegion( pagename )
local index = pagename:match( 'CG%-(%a+)%-?' )
+
-- Get content after the first hyphen after the last `(` in the page name
 +
-- up until the next `-` or `)`
 +
-- More specifically match
 +
-- `(`
 +
-- Any amount of non-`(` non-`-`
 +
-- `-`
 +
-- Any amount of non-`(` non-`-` (Capture the text in this group)
 +
-- An optional `-`
 +
-- An optional amout of non-`(` non-`-`
 +
-- A `)`
 +
-- the end of the string
 +
local index = pagename:match( '%([^%(-]*-([^%(-]*)-?[^%(-]*%)$' )
  
 
local region = DATA.getRegion( index ) -- TODO: handle erroneous region (nil)?
 
local region = DATA.getRegion( index ) -- TODO: handle erroneous region (nil)?
Line 52: Line 64:
  
 
local function getEdition( pagename )
 
local function getEdition( pagename )
local index = pagename:match( 'CG%-%a+%-(%w+)' )
+
-- Get content after the second hyphen after the last `(` in the page name.
 +
local index = pagename:match( '%([^%(-]*-[^%(-]*-([^%(]*)%)$' )
  
 
local edition = DATA.getEdition( index ) -- TODO: handle erroneous edition (nil)?
 
local edition = DATA.getEdition( index ) -- TODO: handle erroneous edition (nil)?
Line 90: Line 103:
 
:wikitext( releaseData.region.full )
 
:wikitext( releaseData.region.full )
 
:wikitext( releaseData.edition and ( ' - %s' ):format( releaseData.edition.full ) )
 
:wikitext( releaseData.edition and ( ' - %s' ):format( releaseData.edition.full ) )
 +
 +
-- If there is a release date, show it in the header
 +
if ( releaseData.releaseDate ) then
 +
header:tag( 'div' ):wikitext( '(Release date: ' .. releaseData.releaseDate .. ')' )
 +
end
  
 
return tostring( header )
 
return tostring( header )
Line 95: Line 113:
  
 
local function makeCategories( ns )
 
local function makeCategories( ns )
return table.concat{
+
local categories = {
( '[[Category:%s %s]]' ):format( releaseData.region.full, ns ),
+
( '[[Category:%s %s]]' ):format( releaseData.region.full, ns )
releaseData.edition and ( '[[Category:%s %s]]' ):format( releaseData.edition.full, ns ),
 
 
}
 
}
 +
 +
if ( releaseData.edition ) then
 +
table.insert( categories, ( '[[Category:%s %s]]' ):format( releaseData.edition.full, ns ) )
 +
end
 +
 +
if ( ns == 'Set Card Lists' and releaseData.isParentSet ) then
 +
table.insert( categories, '[[Category:Set Card Lists for parent sets]]' )
 +
end
 +
 +
-- Set lists with no release dates
 +
-- Excludes lists for parent sets, whose children each have individual release dates
 +
if ( ns == 'Set Card Lists' and not releaseData.releaseDate and not releaseData.isParentSet ) then
 +
table.insert( categories, '[[Category:Set Card Lists with no release date]]' )
 +
end
 +
 +
return table.concat(categories)
 
end
 
end
  
Line 116: Line 149:
 
-- @return table    name, localName, releaseDate
 
-- @return table    name, localName, releaseDate
 
local function querySetData()
 
local function querySetData()
return mw.smw.ask{
+
local results = mw.smw.ask{
 
'[[' .. releaseData.set .. ']]',
 
'[[' .. releaseData.set .. ']]',
 
'?English name = name' ,
 
'?English name = name' ,
 
'?' .. releaseData.language.full .. ' name = localName',
 
'?' .. releaseData.language.full .. ' name = localName',
 
'?' .. releaseData.region.full .. ' release date = releaseDate',
 
'?' .. releaseData.region.full .. ' release date = releaseDate',
 +
-- Bit sloppy, but we need to fallback to this if "Worldwide English release date" is empty
 +
'?English release date = englishReleaseDate',
 +
'?-Parent set = isParentSet',
 
mainlabel = '-'
 
mainlabel = '-'
}[1]
+
}
 +
 
 +
-- Reurn the first result, if there is one
 +
return results and results[ 1 ]
 
end
 
end
  
 
-- Set data for the `releaseData` table based on the page name and parameters
 
-- Set data for the `releaseData` table based on the page name and parameters
local function setReleaseData( currentPageName, args )
+
local function setReleaseData( ns, currentPageName, args )
 
-- Set the set page equal to the supplied set
 
-- Set the set page equal to the supplied set
 
-- or defaul to to the one that can be inferred from the page name
 
-- or defaul to to the one that can be inferred from the page name
Line 148: Line 187:
 
-- Query the set page to find more information
 
-- Query the set page to find more information
 
local queriedData = querySetData()
 
local queriedData = querySetData()
 +
 +
-- Exit early if no results were found
 +
if ( not queriedData ) then
 +
-- todo: Tracking category
 +
return
 +
end
  
 
-- Update the `releaseData` object based on the results of the query
 
-- Update the `releaseData` object based on the results of the query
Line 153: Line 198:
 
releaseData.name        = queriedData.name
 
releaseData.name        = queriedData.name
 
releaseData.localName  = args.name        or queriedData.localName
 
releaseData.localName  = args.name        or queriedData.localName
releaseData.releaseDate = args.releaseDate or queriedData.releaseDate
+
releaseData.isParentSet = queriedData.isParentSet and true or false
 +
 
 +
-- For now, only do the release date for list pages
 +
-- Don't add it to parent set lists e.g. the overall "Shonen Jump promotional cards" list
 +
-- which have multiple releases, each with their own set list.
 +
if ( ns == 'Set Card Lists' and not queriedData.isParentSet ) then
 +
releaseData.releaseDate = args.releaseDate or queriedData.releaseDate
 +
 
 +
-- If 'Worldwide English' and the `releaseDate` is empty, check the `englishReleaseDate`
 +
if ( not releaseData.releaseDate and releaseData.region.full == 'Worldwide English' ) then
 +
releaseData.releaseDate = queriedData.englishReleaseDate
 +
end
 +
end
 
end
 
end
  
Line 171: Line 228:
 
-- Update the `releaseData` object based on information from the page name
 
-- Update the `releaseData` object based on information from the page name
 
-- and the supplied arguments.
 
-- and the supplied arguments.
setReleaseData( currentTitle.text, args )
+
setReleaseData( ns, currentTitle.text, args )
  
 
-- Get the header wikitext
 
-- Get the header wikitext

Latest revision as of 22:03, 4 October 2023

-- <pre>
--[=[Doc
@module Set page header
@description 
@author [[User:Becasita]]
@contact [[User talk:Becasita]]
TODO:
- Validate stuff?
- Create instance?
]=]

local DATA = require( 'Module:Data' )
local UTIL = require( 'Module:Util' )

local mwTitle = mw.title

-- Object containing data on this release of the set
-- (Object is called `releaseData` rather than `setData`, which is ambiguous in programming terms.)
--
-- @param pagename    string    The name of the current page (the list/gallery)
-- @param set         string    The page name of the set
-- @param name        string    The English name of the set
-- @param localName   string    The name of the set in this particular print and language
-- @param language    table     The language of this particular print e.g. "English", "Korean", etc.
--                              (See [[Module:Data/static/language/data]] for the table structure)
-- @param region      table     The distribution region of this print e.g. "European English", "Korean", etc.
--                              (See [[Module:Data/static/region/data]] for the table structure)
-- @param medium      table     The medium (OCG, TCG, etc.)
--                              (See [[Module:Data/static/medium/data]] for the table structure)
-- @param edition     table     The edition of this particular print
--                              (See [[Module:Data/static/edition/data]] for the table structure)
-- @param releaseDate string    The date this print was released
local releaseData = {
	pagename = nil,
	set = nil,
	name = nil,
	localName = nil,
	language = {},
	region = {},
	medium = {},
	edition = nil,
	releaseDate = nil,
	isParentSet = nil,
}

local function getRegion( pagename )
	-- Get content after the first hyphen after the last `(` in the page name
	-- up until the next `-` or `)`
	-- More specifically match
	-- `(`
	-- Any amount of non-`(` non-`-`
	-- `-`
	-- Any amount of non-`(` non-`-` (Capture the text in this group)
	-- An optional `-`
	-- An optional amout of non-`(` non-`-`
	-- A `)`
	-- the end of the string
	local index = pagename:match( '%([^%(-]*-([^%(-]*)-?[^%(-]*%)$' )

	local region = DATA.getRegion( index ) -- TODO: handle erroneous region (nil)?

	return region
end

local function getEdition( pagename )
	-- Get content after the second hyphen after the last `(` in the page name.
	local index = pagename:match( '%([^%(-]*-[^%(-]*-([^%(]*)%)$' )

	local edition = DATA.getEdition( index ) -- TODO: handle erroneous edition (nil)?

	return edition
end

local function getSetPagename( pagename )
	local parts = mw.text.split( pagename, '%(' )

	local length = #parts

	return table.concat( parts, '(', 1, length == 1 and length or ( length - 1 ) )
end


local function makeHeader( setPagename, region, edition )

	local header = mw.html.create( 'div' ):addClass( 'page-header' )

	-- Link to set page:
	header:tag( 'div' )
		:addClass( 'page-header__link' )
		:wikitext( UTIL.link( releaseData.set, releaseData.name ) )

	-- Localized set name:
	if releaseData.language.index ~= 'en' and releaseData.localName then
		header:tag( 'div' )
			:addClass( 'page-header__localized' )
			:attr( 'lang', releaseData.language.index )
			:wikitext( releaseData.localName )
	end

	-- Region and edition
	header:tag( 'div' )
		:addClass( 'page-header__caption' )
		:wikitext( releaseData.region.full )
		:wikitext( releaseData.edition and ( ' - %s' ):format( releaseData.edition.full ) )

	-- If there is a release date, show it in the header
	if ( releaseData.releaseDate ) then
		header:tag( 'div' ):wikitext( '(Release date: ' .. releaseData.releaseDate .. ')' )
	end

	return tostring( header )
end

local function makeCategories( ns )
	local categories = {
		( '[[Category:%s %s]]' ):format( releaseData.region.full, ns )
	}
	
	if ( releaseData.edition ) then
		table.insert( categories, ( '[[Category:%s %s]]' ):format( releaseData.edition.full, ns ) )
	end

	if ( ns == 'Set Card Lists' and releaseData.isParentSet ) then
		table.insert( categories, '[[Category:Set Card Lists for parent sets]]' )
	end

	-- Set lists with no release dates
	-- Excludes lists for parent sets, whose children each have individual release dates
	if ( ns == 'Set Card Lists' and not releaseData.releaseDate and not releaseData.isParentSet ) then
		table.insert( categories, '[[Category:Set Card Lists with no release date]]' )
	end

	return table.concat(categories)
end

local function setSmwData( ns, setPagename, region, edition )
	mw.smw.set({
		['Set page']     = releaseData.set,
		['Local name']   = releaseData.localName,
		['Release']      = releaseData.medium and releaseData.medium.full,
		['Language']     = releaseData.language.full,
		['Locality']     = releaseData.region and releaseData.region.full,
		['Edition']      = releaseData.edition and releaseData.edition.full,
		['Release date'] = releaseData.releaseDate
	})
end

-- Fetch data from the set page
-- @return table    name, localName, releaseDate
local function querySetData()
	local results = mw.smw.ask{
		'[[' .. releaseData.set .. ']]',
		'?English name = name' ,
		'?' .. releaseData.language.full .. ' name = localName',
		'?' .. releaseData.region.full .. ' release date = releaseDate',
		-- Bit sloppy, but we need to fallback to this if "Worldwide English release date" is empty
		'?English release date = englishReleaseDate',
		'?-Parent set = isParentSet',
		mainlabel = '-'
	}

	-- Reurn the first result, if there is one
	return results and results[ 1 ]
end

-- Set data for the `releaseData` table based on the page name and parameters
local function setReleaseData( ns, currentPageName, args )
	-- Set the set page equal to the supplied set
	-- or defaul to to the one that can be inferred from the page name
	releaseData.set = args.set or getSetPagename( currentPageName )

	-- Set the region equal to the supplied region
	-- or default to the one that can be inferred from the page name
	releaseData.region = args.region
		and DATA.getRegion( args.region )
		or getRegion( currentPageName )

	-- Set the language, based on the region
	releaseData.language = DATA.getLanguage( releaseData.region.index )

	-- Set the medium based on the region
	releaseData.medium = DATA.getMedium( releaseData.region.index )

	-- Set the edition based on the page name
	releaseData.edition = getEdition( currentPageName )

	-- Query the set page to find more information
	local queriedData = querySetData()

	-- Exit early if no results were found
	if ( not queriedData ) then
		-- todo: Tracking category
		return
	end

	-- Update the `releaseData` object based on the results of the query
	-- except where overwritten by the `args`.
	releaseData.name        = queriedData.name
	releaseData.localName   = args.name        or queriedData.localName
	releaseData.isParentSet = queriedData.isParentSet and true or false

	-- For now, only do the release date for list pages
	-- Don't add it to parent set lists e.g. the overall "Shonen Jump promotional cards" list
	-- which have multiple releases, each with their own set list.
	if ( ns == 'Set Card Lists' and not queriedData.isParentSet ) then
		releaseData.releaseDate = args.releaseDate or queriedData.releaseDate

		-- If 'Worldwide English' and the `releaseDate` is empty, check the `englishReleaseDate`
		if ( not releaseData.releaseDate and releaseData.region.full == 'Worldwide English' ) then
			releaseData.releaseDate = queriedData.englishReleaseDate
		end
	end
end

function main( args )
	-- Get the name of the current page (distinct from the name of the set page)
	local currentTitle = args.pagename
		and mwTitle.new( args.pagename )
		or mwTitle.getCurrentTitle()

	local ns = currentTitle.subjectNsText

	-- Skip everything if this is in the main namespace
	if not UTIL.trim( ns ) then
		return
	end

	-- Update the `releaseData` object based on information from the page name
	-- and the supplied arguments.
	setReleaseData( ns, currentTitle.text, args )

	-- Get the header wikitext
	local header = makeHeader()

	-- Get the categories wikitext
	local categories = makeCategories( ns )

	-- Set SMW properties
	setSmwData()

	-- Return the wikitext to render
	return table.concat{
		'__NOTOC__',
		header,
		categories,
	}
end

return setmetatable({
	main = function( frame )
		local args = frame:getParent().args

		return main( args )
	end,
}, {
	__call = function( t, args )
		mw.log( main( args ) )
	end,
})
-- </pre>