Nicht angemeldeter Benutzer - Bearbeiten von Seiten ist nur als angemeldeter Benutzer möglich.

Modul:WLink: Unterschied zwischen den Versionen

Aus imedwiki
Zur Navigation springen Zur Suche springen
(update)
(+)
Zeile 1: Zeile 1:
--[=[ 2014-05-03
+
--[=[ 2014-09-28
 
WLink
 
WLink
 
]=]
 
]=]
Zeile 142: Zeile 142:
 
     -- Postcondition:
 
     -- Postcondition:
 
     --    Returns  string, string
 
     --    Returns  string, string
     --                  first with target and title
+
     --                  first with target
     --                  second result false if not piped
+
     --                  second result title, or false if not piped
 
     --              false if nothing found
 
     --              false if nothing found
 
     local r1 = false;
 
     local r1 = false;
Zeile 159: Zeile 159:
 
         if r1 == "" then
 
         if r1 == "" then
 
             r1 = false;
 
             r1 = false;
 +
        else
 +
            r1 = r1:gsub( "_",        " " )
 +
                  :gsub( " ",  " " )
 +
                  :gsub( " ", " " )
 +
                  :gsub( " ",  " " )
 +
                  :gsub( " ",  " " )
 +
                  :gsub( "  +",      " " );
 +
            r1 = mw.text.decode( r1 );
 
         end
 
         end
 
     end
 
     end
 
     return r1, r2;
 
     return r1, r2;
 
end -- extractWikilink()
 
end -- extractWikilink()
 +
 +
 +
 +
function target( attempt )
 +
    -- Retrieve first target (wikilink or URL), or entire string
 +
    -- Precondition:
 +
    --    attempt  -- string, with presumable link somewhere
 +
    -- Postcondition:
 +
    --    Returns  string, number
 +
    --                  string, with detected link target, or entire
 +
    --                  number, with number of brackets, if found, or 2
 +
    --              false if nothing found
 +
    local r1, r2 = WLink.getTarget( attempt );
 +
    if not r1 then
 +
        r1 = mw.text.trim( attempt );
 +
        r2 = 2;
 +
    end
 +
    return r1, r2;
 +
end -- target()
  
  
Zeile 208: Zeile 235:
 
     --    attempt  -- string, with wikilink or page title
 
     --    attempt  -- string, with wikilink or page title
 
     -- Postcondition:
 
     -- Postcondition:
     --    Returns  string, with identified segment
+
     --    Returns  string, with identified segment, or all
 
     local r = false;
 
     local r = false;
 +
    local s, m = target( attempt );
 +
    if m == 2 then
 +
        local sub = s:match( "/([^/]+)$" );
 +
        if sub then
 +
            r = sub;
 +
        else
 +
            r = s;
 +
        end
 +
    end
 
     return r;
 
     return r;
 
end -- WLink.getBaseTitle()
 
end -- WLink.getBaseTitle()
Zeile 224: Zeile 260:
 
     --              false if no extension found
 
     --              false if no extension found
 
     local r = false;
 
     local r = false;
     local s, m = WLink.getTargetPage( attempt );
+
     local s, m = target( attempt );
    if not s then
 
        s = attempt;
 
        m = 2;
 
    end
 
 
     if m == 2 then
 
     if m == 2 then
 
         s = s:match( "%.(%a+)$" );
 
         s = s:match( "%.(%a+)$" );
Zeile 234: Zeile 266:
 
             r = s:lower();
 
             r = s:lower();
 
         end
 
         end
     elseif s:upper():match( "[%./](PDF)%A?" ) then
+
     elseif s:upper():match( "[%./](PDF)%W?" ) then
 
         r = "pdf";
 
         r = "pdf";
 
     end
 
     end
