Jump to content

Module:Citation/CS1: Difference between revisions

Synch from sandbox;
m>Dragons flight
m (Changed protection level of Module:Citation/CS1: Remove cascading, doesn't work like as you would expect for Modules/Templates ([Edit=Allow only administrators] (indefinite) [Move=Allow only administrators] (indefinite)))
m>Trappist the monk
(Synch from sandbox;)
Line 1: Line 1:
local z = {
local z = {
error_categories = {};
error_categories = {}; -- for categorizing citations that contain errors
error_ids = {};
error_ids = {};
message_tail = {};
message_tail = {};
maintenance_cats = {}; -- for categorizing citations that aren't erroneous per se, but could use a little work
properties_cats = {}; -- for categorizing citations based on certain properties, language of source for instance
}
}


Line 41: Line 44:
if true ~= Page_in_deprecated_cat then -- if we haven't been here before then set a  
if true ~= Page_in_deprecated_cat then -- if we haven't been here before then set a  
Page_in_deprecated_cat=true; -- sticky flag so that if there are more than one deprecated parameter the category is added only once
Page_in_deprecated_cat=true; -- sticky flag so that if there are more than one deprecated parameter the category is added only once
-- table.insert( z.message_tail, { seterror( 'deprecated_params', {error_message}, true ) } ); -- add error message
table.insert( z.message_tail, { seterror( 'deprecated_params', {}, true ) } ); -- add error message
table.insert( z.message_tail, { seterror( 'deprecated_params', {}, true ) } ); -- add error message
end
end
Line 69: Line 71:
end
end
return str;
return str;
end
--[[--------------------------< F O R M A T _ S C R I P T _ V A L U E >----------------------------------------
|script-title= holds title parameters that are not written in Latin based scripts: Chinese, Japanese, Arabic, Hebrew, etc. These scripts should
not be italicized and may be written right-to-left.  The value supplied by |script-title= is concatenated onto Title after Title has been wrapped
in italic markup.
Regardless of language, all values provided by |script-title= are wrapped in <bdi>...</bdi> tags to isolate rtl languages from the English left to right.
|script-title= provides a unique feature.  The value in |script-title= may be prefixed with a two-character ISO639-1 language code and a colon:
|script-title=ja:*** *** (where * represents a Japanese character)
Spaces between the two-character code and the colon and the colon and the first script character are allowed:
|script-title=ja : *** ***
|script-title=ja: *** ***
|script-title=ja :*** ***
Spaces preceding the prefix are allowed: |script-title = ja:*** ***
The prefix is checked for validity.  If it is a valid ISO639-1 language code, the lang attribute (lang="ja") is added to the <bdi> tag so that browsers can
know the language the tag contains.  This may help the browser render the script more correctly.  If the prefix is invalid, the lang attribute
is not added.  At this time there is no error message for this condition.
At this writing, only |script-title= is supported.  It is anticipated that additional parameters will be created to use this function.
TODO: error messages when prefix is invalid ISO639-1 code; when script_value has prefix but no script;
]]
function format_script_value (script_value)
local lang=''; -- initialize to empty string
local name;
if script_value:match('^%l%l%s*:') then -- if first 3 non-space characters are script language prefix
lang = script_value:match('^(%l%l)%s*:%s*%S.*'); -- get the language prefix or nil if there is no script
if not is_set (lang) then
return ''; -- script_value was just the prefix so return empty string
end
-- if we get this far we have prefix and script
name = mw.language.fetchLanguageName( lang, "en" ); -- get language name so that we can use it to categorize
if is_set (name) then -- is prefix a proper ISO 639-1 language code?
script_value = script_value:gsub ('^%l%l%s*:%s*', ''); -- strip prefix from script
if inArray (lang, {'ar', 'ja', 'ko', 'he', 'zh'}) then -- is prefix one of these language codes?
table.insert( z.properties_cats, 'CS1 uses ' .. name .. '-language script ('..lang..')'); -- categorize in language-specific categories
else
table.insert( z.properties_cats, 'CS1 uses foreign language script'); -- use this category as a catchall until language-specific category is available
end
lang = ' lang="' .. lang .. '" '; -- convert prefix into a lang attribute
else
lang = ''; -- invalid so set lang to empty string
end
end
script_value = '<bdi' .. lang .. '>' .. script_value .. '</bdi>'; -- isolate incase script is rlt
return script_value;
end
--[[--------------------------< S C R I P T _ C O N C A T E N A T E >------------------------------------------
Initially for |title= and |script-title=, this function concatenates those two parameter values after the script value has been
wrapped in <bdi> tags.
]]
function script_concatenate (title, script)
if is_set (script) then
script = format_script_value (script); -- <bdi> tags, lang atribute, categorization, etc; returns empty string on error
if is_set (script) then
title = title .. ' ' .. script; -- concatenate title and script title
end
end
return title;
end
end


Line 246: Line 316:
-- Formats a link to Amazon
-- Formats a link to Amazon
function amazon(id, domain)
function amazon(id, domain)
if checkisbn( id ) then -- see if asin value is a 10-digit isbn
table.insert( z.maintenance_cats, "CS1 maint: ASIN uses ISBN"); -- add to maint category so a bot or awb script can replace |asin= with |isbn=
end
if not is_set(domain) then  
if not is_set(domain) then  
domain = "com"
domain = "com";
elseif ( "jp" == domain or "uk" == domain ) then
elseif inArray (domain, {'jp', 'uk'}) then -- Japan, United Kingdom
domain = "co." .. domain
domain = "co." .. domain;
elseif inArray (domain, {'au', 'br', 'mx'}) then -- Australia, Brazil, Mexico
domain = "com." .. domain;
end
end
local handler = cfg.id_handlers['ASIN'];
local handler = cfg.id_handlers['ASIN'];
Line 347: Line 422:


length = 8 then all digits
length = 8 then all digits
length = 9 then lccn[1] is alpha
length = 9 then lccn[1] is lower case alpha
length = 10 then lccn[1] and lccn[2] are both alpha or both digits
length = 10 then lccn[1] and lccn[2] are both lower case alpha or both digits
length = 11 then lccn[1] is alpha, lccn[2] and lccn[3] are both alpha or both digits
length = 11 then lccn[1] is lower case alpha, lccn[2] and lccn[3] are both lower case alpha or both digits
length = 12 then lccn[1] and lccn[2] are both alpha
length = 12 then lccn[1] and lccn[2] are both lower case alpha


]]
]]
Line 366: Line 441:
end
end
elseif 9 == len then -- LCCN should be adddddddd
elseif 9 == len then -- LCCN should be adddddddd
if nil == id:match("%a%d%d%d%d%d%d%d%d") then -- does it match our pattern?
if nil == id:match("%l%d%d%d%d%d%d%d%d") then -- does it match our pattern?
err_cat = ' ' .. seterror( 'bad_lccn' ); -- set an error message
err_cat = ' ' .. seterror( 'bad_lccn' ); -- set an error message
end
end
elseif 10 == len then -- LCCN should be aadddddddd or dddddddddd
elseif 10 == len then -- LCCN should be aadddddddd or dddddddddd
if id:match("[^%d]") then -- if LCCN has anything but digits (nil if only digits) ...
if id:match("[^%d]") then -- if LCCN has anything but digits (nil if only digits) ...
if nil == id:match("^%a%a%d%d%d%d%d%d%d%d") then -- ... see if it matches our pattern
if nil == id:match("^%l%l%d%d%d%d%d%d%d%d") then -- ... see if it matches our pattern
err_cat = ' ' .. seterror( 'bad_lccn' ); -- no match, set an error message
err_cat = ' ' .. seterror( 'bad_lccn' ); -- no match, set an error message
end
end
end
end
elseif 11 == len then -- LCCN should be aaadddddddd or adddddddddd
elseif 11 == len then -- LCCN should be aaadddddddd or adddddddddd
if not (id:match("^%a%a%a%d%d%d%d%d%d%d%d") or id:match("^%a%d%d%d%d%d%d%d%d%d%d")) then -- see if it matches one of our patterns
if not (id:match("^%l%l%l%d%d%d%d%d%d%d%d") or id:match("^%l%d%d%d%d%d%d%d%d%d%d")) then -- see if it matches one of our patterns
err_cat = ' ' .. seterror( 'bad_lccn' ); -- no match, set an error message
err_cat = ' ' .. seterror( 'bad_lccn' ); -- no match, set an error message
end
end
elseif 12 == len then -- LCCN should be aadddddddddd
elseif 12 == len then -- LCCN should be aadddddddddd
if not id:match("^%a%a%d%d%d%d%d%d%d%d%d%d") then -- see if it matches our pattern
if not id:match("^%l%l%d%d%d%d%d%d%d%d%d%d") then -- see if it matches our pattern
err_cat = ' ' .. seterror( 'bad_lccn' ); -- no match, set an error message
err_cat = ' ' .. seterror( 'bad_lccn' ); -- no match, set an error message
end
end
Line 510: Line 585:
-- Formats an OpenLibrary link, and checks for associated errors.
-- Formats an OpenLibrary link, and checks for associated errors.
function openlibrary(id)
function openlibrary(id)
local code = id:sub(-1,-1)
local code = id:match("^%d+([AMW])$"); -- only digits followed by 'A', 'M', or 'W'
local handler = cfg.id_handlers['OL'];
local handler = cfg.id_handlers['OL'];
if ( code == "A" ) then
if ( code == "A" ) then
return externallinkid({link=handler.link, label=handler.label,
return externallinkid({link=handler.link, label=handler.label,
Line 620: Line 696:
end
end


-- Extract page numbers from external wikilinks in any of the |page=, |pages=, or |at= parameters for use in COinS.
 
--TODO: Fix so this code supports urls like this:
--[[
-- http://www.history.navy.mil/download/va125153.pdf#page=13 %w/:\.
Strip wiki italic and bold markup from argument so that it doesn't contaminate COinS metadata
function get_coins_pages (pages)
This function strips common patterns of apostrophe markup.  We presume that editors who have taken the time to
markup a title have, as a result, provided valid markup.
]]
function strip_apostrophe_markup (argument)
local pattern, c1, c2;
if not is_set (argument) then return argument; end
while true do -- look for and remove all 5-apostrophe (bold and italic) markup
if argument:match ("%'%'%'%'%'") then -- is there an instance of bold-italic?
if argument:match ("%'%'%'%'%'.*%'%'%'%'%'") then -- 5, 5
pattern, c1 = argument:match ("(%'%'%'%'%'(.*)%'%'%'%'%')");
c2 = ""; -- set to empty string so we do only one replacement at end
elseif argument:match ("%'%'%'%'%'.*%'%'%'.*%'%'") then -- bold italic followed by italic (5, 3, 2)
pattern, c1, c2 = argument:match ("(%'%'%'%'%'(.*)%'%'%'(.*)%'%')");
elseif argument:match ("%'%'%'%'%'.*%'%'.*%'%'%'") then -- bold italic followed by bold (5, 2, 3)
pattern, c1, c2 = argument:match ("(%'%'%'%'%'(.*)%'%'(.*)%'%'%')");
elseif argument:match ("%'%'%'.*%'%'.*%'%'%'%'%'") then -- bold italic followed by italic (3, 2, 5)
pattern, c1, c2 = argument:match ("(%'%'%'(.*)%'%'(.*)%'%'%'%'%')");
elseif argument:match ("%'%'.*%'%'%'.*%'%'%'%'%'") then -- italic followed by bold (2, 3, 5)
pattern, c1, c2 = argument:match ("(%'%'(.*)%'%'%'(.*)%'%'%'%'%')");
end
argument=argument:gsub(pattern, c1..c2); -- remove the markup
else
break; -- none or no more 5-apostrophe matches
end
end
while true do -- look for and remove all 3-apostrophe (bold) markup
if argument:match ("%'%'%'.*%'%'%'") then -- is there an instance of bold?
pattern, c1 = argument:match ("(%'%'%'(.*)%'%'%')")
argument=argument:gsub(pattern, c1); -- remove the markup
else
break; -- none or no more 3 matches
end
end
while true do -- look for and remove all 2-apostrophe (italic) markup
if argument:match ("%'%'.*%'%'") then -- is there an instance of italic?
pattern, c1 = argument:match ("(%'%'(.*)%'%')")
argument=argument:gsub(pattern, c1); -- remove the markup
else
break; -- none or no more 2 matches
end
end
return argument; -- done
end
 
--[[--------------------------< M A K E _ C O I N S _ T I T L E >----------------------------------------------
 
Makes a title for COinS from Title and / or ScriptTitle (or any other name-script pairs)
 
Apostrophe markup (bold, italics) is stripped from each value so that the COinS metadata isn't correupted with strings
of %27%27...
]]
 
function make_coins_title (title, script)
if is_set (title) then
title = strip_apostrophe_markup (title); -- strip any apostrophe markup
else
title=''; -- if not set, make sure title is an empty string
end
if is_set (script) then
script = script:gsub ('^%l%l%s*:%s*', ''); -- remove language prefix if present (script value may now be empty string)
script = strip_apostrophe_markup (script); -- strip any apostrophe markup
else
script=''; -- if not set, make sure script is an empty string
end
if is_set (title) and is_set (script) then
script = ' ' .. script; -- add a space before we concatenate
end
return title .. script; -- return the concatenation
end
 
-- Extract page numbers from external wikilinks in any of the |page=, |pages=, or |at= parameters for use in COinS.
function get_coins_pages (pages)
local pattern;
if not is_set (pages) then return pages; end -- if no page numbers then we're done
if not is_set (pages) then return pages; end -- if no page numbers then we're done
Line 851: Line 1,000:
one = one .. namesep .. first  
one = one .. namesep .. first  
end
end
if is_set(person.link) then one = "[[" .. person.link .. "|" .. one .. "]]" end
if is_set(person.link) and person.link ~= control.page_name then
one = "[[" .. person.link .. "|" .. one .. "]]" -- link author/editor if this page is not the author's/editor's page
end
 
if is_set(person.link) and nil ~= person.link:find("//") then one = one .. " " .. seterror( 'bad_authorlink' ) end -- check for url in author link;
if is_set(person.link) and nil ~= person.link:find("//") then one = one .. " " .. seterror( 'bad_authorlink' ) end -- check for url in author link;
end
end
Line 895: Line 1,047:
are present but |last2= is missing, an error message is emitted. |lastn= is not required to have a matching |firstn=.
are present but |last2= is missing, an error message is emitted. |lastn= is not required to have a matching |firstn=.
]]
]]
--Original function
function extractnames(args, list_name)
function extractnames(args, list_name)
    local names = {};
