Module:Infobox Episode

local p = {}

-- For templates to use this module. First unnamed arg is the value to be interpreted. function p.ep(frame) local ep = frame.args[1] local campaignLink = frame.args['campaignlink'] or nil local seasonDisplay = frame.args['seasondisplay'] or nil local transcript = frame.args['transcript'] or nil local linkedList = frame.args['linkedlist'] or nil local category = frame.args['category'] or nil local noCat = frame.args['nocat'] or nil local epNum = frame.args['epnum'] or nil local epMatcher = require('Module:Ep/Matcher') local epInfo = require('Module:Ep/Info') local epCode = epMatcher.matchCode(ep) local data = '' local exists local validCampaign local validConstruction local title = mw.title.getCurrentTitle local namespace = title.namespace local subpageText = title.subpageText local errorMsg local category -- handle missing epCodes if isempty(ep) then data = getErrorCategory('Category:Episodes missing EpCode field', namespace, subpageText) return data -- handle calls to non-existent and/or invalid episodes elseif epCode == '0x00' then -- epCode not in array but construction and campaign is valid if epMatcher.areYouACode(ep) then epCode = epMatcher.zeropadCode(ep) validConstruction = true validCampaign = true exists = false -- invalid and non-existent epCodes. can still try a few operations below else local prefix, epNum = epInfo.parseCode(ep) -- campaign is invalid but code is constructed properly if not isempty(prefix) and not isempty(epNum) then validConstruction = true validCampaign = false exists = false epCode = epMatcher.zeropadCode(ep) -- code is constructed improperly else validConstruction = false validCampaign = false exists = false end end -- epCode is in Ep/Array, AOK else exists = true validCampaign = true validConstruction = true end

if not isempty(campaignLink) and validConstruction then if validCampaign then data = p.campaignLink(epCode) else errorMsg = string.format('Undefined campaign code "%s" in "%s"; check Module:Ep/Decoder ', epInfo.prefix(epCode), epCode) category = getErrorCategory('Category:Calls to undefined campaigns', namespace, subpageText) data = errorMsg .. category end elseif not isempty(seasonDisplay) then -- handle nonexistent seasons of existing shows if validCampaign and isempty(p.seasonDisplay(epCode)) and not isempty(epInfo.season(epCode)) and epInfo.campaignName(epCode) ~= 'Talks Machina' then errorMsg = string.format('Error for %s: No Season #%s for %s; check Module:Ep/Decoder ', epCode, epInfo.season(epCode), epInfo.campaignName(epCode)) category = getErrorCategory('Category:Calls to nonexistent seasons', namespace, subpageText) data = errorMsg .. category -- handle completely invalid episode codes elseif not validConstruction then errorMsg = string.format('Invalid episode code "%s"; use CxNN format ', ep) category = getErrorCategory('Category:Calls to invalid episodes', namespace, subpageText) data = errorMsg .. category else data = p.seasonDisplay(epCode) -- handle valid episode codes not in Ep/Array with maintenance category and no error message -- change so category doesn't display before pushing live if validCampaign and not exists then data = data .. getErrorCategory('Category:Calls to episode codes missing from Ep/Array', namespace, subpageText) end end elseif not isempty(transcript) and exists then data = p.transcript(epCode) elseif not isempty(linkedList) and validCampaign then data = p.linkedList(epCode) elseif not isempty(category) and validConstruction then data = p.category(epCode, noCat) elseif not isempty(epNum) and validConstruction then data = epInfo.epNum(epCode) if data == '0' or data == 0 then prefix, data = epInfo.parseCode(epCode) data = string.format("%d", data) end elseif validCampaign and validConstruction then data = epCode end return data end