Zeile 251: Zeile 283:
 
     --              false if no file found
 
     --              false if no file found
 
     local r = false;
 
     local r = false;
 +
    local s, m = target( attempt );
 +
    if m == 2 then
 +
        local slow    = ":" .. s:lower();
 +
        local find = function ( a )
 +
                        local seek = string.format( ":%s:().+%%.%%a+$",
 +
                                                    a:lower() );
 +
                        local join = slow:find( seek );
 +
                        local ret;
 +
                        if join then
 +
                            ret = s:sub( join + #a + 1 );
 +
                        end
 +
                        return ret;
 +
                    end;
 +
        r = find( "file" );
 +
        if not r then
 +
            local trsl = mw.site.namespaces[6];
 +
            r = find( trsl.name );
 +
            if not r then
 +
              trsl = trsl.aliases;
 +
              for k, v in pairs( trsl ) do
 +
                  r = find( v );
 +
                  if r then
 +
                      break; -- for k, v
 +
                  end
 +
              end -- for k, v
 +
          end
 +
        end
 +
    end
 
     return r;
 
     return r;
 
end -- WLink.getFile()
 
end -- WLink.getFile()
Zeile 257: Zeile 317:
  
 
function WLink.getFragment( attempt )
 
function WLink.getFragment( attempt )
     -- Retrieve first target page (page name or URL of page)
+
     -- Retrieve fragment
 
     -- Precondition:
 
     -- Precondition:
     --    attempt  -- string, with presumable link somewhere
+
     --    attempt  -- string, with presumable fragment
 
     -- Postcondition:
 
     -- Postcondition:
     --    Returns  string, with first detected linked page
+
     --    Returns  string, with detected fragment
     --              false if nothing found
+
     --              false if no address found
 
     local r = false;
 
     local r = false;
     local s = WLink.getTarget( attempt );
+
     local s, m = target( attempt );
     if r then
+
     if s then
 
         local i = s:find( "#", 1, true );
 
         local i = s:find( "#", 1, true );
 
         if i then
 
         if i then
             r = mw.text.trim( r:sub( i + 1 ) );
+
             if i > 1 then
 +
                s = s:sub( i - 1 );
 +
                i = 2;
 +
            end
 +
            if s:find( "&#", 1, true ) then
 +
                s = mw.text.decode( s );
 +
                i = s:find( "#", 1, true );
 +
                if not i then
 +
                  s = "";
 +
                  i = 0;
 +
                end
 +
            end
 +
            s = s:sub( i + 1 );
 +
            r = mw.text.trim( s );
 
             if r == "" then
 
             if r == "" then
 
                 r = false;
 
                 r = false;
 +
            elseif m == 2 then
 +
                r = r:gsub( "%.(%x%x)", "%%%1" )
 +
                    :gsub( "_", " " );
 +
                r = mw.uri.decode( r, "PATH" );
 
             end
 
             end
 
         end
 
         end
Zeile 287: Zeile 364:
 
     --              false if no project language found
 
     --              false if no project language found
 
     local r = false;
 
     local r = false;
 +
    local s, m = target( attempt );
 
     return r;
 
     return r;
 
end -- WLink.getLanguage()
 
end -- WLink.getLanguage()
Zeile 300: Zeile 378:
 
     --              false if no namespace found
 
     --              false if no namespace found
 
     local r = false;
 
     local r = false;
 +
    local s, m = target( attempt );
 
     return r;
 
     return r;
 
end -- WLink.getNamespace()
 
end -- WLink.getNamespace()
Zeile 643: Zeile 722:
 
         r = string.format( "<span class=\"error\">%s</span>", r );
 
         r = string.format( "<span class=\"error\">%s</span>", r );
 
     end
 
     end
     return r
+
     return r;
 
end -- Template()
 
end -- Template()
  

Version vom 2. Oktober 2014, 11:44 Uhr

Vorlagenprogrammierung Diskussionen Lua Unterseiten
Modul Deutsch English

Modul: Dokumentation
Diese Seite enthält Code in der Programmiersprache Lua. Einbindungszahl Cirrus
Wikipedia-logo-v2.svg
Dieses Modul (und die Dokumentation) basieren (teilweise) auf Modul:WLink aus der freien Enzyklopädie Wikipedia in der Fassung 129808410 vom 14. December 2019 und steht unter der GNU Lizenz für freie Dokumentation und der Creative Commons Attribution/Share Alike. Auf Wikipedia ist eine Liste der Autoren verfügbar. Veränderungen seither in Imedwiki. Veränderungen seither in Wikipedia.Weiteres zum Import aus Wikipedia siehe Seite Imedwiki:Import aus Wikipedia.

--[=[ 2014-09-28
WLink
]=]



-- local globals
local WLink   = { };
local URLutil = false;



local utilURL = function ()
    -- Attach URLutil library module
    -- Postcondition:
    --     Returns  table, with URLutil library
    --     Throws error, if not available
    if not URLutil then
        local lucky, util = pcall( require, "Module:URLutil" );
        if lucky then
            if type( util ) == "table" then
                URLutil = util.URLutil();
            end
            util = "library URLutil invalid";
        end
        if type( URLutil ) ~= "table" then
            error( util, 0 );
        end
    end
    return URLutil;
end -- utilURL()



local contentExtlink = function ( attempt )
    -- Retrieve span of external link between brackets
    -- Precondition:
    --     attempt  -- string, with presumable link
    --                         the first char is expected to be "["
    -- Postcondition:
    --     Returns  string, number, number
    --                  string including whitespace
    --                  number with index of relevant "["
    --                  number with index after relevant "]"
    --              false if nothing found
    local r1 = false;
    local r2 = false;
    local r3 = attempt:find( "]", 2, true );
    if r3 then
        local s = attempt:sub( 2,  r3 - 1 );
        local i = s:find( "[", 1, true );
        if i then
            r1 = s:sub( i + 1 );
            r2 = i;
        else
            r1 = s;
            r2 = 1;
        end
    else
        r3 = false;
    end
    return r1, r2, r3;
end -- contentExtlink()



local contentWikilink = function ( attempt )
    -- Retrieve span of wikilink between brackets
    -- Precondition:
    --     attempt  -- string, with presumable link
    --                        the first two chars are expected to be "[["
    -- Postcondition:
    --     Returns  string, number, number
    --                  string including whitespace
    --                  number with index of relevant "[["
    --                  number with index after relevant "]]"
    --              false if nothing found
    local r1 = false;
    local r2 = false;
    local r3 = attempt:find( "]]", 3, true );
    if r3 then
        local s = attempt:sub( 3,  r3 - 1 );
        local i = s:find( "[[", 1, true );
        if i then
            r1 = s:sub( i + 2 );
            r2 = i;
        else
            r1 = s;
            r2 = 1;
        end
    end
    return r1, r2, r3;
end -- contentWikilink()



local extractExtlink = function ( attempt )
    -- Retrieve external link
    -- Precondition:
    --     attempt  -- string, with presumable link
    --                        the first char is expected to be "["
    -- Postcondition:
    --     Returns  string, string
    --                  first with target and title
    --                  second result false if not titled
    --              false if nothing found
    local r1 = false;
    local r2 = false;
    local s = contentExtlink( attempt );
    if s then
        local i = s:find( "%s", 1 );
        if i then
            r1 = s:sub( 1,  i - 1 );
            r2 = mw.text.trim( s:sub( i + 1 ) );
            if r2 == "" then
                r2 = false;
            end
        else
            r1 = s;
        end
        if r1 then
            r1 = mw.text.trim( r1 );
            if r1 == ""  or
               not utilURL().isResourceURL( r1 ) then
                r1 = false;
            end
        end
        if not r1 then
            r2 = false;
        end
    end
    return r1, r2;
end -- extractExtlink()



local extractWikilink = function ( attempt )
    -- Retrieve wikilink
    -- Precondition:
    --     attempt  -- string, with presumable link
    --                        the first two chars are expected to be "[["
    -- Postcondition:
    --     Returns  string, string
    --                  first with target
    --                  second result title, or false if not piped
    --              false if nothing found
    local r1 = false;
    local r2 = false;
    local s = contentWikilink( attempt );
    if s then
        local i = s:find( "|", 1, true );
        if i then
            r1 = s:sub( 1,  i - 1 );
            r2 = s:sub( i + 1 );
        else
            r1 = s;
        end
        r1 = mw.text.trim( r1 );
        if r1 == "" then
            r1 = false;
        else
            r1 = r1:gsub( "_",        " " )
                   :gsub( "&nbsp;",   " " )
                   :gsub( "&thinsp;", " " )
                   :gsub( "&#160;",   " " )
                   :gsub( "&#8239;",  " " )
                   :gsub( "  +",      " " );
            r1 = mw.text.decode( r1 );
        end
    end
    return r1, r2;
end -- extractWikilink()



function target( attempt )
    -- Retrieve first target (wikilink or URL), or entire string
    -- Precondition:
    --     attempt  -- string, with presumable link somewhere
    -- Postcondition:
    --     Returns  string, number
    --                  string, with detected link target, or entire
    --                  number, with number of brackets, if found, or 2
    --              false if nothing found
    local r1, r2 = WLink.getTarget( attempt );
    if not r1 then
        r1 = mw.text.trim( attempt );
        r2 = 2;
    end
    return r1, r2;
end -- target()



function WLink.ansiPercent( attempt )
    -- Convert string by ANSI encoding rather than UTF-8 encoding
    -- Precondition:
    --     attempt  -- string, with presumable ANSI characters
    -- Postcondition:
    --     Returns  string, encoded
    local k, s;
    local r = attempt;
    for i = mw.ustring.len( attempt ), 1, -1 do
        k = mw.ustring.codepoint( attempt, i, i );
        if k <= 32  or  k > 126 then
            if k > 255 then
                s = mw.ustring.sub( attempt, i, i );
                if k > 2047 then
                    s = string.format( "%%%2X%%%2X%%%2X",
                                       s:byte( 1, 1 ),
                                       s:byte( 2, 2 ),
                                       s:byte( 3, 3 ) );
                else
                    s = string.format( "%%%2X%%%2X",
                                       s:byte( 1, 1 ),
                                       s:byte( 2, 2 ) );
                end
            else
                s = string.format( "%%%2X", k );
            end
            r = string.format( "%s%s%s",
                               mw.ustring.sub( attempt,  1,  i - 1 ),
                               s,
                               mw.ustring.sub( r,  i + 1 ) );
        end
    end -- for --i
    return r;
end -- WLink.ansiPercent()



function WLink.getBaseTitle( attempt )
    -- Retrieve last segment in subpage, no extension or fragment
    -- Precondition:
    --     attempt  -- string, with wikilink or page title
    -- Postcondition:
    --     Returns  string, with identified segment, or all
    local r = false;
    local s, m = target( attempt );
    if m == 2 then
        local sub = s:match( "/([^/]+)$" );
        if sub then
            r = sub;
        else
            r = s;
        end
    end
    return r;
end -- WLink.getBaseTitle()



function WLink.getExtension( attempt )
    -- Retrieve media extension
    -- Precondition:
    --     attempt  -- string, with wikilink (media link) or page title
    --                         if URL, PDF may be detected
    -- Postcondition:
    --     Returns  string, with detected downcased media type
    --              false if no extension found
    local r = false;
    local s, m = target( attempt );
    if m == 2 then
        s = s:match( "%.(%a+)$" );
        if s then
            r = s:lower();
        end
    elseif s:upper():match( "[%./](PDF)%W?" ) then
        r = "pdf";
    end
    return r;
end -- WLink.getExtension()



function WLink.getFile( attempt )
    -- Retrieve media page identifier
    -- Precondition:
    --     attempt  -- string, with wikilink (media link) or page title
    -- Postcondition:
    --     Returns  string, with detected file title
    --                      no namespace nor project
    --              false if no file found
    local r = false;
    local s, m = target( attempt );
    if m == 2 then
        local slow    = ":" .. s:lower();
        local find = function ( a )
                         local seek = string.format( ":%s:().+%%.%%a+$",
                                                     a:lower() );
                         local join = slow:find( seek );
                         local ret;
                         if join then
                             ret = s:sub( join + #a + 1 );
                         end
                         return ret;
                     end;
        r = find( "file" );
        if not r then
            local trsl = mw.site.namespaces[6];
            r = find( trsl.name );
            if not r then
               trsl = trsl.aliases;
               for k, v in pairs( trsl ) do
                   r = find( v );
                   if r then
                       break; -- for k, v
                   end
               end -- for k, v
           end
        end
    end
    return r;
end -- WLink.getFile()



function WLink.getFragment( attempt )
    -- Retrieve fragment
    -- Precondition:
    --     attempt  -- string, with presumable fragment
    -- Postcondition:
    --     Returns  string, with detected fragment
    --              false if no address found
    local r = false;
    local s, m = target( attempt );
    if s then
        local i = s:find( "#", 1, true );
        if i then
            if i > 1 then
                s = s:sub( i - 1 );
                i = 2;
            end
            if s:find( "&#", 1, true ) then
                s = mw.text.decode( s );
                i = s:find( "#", 1, true );
                if not i then
                   s = "";
                   i = 0;
                end
            end
            s = s:sub( i + 1 );
            r = mw.text.trim( s );
            if r == "" then
                r = false;
            elseif m == 2 then
                r = r:gsub( "%.(%x%x)", "%%%1" )
                     :gsub( "_", " " );
                r = mw.uri.decode( r, "PATH" );
            end
        end
    end
    return r;
end -- WLink.getFragment()



function WLink.getLanguage( attempt )
    -- Retrieve language project identifier
    -- Precondition:
    --     attempt  -- string, with wikilink or page title
    -- Postcondition:
    --     Returns  string, with detected downcased language identifier
    --              false if no project language found
    local r = false;
    local s, m = target( attempt );
    return r;
end -- WLink.getLanguage()



function WLink.getNamespace( attempt )
    -- Retrieve namespace number
    -- Precondition:
    --     attempt  -- string, with wikilink or page title
    -- Postcondition:
    --     Returns  number, of detected namespace
    --              false if no namespace found
    local r = false;
    local s, m = target( attempt );
    return r;
end -- WLink.getNamespace()



function WLink.getPlain( attempt )
    -- Retrieve text with all links replaced by link titles
    -- Precondition:
    --     attempt  -- string, with wikitext
    -- Postcondition:
    --     Returns  string, with modified wikitext without links
    local r = attempt;
    local i = 1;
    local j, k, n, lean, s, shift, suffix;
    while ( true ) do
        j = r:find( "[", i, true );
        if j then
            suffix = r:sub( j );
            i      = j + 1;
            lean   = ( r:byte( i, i ) == 91 );
            if lean then
                s, k, n = contentWikilink( suffix );
            else
                s, k, n = contentExtlink( suffix );
            end
            if s then
                if k > 1 then
                    n      = n - k;
                    i      = j + k;
                    j      = i - 1;
                    suffix = r:sub( j );
                end
                if lean then
                    s, shift = extractWikilink( suffix );
                    if not shift then
                        shift = s;
                    end
                else
                    s, shift = extractExtlink( suffix );
                    if not shift then
                        shift = "";
                    end
                    i = i - 1;
                end
                if j > 1 then
                    s = r:sub( 1, j - 1 );
                else
                    s = "";
                end
                r = string.format( "%s%s%s",
                                   s,  shift,  r:sub( n + i ) );
                i = i + #shift;
            else
                break; -- while true
            end
        else
            break; -- while true
        end
    end -- while true
    return r;
end -- WLink.getPlain()



function WLink.getProject( attempt )
    -- Retrieve project identifier
    -- Precondition:
    --     attempt  -- string, with wikilink or page title
    -- Postcondition:
    --     Returns  string, with detected downcased project identifier
    --              false if no project identifier found
    local r = false;
    return r;
end -- WLink.getProject()



function WLink.getTarget( attempt )
    -- Retrieve first target (wikilink or URL)
    -- Precondition:
    --     attempt  -- string, with presumable link somewhere
    -- Postcondition:
    --     Returns  string, number
    --                  string, with first detected link target
    --                  number, with number of brackets, if found
    --              false if nothing found
    local r1 = false;
    local r2 = false;
    local i  = attempt:find( "[", 1, true );
    if i then
        local m;
        r1 = attempt:sub( i );
        if r1:byte( 2, 2 ) == 91 then
            m  = 2;
            r1 = extractWikilink( r1 );
        else
            m  = 1;
            r1 = extractExtlink( r1 );
        end
        if r1 then
            r2 = m;
        end
    else
        r1 = attempt:match( "%A?([hf]t?tps?://%S+)%s?" );
        if r1 then
            if utilURL().isResourceURL( r1 ) then
                r2 = 0;
            else
                r1 = false;
            end
        else
            r1 = false;
        end
    end
    return r1, r2;
end -- WLink.getTarget()



function WLink.getTargetPage( attempt )
    -- Retrieve first target page (page name or URL of page)
    -- Precondition:
    --     attempt  -- string, with presumable link somewhere
    -- Postcondition:
    --     Returns  string, with first detected linked page
    --              false if nothing found
    local r1, r2 = WLink.getTarget( attempt );
    if r1 then
        local i = r1:find( "#", 1, true );
        if i then
            if i == 1 then
                r1 = false;
            else
                r1 = mw.text.trim( r1:sub( 1,  i - 1 ) );
            end
        end
    end
    return r1, r2;
end -- WLink.getTargetPage()



function WLink.getTitle( attempt )
    -- Retrieve first link title (wikilink or URL), or wikilink target
    -- Precondition:
    --     attempt  -- string, with presumable link somewhere
    -- Postcondition:
    --     Returns  string, with first detected link target
    --              false if nothing found
    local r = false;
    local i = attempt:find( "[", 1, true );
    if i then
        local s1, s2;
        r = attempt:sub( i );
        if r:byte( 2, 2 ) == 91 then
            s1, s2 = extractWikilink( r );
            if s2 then
                r = s2;
            else
                r = s1;
            end
        else
            s1, r = extractExtlink( r );
        end
    end
    return r;
end -- WLink.getTitle()



function WLink.isBracketedLink( attempt )
    -- Does attempt match a bracketed link?
    -- Precondition:
    --     attempt  -- string, with
    -- Postcondition:
    --     Returns  boolean
    local r = false;
    local i = attempt:find( "[", 1, true );
    if i then
        local s = attempt:sub( i );
        if s:byte( 2, 2 ) == 91 then
            s = extractWikilink( s );
        else
            s = extractExtlink( s );
        end
        if s then
            r = true;
        end
    end
    return r;
end -- WLink.isBracketedLink()



function WLink.isBracketedURL( attempt )
    -- Does attempt match a bracketed URL?
    -- Precondition:
    --     attempt  -- string, with
    -- Postcondition:
    --     Returns  boolean
    local r = false;
    return r;
end -- WLink.isBracketedURL()



function WLink.isExternalLink( attempt )
    -- Does attempt match an external link?
    -- Precondition:
    --     attempt  -- string, with
    -- Postcondition:
    --     Returns  boolean
    local s, r = WLink.getTarget( attempt );
    if r then
        r = ( r < 2 );
    end
    return r;
end -- WLink.isExternalLink()



function WLink.isInterlanguage( attempt )
    -- Does attempt match an interlanguage link?
    -- Precondition:
    --     attempt  -- string, with
    -- Postcondition:
    --     Returns  boolean
    local r = false;
    return r;
end -- WLink.isInterlanguage()



function WLink.isInterwiki( attempt )
    -- Does attempt match an interwiki link?
    -- Precondition:
    --     attempt  -- string, with
    -- Postcondition:
    --     Returns  boolean
    local r = false;
    return r;
end -- WLink.isInterwiki()



function WLink.isTitledLink( attempt )
    -- Does attempt match a titled link?
    -- Precondition:
    --     attempt  -- string, with
    -- Postcondition:
    --     Returns  boolean
    local r = false;
    local i = attempt:find( "[", 1, true );
    if i then
        local c;
        local s = attempt:sub( i );
        if s:byte( 2, 2 ) == 91 then
            s = extractWikilink( s );
            c = "|";
        else
            s = extractExtlink( s );
            c = "%s";
        end
        if s then
            if s:find( c, 2 ) then
                r = true;
            end
        end
    end
    return r;
end -- WLink.isTitledLink()



function WLink.isValidLink( attempt )
    -- Does attempt match a link?
    -- Precondition:
    --     attempt  -- string, with
    -- Postcondition:
    --     Returns  boolean
    local s, r = WLink.getTarget( attempt );
    if r then
        r = true;
    end
    return r;
end -- WLink.isValidLink()



function WLink.isWikilink( attempt )
    -- Does attempt match a wikilink?
    -- Precondition:
    --     attempt  -- string, with
    -- Postcondition:
    --     Returns  boolean
    local s, m = WLink.getTarget( attempt );
    return ( m == 2 );
end -- WLink.isWikilink()



local function Template( frame, action, leave )
    -- Run actual code from template transclusion
    -- Precondition:
    --     frame   -- object
    --     action  -- string, with function name
    --     leave   -- true: keep whitespace around
    -- Postcondition:
    --     Return string; might be error message
    local k, v;
    local lucky = true;
    local s = false;
    local r = false;
    for k, v in pairs( frame.args ) do
        if k == 1 then
            if leave then
                s = v;
            else
                s = mw.text.trim( v );
            end
        elseif k ~= "template" then
            lucky = false;
            if r then
                r = r .. "|";
            else
                r = "Unknown parameter: ";
            end
            r = string.format( "%s%s=", r, k );
        end
    end -- for k, v
    if lucky then
        if s then
            lucky, r = pcall( WLink[ action ], s );
        else
            r = "Parameter missing";
            lucky = false;
        end
    end
    if lucky then
        r = r or "";
    else
        r = string.format( "<span class=\"error\">%s</span>", r );
    end
    return r;
end -- Template()



-- Export
local p = { }

p.ansiPercent = function ( frame )
    return Template( frame, "ansiPercent" );
end
p.getBaseTitle = function ( frame )
    return Template( frame, "getBaseTitle" );
end
p.getExtension = function ( frame )
    return Template( frame, "getExtension" );
end
p.getFile = function ( frame )
    return Template( frame, "getFile" );
end
p.getFragment = function ( frame )
    return Template( frame, "getFragment" );
end
p.getLanguage = function ( frame )
    return Template( frame, "getLanguage" );
end
p.getNamespace = function ( frame )
    return Template( frame, "getNamespace" );
end
p.getPlain = function ( frame )
    return Template( frame, "getPlain" );
end
p.getProject = function ( frame )
    return Template( frame, "getProject" );
end
p.getTarget = function ( frame )
    return Template( frame, "getTarget" );
end
p.getTargetPage = function ( frame )
    return Template( frame, "getTargetPage" );
end
p.getTitle = function ( frame )
    return Template( frame, "getTitle" );
end
p.getInterwiki = function ( frame )
    return Template( frame, "getInterwiki" );
end
p.isBracketedLink = function ( frame )
    return Template( frame, "isBracketedLink" );
end
p.isBracketedURL = function ( frame )
    return Template( frame, "isBracketedURL" );
end
p.isExternalLink = function ( frame )
    return Template( frame, "isExternalLink" );
end
p.isInterlanguage = function ( frame )
    return Template( frame, "isInterlanguage" );
end
p.isInterwiki = function ( frame )
    return Template( frame, "isInterwiki" );
end
p.isTitledLink = function ( frame )
    return Template( frame, "isTitledLink" );
end
p.isValidLink = function ( frame )
    return Template( frame, "isValidLink" );
end
p.isWeblink = function ( frame )
    return Template( frame, "isWeblink" );
end
p.isWikilink = function ( frame )
    return Template( frame, "isWikilink" );
end
p.WLink = function ()
    return WLink;
end

return p