local names = {}; -- table of names
    local i = 1;
local last; -- individual name components
    local last;
local first;
local link;
    while true do
local mask;
        last = selectone( args, cfg.aliases[list_name .. '-Last'], 'redundant_parameters', i );
        if not is_set(last) then
            -- just in case someone passed in an empty parameter
            break;
        end
        names[i] = {
            last = last,
            first = selectone( args, cfg.aliases[list_name .. '-First'], 'redundant_parameters', i ),
            link = selectone( args, cfg.aliases[list_name .. '-Link'], 'redundant_parameters', i ),
            mask = selectone( args, cfg.aliases[list_name .. '-Mask'], 'redundant_parameters', i )
        };
        i = i + 1;
    end
    return names;
end
 
--[[ Broken.  Editor CITEREF IDs are broken by this code (no editor list). Author CITEREF ID render correctly
function extractnames(args, list_name)
local names = {}; -- table of names
local i = 1; -- loop counter/indexer
local i = 1; -- loop counter/indexer
local n = 1; -- output table indexer
local count = 0; -- used to count the number of times we haven't found a |last= (or alias for authors, |editor-last or alias for editors)
local count = 0; -- used to count the number of times we haven't found a |last= (or alias for authors, |editor-last or alias for editors)
Line 927: Line 1,060:


while true do
while true do
names[i] = -- search through args for name components beginning at 1
last = selectone( args, cfg.aliases[list_name .. '-Last'], 'redundant_parameters', i ); -- search through args for name components beginning at 1
{
first = selectone( args, cfg.aliases[list_name .. '-First'], 'redundant_parameters', i );
last = selectone( args, cfg.aliases[list_name .. '-Last'], 'redundant_parameters', i ),
link = selectone( args, cfg.aliases[list_name .. '-Link'], 'redundant_parameters', i );
first = selectone( args, cfg.aliases[list_name .. '-First'], 'redundant_parameters', i ),
mask = selectone( args, cfg.aliases[list_name .. '-Mask'], 'redundant_parameters', i );
link = selectone( args, cfg.aliases[list_name .. '-Link'], 'redundant_parameters', i ),
 
mask = selectone( args, cfg.aliases[list_name .. '-Mask'], 'redundant_parameters', i )
if first and not last then -- if there is a firstn without a matching lastn
};
if names[i].first and not names[i].last then -- if there is a firstn without a matching lastn
names[i].first = nil; -- set first to nil so we don't confuse the implicit et al message code
table.insert( z.message_tail, { seterror( 'first_missing_last', {err_msg_list_name, i}, true ) } ); -- add this error message
table.insert( z.message_tail, { seterror( 'first_missing_last', {err_msg_list_name, i}, true ) } ); -- add this error message
break; -- and done because lastn not found
elseif not first and not last then -- if both firstn and lastn aren't found, are we done?
elseif not names[i].first and not names[i].last then -- if both firstn and lastn aren't found, are we done?
count = count + 1; -- number of times we haven't found last and first
count = count + 1; -- number of times we haven't found last and first
if 2 == count then -- two missing names and we give up
if 2 == count then -- two missing names and we give up
break; -- normal exit or there is a two-name hole in the list; can't tell which
break; -- normal exit or there is a two-name hole in the list; can't tell which
end
end
else -- last with or without a first
else -- we have last with or without a first
names[n] = {last = last, first = first, link = link, mask = mask}; -- add this name to our names list
n = n + 1; -- point to next location in the names table
if 1 == count then -- if the previous name was missing
if 1 == count then -- if the previous name was missing
table.insert( z.message_tail, { seterror( 'missing_name', {err_msg_list_name, i-1}, true ) } ); -- add this error message
table.insert( z.message_tail, { seterror( 'missing_name', {err_msg_list_name, i-1}, true ) } ); -- add this error message
Line 949: Line 1,080:
count = 0; -- reset the counter, we're looking for two consecutive missing names
count = 0; -- reset the counter, we're looking for two consecutive missing names
end
end
i = i + 1; -- bump to the next name
i = i + 1; -- point to next args location
end
end
return names; -- all done, return our list of names
return names; -- all done, return our list of names
end
end
]]