-- for the link to the campaign in the episode infobox field "subheader" p.campaignLink = function(epCode) local epInfo = require('Module:Ep/Info') local titleLink local titleName local campaignLink local campaign = epInfo.campaign(epCode) local campaignName = epInfo.campaignName(epCode, false) local campaignNamePlain = epInfo.campaignName(epCode, true) local decoder = mw.loadData('Module:Ep/Decoder') if decoder[campaign]['titleLink'] then titleLink = decoder[campaign]['titleLink'] else titleLink = campaignNamePlain end if decoder[campaign]['infoboxTitle'] then titleName = decoder[campaign]['infoboxTitle'] else titleName = campaignName end if titleLink ~= titleName then campaignLink = titleLink .. '|' .. titleName else campaignLink = titleLink end campaignLink =  .. campaignLink ..  -- should be a helper function return campaignLink end

-- displays in the infobox "Episode" field before the episode number p.seasonDisplay = function(epCode) local seasonDisplay local decoder = mw.loadData('Module:Ep/Decoder') local epInfo = require('Module:Ep/Info') local campaign, season = epInfo.campSeason(epCode) local valid_seasons local pagename local nameForDisplay local italics season = tostring(season) if campaign then valid_seasons = decoder[campaign]['seasons'] or nil end

-- if there's no season or the campaign doesn't have seasons, blank if isempty(season) or isempty(valid_seasons) then return '' -- is season valid? if not, blank elseif not searchKeys(season, valid_seasons) then return '' -- get season info from decoder else pagename = valid_seasons[season]['page'] or '' nameForDisplay = valid_seasons[season]['name'] or '' italics = valid_seasons[season]['italics'] or false end

-- Default display is e.g. "Season 1", other build with season data from decoder if isempty(nameForDisplay) then nameForDisplay = 'Season ' .. season end if not isempty(pagename) then seasonDisplay =  .. nameForDisplay ..  else seasonDisplay = nameForDisplay end if italics then seasonDisplay = "''" .. seasonDisplay .. "''"	end return seasonDisplay end

p.transcript = function(epCode) local epInfo = require('Module:Ep/Info') local pagename = epInfo.pagename(epCode) local transcript = "Transcript:" .. pagename return transcript end

-- for the link to list of episodes in the infobox field "below" p.linkedList = function(epCode) local listLink local listTitle local listContent local linkedListFinal local decoder = mw.loadData('Module:Ep/Decoder') local epInfo = require('Module:Ep/Info') local camp = epInfo.campaign(epCode) if not isempty(decoder[camp]['listLink']) then listLink = decoder[camp]['listLink'] else listLink = decoder[camp]['title'] end if not isempty(decoder[camp]['listTitle']) then listTitle = decoder[camp]['listTitle'] else listTitle = listLink end if listLink ~= listTitle then listContent = listLink .. '|' .. listTitle else listContent = listLink end linkedListFinal =  .. listContent ..  return linkedListFinal end

p.category = function(epCode, noCat) local categoryName if not noCat then noCat = false end local epInfo = require('Module:Ep/Info') local campaign = epInfo.campaign(epCode) local decoder = mw.loadData('Module:Ep/Decoder') if campaign then categoryName = decoder[campaign]['category'] or nil end if isempty(categoryName) then categoryName = 'Episodes not assigned to category' end if noCat then categoryName = 'Category:' .. categoryName .. '' else categoryName = '' end return categoryName end

--function to determine if a string is empty function isempty(s) return s == nil or s == '' end

-- functions for searching an array for a value (case-insensitive) function keyset(dict) local keys = {} for k,v in pairs(dict) do	   keys[k:lower]=true end return keys end

function searchKeys(item, dict) local keys = keyset(dict) if keys[item:lower] then return true else return false end end

-- for including error categories to only certain namespaces function getErrorCategory(category, namespace, subpageText) -- in article namespace, add page to article maintenance category if namespace == 0 then category = "" .. category .. "" -- in a testing space, print out the error on the page itself elseif subpageText == 'test' or subpageText == 'testcases' then category = ' would be in ' .. category .. ' ' -- if it's not a test page, don't add to category else category = '' end return category end

return p