mediawiki-extensions-Scribunto/engines/LuaCommon/lualib/mw.ustring.lua
Brad Jorsch 4dcac2fcd9 Fix mw.ustring.gmatch and patterns with '^'
The Lua manual says this:

 For this function, a '^' at the start of a pattern does not work as an
 anchor, as this would prevent the iteration.

I had interpreted that to mean that a pattern starting with '^' would
never match in gmatch. But further testing reveals that the '^' is just
treated as a literal character: string.gmatch( "foo ^bar baz", "^%a+" )
will match "^bar".

Change-Id: Id91d6ee2db753ce1d6a4f6ae27764691d9e9fdc4
2013-02-14 14:25:55 -05:00

86 lines
2 KiB
Lua

-- Get a fresh copy of the basic ustring
local old_ustring = package.loaded.ustring
package.loaded.ustring = nil
local ustring = require( 'ustring' )
package.loaded.ustring = old_ustring
old_ustring = nil
local util = require 'libraryUtil'
local checkType = util.checkType
local gmatch_init = nil
local gmatch_callback = nil
local function php_gmatch( s, pattern )
checkType( 'gmatch', 1, s, 'string' )
checkType( 'gmatch', 2, pattern, 'string' )
local re, capt = gmatch_init( s, pattern )
local pos = 0
return function()
local ret
pos, ret = gmatch_callback( s, re, capt, pos )
return unpack( ret )
end, nil, nil
end
function ustring.setupInterface( opt )
-- Boilerplate
ustring.setupInterface = nil
-- Set string limits
ustring.maxStringLength = opt.stringLengthLimit
ustring.maxPatternLength = opt.patternLengthLimit
-- Gmatch
if mw_interface.gmatch_callback and mw_interface.gmatch_init then
gmatch_init = mw_interface.gmatch_init
gmatch_callback = mw_interface.gmatch_callback
ustring.gmatch = php_gmatch
end
mw_interface.gmatch_init = nil
mw_interface.gmatch_callback = nil
-- Replace pure-lua implementation with php callbacks
local nargs = {
char = 0,
find = 2,
match = 2,
gsub = 3,
}
for k, v in pairs( mw_interface ) do
local n = nargs[k] or 1
if n == 0 then
ustring[k] = v
else
-- Avoid PHP warnings for missing arguments by checking before
-- calling PHP.
ustring[k] = function ( ... )
if select( '#', ... ) < n then
error( "too few arguments to mw.ustring." .. k, 2 )
end
return v( ... )
end
end
end
mw_interface = nil
-- Replace upper/lower with mw.language versions if available
if mw and mw.language then
local lang = mw.language.getContentLanguage()
ustring.upper = function ( s )
return lang:uc( s )
end
ustring.lower = function ( s )
return lang:lc( s )
end
end
-- Register this library in the "mw" global
mw = mw or {}
mw.ustring = ustring
package.loaded['mw.ustring'] = ustring
end
return ustring