-- Populates ID table from arguments using configuration settings
-- Populates ID table from arguments using configuration settings
Line 1,159: Line 1,287:
end
end


--[[
 
This is the main function doing the majority of the citation
--[[--------------------------< G E T _ I S O 6 3 9 _ C O D E >------------------------------------------------
formatting.
 
Validates language names provided in |language= parameter if not an ISO639-1 code.  Handles the special case that is Norwegian where
ISO639-1 code 'no' is mapped to language name 'Norwegian Bokmål' by Extention:CLDR.
 
Returns the language name and associated ISO639-1 code.  Because case of the source may be incorrect or different from the case that Wikimedia
uses, the name comparisons are done in lower case and when a match is found, the Wikimedia version (assumed to be correct) is returned along
with the code.  When there is no match, we return the original language name string.
 
mw.language.fetchLanguageNames() will return a list of languages that aren't part of ISO639-1. Names that aren't ISO639-1 but that are included
in the list will be found if that name is provided in the |language= parameter.  For example, if |language=Samaritan Aramaic, that name will be
found with the associated code 'sam', not an ISO639-1 code.  When names are found and the associated code is not two characters, this function
returns only the Wikimedia language name.
 
Adapted from code taken from Module:Check ISO 639-1.
]]
]]
function citation0( config, args)
--[[
Load Input Parameters
The argument_wrapper facilitates the mapping of multiple
aliases to single internal variable.
]]
local A = argument_wrapper( args );


