Module:Footnotes: Difference between revisions

m 1 revision imported
No edit summary
 
Line 1: Line 1:
require('Module:No globals');
require('strict');
local getArgs = require ('Module:Arguments').getArgs;
local getArgs = require ('Module:Arguments').getArgs;


Line 10: Line 10:


local args_default = {
local args_default = {
    group = '',
bracket_left = '',
bracket_left = '',
bracket_right = '',
bracket_right = '',
Line 40: Line 41:
local article_whitelist = anchor_id_list_module.article_whitelist;
local article_whitelist = anchor_id_list_module.article_whitelist;
local template_list = anchor_id_list_module.template_list;
local template_list = anchor_id_list_module.template_list;
    local citeref_patterns = anchor_id_list_module.citeref_patterns
local whitelist_module = mw.loadData ('Module:Footnotes/whitelist');
local whitelist_module = mw.loadData ('Module:Footnotes/whitelist');
local whitelist = whitelist_module.whitelist;
local whitelist = whitelist_module.whitelist;
local special_patterns = whitelist_module.special_patterns;
local DNB_special_patterns = whitelist_module.DNB_special_patterns;
local DNB_template_names = whitelist_module.DNB_template_names;
if 10 == namespace then
return ''; -- automatic form of |no-tracking=yes; TODO: is this too broad?
end


local tally = anchor_id_list[anchor_id]; -- nil when anchor_id not in list; else a tally
local tally = anchor_id_list[anchor_id]; -- nil when anchor_id not in list; else a tally
Line 84: Line 79:
end
end


for _, pattern in ipairs (special_patterns) do -- spin through the spcial patterns and try to match
        for _, pattern in ipairs(citeref_patterns) do                           -- load patterns for wrapper templates on this page
if anchor_id:match (pattern) then
          if anchor_id:match(pattern) then                                     -- spin through the special patterns and try to match
return '';
              return ''
end
          end
end
        end
 
 
for _, dnb_t in ipairs (DNB_template_names or {}) do -- getting desparate now, are there any DNB templates? DNB_template_names may be nil; empty table prevents script error
if template_list[dnb_t] then -- if the article has this DNB template
for _, pattern in ipairs (DNB_special_patterns) do -- spin through the DNB-specifiec wildcard patterns
if anchor_id:match (pattern) then -- and attempt a match
return ''; -- found a match
end
end
end
end


msg = 'no target: ' .. anchor_id; -- anchor_id not found
msg = 'no target: ' .. anchor_id; -- anchor_id not found
mw.log(msg)
        if namespace == 10 and not args.show then                              -- do not generate error message in template namespace
          return ''
        end
category = '[[Category:Harv and Sfn no-target errors]]';
category = '[[Category:Harv and Sfn no-target errors]]';


elseif 1 < tally then
elseif 1 < tally then
msg = 'multiple targets (' .. tally .. '×): ' .. anchor_id; -- more than one anchor_id in this article
msg = 'multiple targets (' .. tally .. '×): ' .. anchor_id; -- more than one anchor_id in this article
mw.log(msg)
        if namespace == 10 and not args.show then                              -- do not generate error message in template namespace
          return ''
        end
category = 0 == namespace and '[[Category:Harv and Sfn multiple-target errors]]' or ''; -- only categorize in article space
category = 0 == namespace and '[[Category:Harv and Sfn multiple-target errors]]' or ''; -- only categorize in article space
return '<span class="error harv-error" style="display: inline; font-size:100%"> ' .. args.template .. ' error: ' .. msg .. ' ([[:Category:Harv and Sfn template errors|help]])</span>' .. category;
return '<span class="error harv-error" style="display: inline; font-size:100%"> ' .. args.template .. ' error: ' .. msg .. ' ([[:Category:Harv and Sfn template errors|help]])</span>' .. category;
Line 112: Line 106:
category = 0 == namespace and category or ''; -- only categorize in article space
category = 0 == namespace and category or ''; -- only categorize in article space


--use this version to show error messages
-- display based on args.show (no display by default)
-- return msg and '<span class="error harv-error" style="display: inline; font-size:100%"> ' .. args.template .. ' error: ' .. msg .. ' ([[:Category:Harv and Sfn template errors|help]])</span>' .. category or '';
    local display = args.show and 'inline' or 'none'
--use this version to hide error messages
    return msg and '<span class="error harv-error" style="display: '..display..'; font-size:100%"> ' .. args.template .. ' error: ' .. msg .. ' ([[:Category:Harv and Sfn template errors|help]])</span>' .. category or '';
return msg and '<span class="error harv-error" style="display: none; font-size:100%"> ' .. args.template .. ' error: ' .. msg .. ' ([[:Category:Harv and Sfn template errors|help]])</span>' .. category or '';


end
end
Line 231: Line 224:
result = table.concat ({args.bracket_left, result, args.bracket_right, args.postscript}):gsub ('%s+', ' '); -- strip redundant spaces
result = table.concat ({args.bracket_left, result, args.bracket_right, args.postscript}):gsub ('%s+', ' '); -- strip redundant spaces
return result .. err_msg;
return result .. err_msg;
end
--[[--------------------------< H Y P H E N _ T O _ D A S H >--------------------------------------------------
Converts a hyphen to a dash under certain conditions.  The hyphen must separate
like items; unlike items are returned unmodified.  These forms are modified:
letter - letter (A - B)
digit - digit (4-5)
digit separator digit - digit separator digit (4.1-4.5 or 4-1-4-5)
letterdigit - letterdigit (A1-A5) (an optional separator between letter and
digit is supported – a.1-a.5 or a-1-a-5)
digitletter - digitletter (5a - 5d) (an optional separator between letter and
digit is supported – 5.a-5.d or 5-a-5-d)
any other forms are returned unmodified.
str may be a comma- or semicolon-separated list
This code copied from Module:Citation/CS1.  The only modification is to require Module:Citation/CS1/Utilities
so that it has access to the functions is_set() and has_accept_as_written()
]]
local function hyphen_to_dash( str )
local utilities = require ('Module:Citation/CS1/Utilities'); -- only modification so that this function has access to is_set() and has_accept_as_written()
if not utilities.is_set (str) then
return str;
end
local accept; -- Boolean
str = str:gsub ('&[nm]dash;', {['&ndash;'] = '–', ['&mdash;'] = '—'}); -- replace &mdash; and &ndash; entities with their characters; semicolon mucks up the text.split
str = str:gsub ('&#45;', '-'); -- replace HTML numeric entity with hyphen character
str = str:gsub ('&nbsp;', ' '); -- replace &nbsp; entity with generic keyboard space character
local out = {};
local list = mw.text.split (str, '%s*[,;]%s*'); -- split str at comma or semicolon separators if there are any
for _, item in ipairs (list) do -- for each item in the list
item, accept = utilities.has_accept_as_written (item); -- remove accept-this-as-written markup when it wraps all of item
if not accept and mw.ustring.match (item, '^%w*[%.%-]?%w+%s*[%-–—]%s*%w*[%.%-]?%w+$') then -- if a hyphenated range or has endash or emdash separators
if item:match ('^%a+[%.%-]?%d+%s*%-%s*%a+[%.%-]?%d+$') or -- letterdigit hyphen letterdigit (optional separator between letter and digit)
item:match ('^%d+[%.%-]?%a+%s*%-%s*%d+[%.%-]?%a+$') or -- digitletter hyphen digitletter (optional separator between digit and letter)
item:match ('^%d+[%.%-]%d+%s*%-%s*%d+[%.%-]%d+$') or -- digit separator digit hyphen digit separator digit
item:match ('^%d+%s*%-%s*%d+$') or -- digit hyphen digit
item:match ('^%a+%s*%-%s*%a+$') then -- letter hyphen letter
item = item:gsub ('(%w*[%.%-]?%w+)%s*%-%s*(%w*[%.%-]?%w+)', '%1–%2'); -- replace hyphen, remove extraneous space characters
else
item = mw.ustring.gsub (item, '%s*[–—]%s*', '–'); -- for endash or emdash separated ranges, replace em with en, remove extraneous whitespace
end
end
table.insert (out, item); -- add the (possibly modified) item to the output table
end
local temp_str = ''; -- concatenate the output table into a comma separated string
temp_str, accept = utilities.has_accept_as_written (table.concat (out, ', ')); -- remove accept-this-as-written markup when it wraps all of concatenated out
if accept then
temp_str = utilities.has_accept_as_written (str); -- when global markup removed, return original str; do it this way to suppress boolean second return value
return temp_str;
else
return temp_str; -- else, return assembled temp_str
end
end
end


Line 253: Line 311:
args.postscript = '';
args.postscript = '';
end
end
args.group = pframe.args.group or '';
args.page = pframe.args.p or pframe.args.page or '';
args.page = pframe.args.p or pframe.args.page or '';
args.pages = pframe.args.pp or pframe.args.pages or '';
args.pages = pframe.args.pp or pframe.args.pages or '';
args.location = pframe.args.loc or '';
args.pages = ('' ~= args.pages) and hyphen_to_dash (args.pages) or '';
args.location = pframe.args.at or pframe.args.loc or '';
args.ref = pframe.args.ref or pframe.args.Ref or '';
args.ref = pframe.args.ref or pframe.args.Ref or '';
args.ignore = ('yes' == pframe.args['ignore-false-positive']) or ('yes' == pframe.args['ignore-err']);
args.ignore = ('yes' == pframe.args['ignore-false-positive']) or ('yes' == pframe.args['ignore-err']);
Line 339: Line 399:
local name = table.concat ({'FOOTNOTE', args.P1, args.P2, args.P3, args.P4, args.P5, strip_url (args.page), strip_url (args.pages), strip_url (args.location)}):gsub ('%s+', ' ');
local name = table.concat ({'FOOTNOTE', args.P1, args.P2, args.P3, args.P4, args.P5, strip_url (args.page), strip_url (args.pages), strip_url (args.location)}):gsub ('%s+', ' ');


return frame:extensionTag ({name='ref', args={name=name}, content=result});
return frame:extensionTag ({name='ref', args={group=args.group, name=name}, content=result});


Line 405: Line 465:
args.postscript = '';
args.postscript = '';
end
end
 
args.group = pframe.args.group or ''; -- reference group
args.ref = pframe.args[table.concat ({n, 'ref'})] or ''; -- alternate reference for this source
args.ref = pframe.args[table.concat ({n, 'ref'})] or ''; -- alternate reference for this source


args.page = pframe.args[table.concat ({n, 'p'})] or ''; -- insource locations for this source
args.page = pframe.args[table.concat ({n, 'p'})] or ''; -- insource locations for this source
args.pages = pframe.args[table.concat ({n, 'pp'})] or '';
args.pages = pframe.args[table.concat ({n, 'pp'})] or '';
args.location = pframe.args[table.concat ({n, 'loc'})] or '';
args.pages = ('' ~= args.pages) and hyphen_to_dash (args.pages) or '';
args.location = pframe.args[table.concat ({n, 'loc'})] or pframe.args[table.concat ({n, 'at'})] or '';
args.ignore = ('yes' == pframe.args[table.concat ({n, 'ignore-false-positive'})]) or ('yes' == pframe.args[table.concat ({n, 'ignore-err'})]);
args.ignore = ('yes' == pframe.args[table.concat ({n, 'ignore-false-positive'})]) or ('yes' == pframe.args[table.concat ({n, 'ignore-err'})]);
-- args.ignore = 'yes' == pframe.args[table.concat ({n, 'ignore-err'})];


table.insert (out, core (args)); -- save the rendering of this source
table.insert (out, core (args)); -- save the rendering of this source
Line 443: Line 503:


local result = table.concat ({table.concat (out, '; '), (last_index == last_ps) and '' or  args.end_ps});
local result = table.concat ({table.concat (out, '; '), (last_index == last_ps) and '' or  args.end_ps});
return frame:extensionTag ({name='ref', args={name=name}, content=result});
return frame:extensionTag ({name='ref', args={group=args.group, name=name}, content=result});
end
end


Line 488: Line 548:
sfnm = sfnm,
sfnm = sfnm,
sfnref = sfnref,
sfnref = sfnref,
    target_check = target_check,
};
};