local i
function get_iso639_code (lang)
local PPrefix = A['PPrefix']
if 'Norwegian' == lang then
local PPPrefix = A['PPPrefix']
return lang, 'no'; -- special case related to Wikimedia remap of code 'no' at Extension:CLDR
if is_set( A['NoPP'] ) then PPPrefix = "" PPrefix = "" end
end
local languages = mw.language.fetchLanguageNames('en', 'all') -- get a list of language names known to Wikimedia
-- ('all' is required for North Ndebele, South Ndebele, and Ojibwa)
local langlc = mw.ustring.lower(lang); -- lower case version for comparisons
-- Pick out the relevant fields from the arguments.  Different citation templates
for code, name in pairs(languages) do -- scan the list to see if we can find our language
-- define different field names for the same underlying things.
if langlc == mw.ustring.lower(name) then
local Authors = A['Authors'];
if 2 ~= code:len() then -- ISO639-1 codes only
local a = extractnames( args, 'AuthorList' );
return name; -- so return the name but not the code
 
end
local Coauthors = A['Coauthors'];
return name, code; -- found it, return name to ensure proper capitalization and the ISO639-1 code
local Others = A['Others'];
end
local Editors = A['Editors'];
end
local e = extractnames( args, 'EditorList' );
return lang; -- not valid language; return language in original case and nil for ISO639-1 code
 
end
local Year = A['Year'];
 
local PublicationDate = A['PublicationDate'];
--[[--------------------------< L A N G U A G E _ P A R A M E T E R >------------------------------------------
local OrigYear = A['OrigYear'];
 
local Date = A['Date'];
Get language name from ISO639-1 code value provided.  If a code is valid use the returned name; if not, then use the value that was provided with the language parameter.
local LayDate = A['LayDate'];
 
------------------------------------------------- Get title data
There is an exception.  There are three ISO639-1 codes for Norewegian language variants.  There are two official variants: Norwegian Bokmål (code 'nb') and
local Title = A['Title'];
Norwegian Nynorsk (code 'nn').  The third, code 'no',  is defined by ISO639-1 as 'Norwegian' though in Norway this is pretty much meaningless.  However, it appears
local BookTitle = A['BookTitle'];
that on enwiki, editors are for the most part unaware of the nb and nn variants (compare page counts for these variants at Category:Articles with non-English-language external links.
local Conference = A['Conference'];
 
local TransTitle = A['TransTitle'];
Because Norwegian Bokmål is the most common language variant, Media wiki has been modified to return Norwegian Bokmål for ISO639-1 code 'no'. Here we undo that and
local TitleNote = A['TitleNote'];
return 'Norwegian' when editors use |language=no.  We presume that editors don't know about the variants or can't descriminate between them.
local TitleLink = A['TitleLink'];
 
See Help talk:Citation Style_1#An ISO 639-1 language name test
 
When |language= contains a valid ISO639-1 code, the page is assigned to the category for that code: Category:Norwegian-language sources (no) if
the page is a mainspace page and the ISO639-1 code is not 'en'.  Similarly, if the  parameter is |language=Norwegian, it will be categorized in the same way.
 
TODO: Error message when language or language code is not ISO639-1?
]]
 
function language_parameter (lang, namespace)
local code; -- the ISO639-1 two character code
local name; -- the language name
local test='';
if 0 == namespace and (('en' == lang:lower()) or ('english' == lang:lower())) then
table.insert (z.maintenance_cats, 'CS1 maint: English language specified'); -- add maintenance category if |language=English or |language=en in article space
end
 
if 2 == lang:len() then -- ISO639-1 language code are 2 characters (fetchLanguageName also supports 3 character codes)
name = mw.language.fetchLanguageName( lang:lower(), "en" ); -- get ISO 639-1 language name if Language is a proper code
end
 
if is_set (name) then -- if Language specified a valid ISO639-1 code
code = lang:lower(); -- save it
else
name, code = get_iso639_code (lang); -- attempt to get code from name (assign name here so that we are sure of proper capitalization)
end
 
if is_set (code) then
if 'no' == code then name = 'Norwegian' end; -- override wikimedia when code is 'no'
if 0 == namespace and 'en' ~= code then -- is this page main / article space and English not the language?
table.insert( z.properties_cats, 'CS1 ' .. name .. '-language sources (' .. code .. ')'); -- in main space and not English: categorize
end
end
return (" " .. wrap( 'language', name)); -- wrap with '(in ...)'
end
 
 
 
 
--[[--------------------------< C I T A T I O N 0 >------------------------------------------------------------
This is the main function doing the majority of the citation
formatting.
]]
function citation0( config, args)
--[[
Load Input Parameters
The argument_wrapper facilitates the mapping of multiple
aliases to single internal variable.
]]
local A = argument_wrapper( args );
 
local i
local PPrefix = A['PPrefix']
local PPPrefix = A['PPPrefix']
if is_set( A['NoPP'] ) then PPPrefix = "" PPrefix = "" end
-- Pick out the relevant fields from the arguments.  Different citation templates
-- define different field names for the same underlying things.
local Authors = A['Authors'];
local a = extractnames( args, 'AuthorList' );
 
local Coauthors = A['Coauthors'];
local Others = A['Others'];
local Editors = A['Editors'];
local e = extractnames( args, 'EditorList' );
 
local Year = A['Year'];
local PublicationDate = A['PublicationDate'];
local OrigYear = A['OrigYear'];
local Date = A['Date'];
local LayDate = A['LayDate'];
------------------------------------------------- Get title data
local Title = A['Title'];
local ScriptTitle = A['ScriptTitle'];
local BookTitle = A['BookTitle'];
local Conference = A['Conference'];
local TransTitle = A['TransTitle'];
local TitleNote = A['TitleNote'];
local TitleLink = A['TitleLink'];
local Chapter = A['Chapter'];
local Chapter = A['Chapter'];
local ChapterLink = A['ChapterLink'];
local ChapterLink = A['ChapterLink'];
Line 1,291: Line 1,508:
--check this page to see if it is in one of the namespaces that cs1 is not supposed to add to the error categories.
--check this page to see if it is in one of the namespaces that cs1 is not supposed to add to the error categories.
if not is_set(no_tracking_cats) then -- ignore if we are already not going to categorize this page
if not is_set(no_tracking_cats) then -- ignore if we are already not going to categorize this page
for k, v in pairs( cfg.uncategorized_namespaces ) do -- otherwise, spin through the list of namespaces we don't include in error categories
if inArray (this_page.nsText, cfg.uncategorized_namespaces) then
if this_page.nsText == v then -- if we find one
no_tracking_cats = "true"; -- set no_tracking_cats
no_tracking_cats = "true"; -- set no_tracking_cats
break; -- and we're done
end
end
end
end
end
Line 1,500: Line 1,714:
-- COinS metadata (see <http://ocoins.info/>) for
-- COinS metadata (see <http://ocoins.info/>) for
-- automated parsing of citation information.
-- automated parsing of citation information.
-- this is the function call to COinS()
local OCinSoutput = COinS{
local OCinSoutput = COinS{
['Periodical'] = Periodical,
['Periodical'] = Periodical,
['Chapter'] = Chapter,
['Chapter'] = strip_apostrophe_markup (Chapter), -- Chapter stripped of bold / italic wikimarkup
['Title'] = Title,
['Title'] = make_coins_title (Title, ScriptTitle), -- strip_apostrophe_markup (Title), -- Title stripped of bold / italic wikimarkup
['PublicationPlace'] = PublicationPlace,
['PublicationPlace'] = PublicationPlace,
['Date'] = first_set(COinS_date, Date), -- COinS_date has correctly formatted date if Date is valid; any reason to keep Date here?  Should we be including invalid dates in metadata?
['Date'] = first_set(COinS_date, Date), -- COinS_date has correctly formatted date if Date is valid; any reason to keep Date here?  Should we be including invalid dates in metadata?
Line 1,517: Line 1,732:
['RawPage'] = this_page.prefixedText,
['RawPage'] = this_page.prefixedText,
};
};
 
--[[Why is this here?  Why are we mapping Title to Chapter when Periodical is set?
if is_set(Periodical) and not is_set(Chapter) and is_set(Title) then
if is_set(Periodical) and not is_set(Chapter) and is_set(Title) then
Chapter = Title;
Chapter = Title;
Line 1,526: Line 1,741:
TransTitle = '';
TransTitle = '';
end
end
]]
--[[ Hide unfinished cite newsgroup code so that long delayed update can take place
--[[ Hide unfinished cite newsgroup code so that long delayed update can take place
-- special case for cite newsgroup.  Do this after COinS because we are modifying Publishername and ID
-- special case for cite newsgroup.  Do this after COinS because we are modifying Publishername and ID
Line 1,555: Line 1,771:
format = A["AuthorFormat"],
format = A["AuthorFormat"],
maximum = Maximum,
maximum = Maximum,
lastauthoramp = LastAuthorAmp
lastauthoramp = LastAuthorAmp,
page_name = this_page.text -- get current page name so that we don't wikilink to it via authorlinkn
};
};
Line 1,587: Line 1,804:
format = A['EditorFormat'],
format = A['EditorFormat'],
maximum = Maximum,
maximum = Maximum,
lastauthoramp = LastAuthorAmp
lastauthoramp = LastAuthorAmp,
page_name = this_page.text -- get current page name so that we don't wikilink to it via authorlinkn
};
};


Line 1,636: Line 1,854:
-- Test if citation has no title
-- Test if citation has no title
if not is_set(Chapter) and
if not is_set(Title) and
not is_set(Title) and
not is_set(Periodical) and
not is_set(Periodical) and
not is_set(Conference) and
not is_set(Conference) and
not is_set(TransTitle) and
not is_set(TransTitle) and
not is_set(TransChapter) then
not is_set(ScriptTitle) then
table.insert( z.message_tail, { seterror( 'citation_missing_title', {}, true ) } );
table.insert( z.message_tail, { seterror( 'citation_missing_title', {}, true ) } );
end
end
Line 1,660: Line 1,877:
Chapter = "[[" .. ChapterLink .. "|" .. Chapter .. "]]";
Chapter = "[[" .. ChapterLink .. "|" .. Chapter .. "]]";
end
end
if is_set(Periodical) and is_set(Title) then
 
Chapter = wrap( 'italic-title', Chapter );
Chapter = kern_quotes (Chapter); -- if necessary, separate chapter title's leading and trailing quote marks from Module provided quote marks
TransChapter = wrap( 'trans-italic-title', TransChapter );
Chapter = wrap( 'quoted-title', Chapter );
else
TransChapter = wrap( 'trans-quoted-title', TransChapter );
Chapter = kern_quotes (Chapter); -- if necessary, separate chapter title's leading and trailing quote marks from Module provided quote marks
 
Chapter = wrap( 'quoted-title', Chapter );
TransChapter = wrap( 'trans-quoted-title', TransChapter );
end
local TransError = ""
local TransError = ""
if is_set(TransChapter) then
if is_set(TransChapter) then
Line 1,710: Line 1,923:
Title = "[[" .. TitleLink .. "|" .. Title .. "]]"
Title = "[[" .. TitleLink .. "|" .. Title .. "]]"
end
end
 
if is_set(Periodical) then
if inArray(config.CitationClass, {"web","news","journal","pressrelease","conference","podcast"}) then
Title = kern_quotes (Title); -- if necessary, separate title's leading and trailing quote marks from Module provided quote marks
Title = kern_quotes (Title); -- if necessary, separate title's leading and trailing quote marks from Module provided quote marks
Title = wrap( 'quoted-title', Title );
TransTitle = wrap( 'trans-quoted-title', TransTitle );
--[[ Hide unfinished cite newsgroup code so that long delayed update can take place
elseif inArray(config.CitationClass, {"web","news","pressrelease","conference","podcast","newsgroup"}) and
]] elseif inArray(config.CitationClass, {"web","news","pressrelease","conference","podcast"}) and
not is_set(Chapter) then
Title = kern_quotes (Title); -- if necessary, separate title's leading and trailing quote marks from Module provided quote marks
Title = wrap( 'quoted-title', Title );
Title = wrap( 'quoted-title', Title );
Title = script_concatenate (Title, ScriptTitle); -- <bdi> tags, lang atribute, categorization, etc; must be done after title is wrapped
TransTitle = wrap( 'trans-quoted-title', TransTitle );
TransTitle = wrap( 'trans-quoted-title', TransTitle );
Chapter = ''; -- chapter not allowed
else
else
Title = wrap( 'italic-title', Title );
Title = wrap( 'italic-title', Title );
Title = script_concatenate (Title, ScriptTitle); -- <bdi> tags, lang atribute, categorization, etc; must be done after title is wrapped
TransTitle = wrap( 'trans-italic-title', TransTitle );
TransTitle = wrap( 'trans-italic-title', TransTitle );
end
end
 
TransError = "";
TransError = "";
if is_set(TransTitle) then
if is_set(TransTitle) then
if not is_set(Title) then
if is_set(Title) then
TransTitle = " " .. TransTitle;
else
TransError = " " .. seterror( 'trans_missing_title' );
TransError = " " .. seterror( 'trans_missing_title' );
else
TransTitle = " " .. TransTitle;
end
end
end
end
Line 1,828: Line 2,037:
end
end


--[[Look in the list of iso639-1 language codes to see if the value provided in the language parameter matches one of them.  If a match is found,
use that value; if not, then use the value that was provided with the language parameter.
Categories are assigned in a manner similar to the {{xx icon}} templates - categorizes only mainspace citations and only when the language code is not 'en' (English).
]]
if is_set (Language) then
if is_set (Language) then
-- local name = mw.language.fetchLanguageName( Language:lower(), "en" ); -- experiment: this seems to return correct ISO 639-1 language names
Language = language_parameter (Language, this_page.namespace); -- format, categories (article namespace only), name from ISO639-1, etc
local name = cfg.iso639_1[Language:lower()]; -- get the language name if Language parameter has a valid iso 639-1 code
if nil == name then
Language=" " .. wrap( 'language', Language ); -- no match, use parameter's value
else
if 0 == this_page.namespace and 'en' ~= Language:lower() then --found a match; is this page main / article space and English not the language?
Language=" " .. wrap( 'language', name .. '[[Category:Articles with ' .. name .. '-language external links]]' ); -- in main space and not English: categorize
else
Language=" " .. wrap( 'language', name ); --not in mainspace or language is English so don't categorize
end
end
else
else
Language=""; -- language not specified so make sure this is an empty string;
Language=""; -- language not specified so make sure this is an empty string;
end
end


Line 2,207: Line 2,401:
if inArray(no_tracking_cats, {"", "no", "false", "n"}) then
if inArray(no_tracking_cats, {"", "no", "false", "n"}) then
for _, v in ipairs( z.error_categories ) do
for _, v in ipairs( z.error_categories ) do
text = text .. '[[Category:' .. v ..']]';
end
for _, v in ipairs( z.maintenance_cats ) do -- append maintenance categories
text = text .. '[[Category:' .. v ..']]';
end
for _, v in ipairs( z.properties_cats ) do -- append maintenance categories
text = text .. '[[Category:' .. v ..']]';
text = text .. '[[Category:' .. v ..']]';
end
end
Anonymous user
Cookies help us deliver our services. By using our services, you agree to our use of cookies.