Module:Mock title/testcases

local mMockTitle = require('Module:Mock title/sandbox') local ScribuntoUnit = require('Module:ScribuntoUnit')

local suite = ScribuntoUnit:new

-- Custom assertion methods

function suite:assertTitlesAreEqual(expected, actual) local properties = { 'prefixedText', 'id', 'exists', 'isRedirect', 'redirectTarget', 'contentModel', }	for _, prop in ipairs(properties) do		self:assertEquals(			expected[prop],			actual[prop],			string.format('mismatch in property "%s"', prop)		) end local deepProperties = {'protectionLevels', 'cascadingProtection'} for _, prop in ipairs(deepProperties) do		self:assertDeepEquals(			expected[prop],			actual[prop],			string.format('mismatch in property "%s"', prop)		) end self:assertEquals(		not not expected.file,		not not actual.file,		string.format( 'expected %s file property; actual %s file property', expected.file and 'has' or 'has no', actual.file and 'has' or 'has no' )	)	if expected.file and actual.file then local fileProperties = { 'exists', 'width', 'height', 'size', 'mimeType', 'length', }		for _, prop in ipairs(fileProperties) do			self:assertEquals(				expected.file[prop],				actual.file[prop],				string.format('mismatch in property "file.%s"', prop)			) end self:assertDeepEquals(			expected.file.pages,			actual.file.pages,			string.format('mismatch in property "%s"', prop)		) end self:assertEquals(		expected:getContent,		actual:getContent,		'mismatch in getContent'	) end

function suite:assertTitlesAreNotEqual(expected, actual) local success, result = pcall(self.assertTitlesAreEqual, self, expected, actual) if success then self:fail(string.format( 'Failed to assert that the specified titles are not equal (title: %s)', tostring(expected) ))	end end

-- MockTitle tests

suite['test MockTitle: when no argument table is supplied, an error is raised'] = function (self) self:assertThrows(		function mMockTitle.MockTitle end,		"bad argument #1 to 'MockTitle' (table expected, got nil)"	) end

suite['test MockTitle: when no title argument is supplied, an error is raised'] = function (self) self:assertThrows(		function mMockTitle.MockTitle{} end,		"bad named argument title to 'MockTitle' (string or number expected, got nil)"	) end

local pageNames = { 'Example', 'fr:Example', 'Module:Sandbox', 'Module:Sandbox/subpage', 'mw:Test', 'fr:b:Example', }

for _, pageName in ipairs(pageNames) do	suite[ string.format(			'test MockTitle: when using page name "%s", the prefixedText property equals the page name',			pageName		) ] = function (self) self:assertEquals(pageName, mMockTitle.MockTitle({title = pageName}).prefixedText) end end

local simplePropertyTestData = { {		property = 'id', title = 'Example', value = 123456, },	{		property = 'isRedirect', title = 'Main Page', value = true, },	{		property = 'exists', title = 'Main Page', value = false, },	{		property = 'contentModel', title = 'Main Page', value = 'foo', }, }

for _, testData in ipairs(simplePropertyTestData) do	suite[string.format('test MockTitle: property %s is mocked using the %s option', testData.property, testData.property)] = function (self) local title = mMockTitle.MockTitle({title = testData.title, [testData.property] = testData.value}) self:assertEquals(testData.value, title[testData.property]) end end

suite['test MockTitle: passing a page name to the redirectTarget option causes redirectTarget to be a MockTitle object with that page name'] = function (self) local title = mMockTitle.MockTitle({title = 'Example', redirectTarget = 'User:Example'}) self:assertEquals('User:Example', title.redirectTarget.prefixedText) end

suite['test MockTitle: passing an ID to the redirectTarget option causes redirectTarget to be a MockTitle object with that ID'] = function (self) local mainPageId = 15580374 local title = mMockTitle.MockTitle({title = 'Example', redirectTarget = mainPageId}) self:assertEquals(mainPageId, title.redirectTarget.id) end

suite['test MockTitle: passing an options table to the redirectTarget option causes redirectTarget to be a MockTitle object with those options'] = function (self) local title = mMockTitle.MockTitle({title = 'Example', redirectTarget = {title = 'User:Example/common.js', contentModel = 'wikitext'}}) self:assertEquals('User:Example/common.js', title.redirectTarget.prefixedText) self:assertEquals('wikitext', title.redirectTarget.contentModel) end

suite['test MockTitle: passing a MockTitle object to the redirectTarget option causes redirectTarget to be that MockTitle object'] = function (self) local mockRedirectTarget = mMockTitle.MockTitle({title = 'User:Example/common.js', contentModel = 'wikitext'}) local title = mMockTitle.MockTitle({title = 'Example', redirectTarget = mockRedirectTarget}) self:assertEquals('User:Example/common.js', title.redirectTarget.prefixedText) self:assertEquals('wikitext', title.redirectTarget.contentModel) end

local protectionLevelTestData = { {		optionName = 'editProtection', optionValue = 'sysop', expectedProtectionAction = 'edit', },	{		optionName = 'moveProtection', optionValue = 'sysop', expectedProtectionAction = 'move', },	{		optionName = 'createProtection', optionValue = 'sysop', expectedProtectionAction = 'create', },	{		optionName = 'uploadProtection', optionValue = 'sysop', expectedProtectionAction = 'upload', }, }

for _, testData in ipairs(protectionLevelTestData) do	suite[ string.format(			'test MockTitle: when setting option %s to "%s", the protectionLevels table is updated accordingly',			testData.optionName,			testData.optionValue		) ] = function (self) local title = mMockTitle.MockTitle{title = 'Example', [testData.optionName] = testData.optionValue} self:assertEquals(testData.optionValue, title.protectionLevels[testData.expectedProtectionAction][1]) end end

local cascadingProtectionLevelTestData = { {		optionName = 'cascadingEditProtection', optionValue = 'sysop', expectedProtectionAction = 'edit', },	{		optionName = 'cascadingMoveProtection', optionValue = 'sysop', expectedProtectionAction = 'move', },	{		optionName = 'cascadingCreateProtection', optionValue = 'sysop', expectedProtectionAction = 'create', },	{		optionName = 'cascadingUploadProtection', optionValue = 'sysop', expectedProtectionAction = 'upload', }, }

for _, testData in ipairs(cascadingProtectionLevelTestData) do	suite[ string.format(			'test MockTitle: when setting option %s to "%s", '			.. 'and when setting the cascadingProtectionSources option, '			.. 'the cascadingProtection table is updated accordingly',			testData.optionName,			testData.optionValue		) ] = function (self) local title = mMockTitle.MockTitle{ title = 'Example', [testData.optionName] = testData.optionValue, cascadingProtectionSources = {'Example', 'Example 2'}, }		self:assertEquals(			testData.optionValue,			title.cascadingProtection.restrictions[testData.expectedProtectionAction][1]		) self:assertDeepEquals(			{'Example', 'Example 2'},			title.cascadingProtection.sources		) end end

suite['test MockTitle: when a cascading protection argument is given, but no cascading protection sources are given, an error is raised'] = function (self) self:assertThrows(		function mMockTitle.MockTitle{title = 'Example', cascadingEditProtection = 'sysop'} end,		'a cascading protection argument was given but the cascadingProtectionSources argument was missing or empty'	) end

suite['test MockTitle: when a cascading protection argument is given, but the cascading protection sources table is empty, an error is raised'] = function (self) self:assertThrows(		function mMockTitle.MockTitle{title = 'Example', cascadingEditProtection = 'sysop', cascadingProtectionSources = {}} end,		'a cascading protection argument was given but the cascadingProtectionSources argument was missing or empty'	) end

suite['test MockTitle: when cascading protection sources are given, but no cascading protection argument is given, an error is raised'] = function (self) self:assertThrows(		function mMockTitle.MockTitle{title = 'Example', cascadingProtectionSources = {'Example 2', 'Example 3'}} end,		'the cascadingProtectionSources argument was given, but no cascading protection argument was given'	) end

suite['test MockTitle: if the content option is provided, getContent returns the specified string'] = function (self) local title = mMockTitle.MockTitle{title = 'Non-existent page 29dh12yxm', content = 'some wikitext content'} self:assertEquals('some wikitext content', title:getContent) end

local filePropertyTestData = { {		property = 'exists', optionName = 'fileExists', optionValue = true, },	{		property = 'width', optionName = 'fileWidth', optionValue = 123, },	{		property = 'height', optionName = 'fileHeight', optionValue = 456, },	{		property = 'pages', optionName = 'filePages', optionValue = {{height = 800, width = 600}, {height = 800, width = 600}}, },	{		property = 'size', optionName = 'fileSize', optionValue = 1024, },	{		property = 'mimeType', optionName = 'fileMimeType', optionValue = 'image/png', },	{		property = 'length', optionName = 'fileLength', optionValue = 60, }, }

for _, testData in ipairs(filePropertyTestData) do	suite[string.format(			'test MockTitle: when setting option %s to "%s", the file table is updated accordingly',			testData.optionName,			tostring(testData.optionValue)	)] = function(self) local title = mMockTitle.MockTitle{title = 'File:Non-existent hf893bc0.png', [testData.optionName] = testData.optionValue} self:assertEquals(testData.optionValue, title.file[testData.property]) end end

suite['test MockTitle: when setting fileExists in a non-file namespace, no file table is set'] = function(self) local title = mMockTitle.MockTitle{title = 'Non-existent page 34u8wg90bfr', fileExists = true} self:assertEquals(nil, title.file) end

local fileExistsTestData = { {		title = 'Non-existent article tr9w78ebna0', expected = nil, },	{		title = 'Talk:Non-existent talk page 34hdbe0pafj', expected = nil, },	{		title = 	'File:Non-existent file 341gh87fgg8', expected = true, },	{		title = 'Media:Non-existent file pbfhrw3v8d', expected = true, }, }

for _, testData in ipairs(fileExistsTestData) do	suite[ string.format(			'test MockTitle: when using page "%s", the fileExists property is %s',			testData.title,			testData.expected and 'set' or 'not set'		) ] = function (self) local title = mMockTitle.MockTitle({title = testData.title, fileExists = true}) self:assertEquals(testData.expected, title.fileExists) end end

local fallbackPropertyTestData = { {		property = 'id', option = 'id', title = 'Example', },	{		property = 'isRedirect', option = 'isRedirect', title = 'WP:ANI', },	{		property = 'exists', option = 'exists', title = 'Non-existent title f292umz0tyi', },	{		property = 'contentModel', option = 'contentModel', title = 'User:Example/common.js', },	{		property = 'redirectTarget', option = 'redirectTarget', title = 'WP:ANI', },	{		property = 'protectionLevels', option = 'editProtection', title = 'Main Page', },	{		property = 'redirectTarget', option = 'redirectTarget', title = 'WP:ANI', },	{		property = 'cascadingProtection', option = 'cascadingEditProtection', title = 'Main Page', },	{		property = 'cascadingProtection', option = 'cascadingProtectionSources', title = 'Main Page', }, }

for _, testData in ipairs(fallbackPropertyTestData) do	suite[string.format('test MockTitle: if no %s option is specified, the real %s value is used', testData.option, testData.property)] = function (self) suite:assertDeepEquals(			mw.title.new(testData.title)[testData.property],			mMockTitle.MockTitle{title = testData.title}[testData.property]		) end end

suite['test MockTitle: if no content option is specified, getContent returns the the real content'] = function (self) suite:assertEquals(		mw.title.new('Main Page'):getContent,		mMockTitle.MockTitle{title = 'Main Page'}:getContent	) end

suite['test MockTitle: the content property is not shared between mock objects'] = function (self) suite:assertNotEquals(		mMockTitle.MockTitle{title = 'Foo', content = 'Bar'}:getContent,		mMockTitle.MockTitle{title = 'Foo', content = 'Baz'}:getContent	) end

-- patchTitleObject tests

suite['test patchTitleObject: patchTitleObject returns an equivalent object to MockTitle when used on the same title'] = function (self) suite:assertTitlesAreEqual(		mMockTitle.MockTitle{			title = 'Main Page',			isRedirect = true,			redirectTarget = 'Wikipedia:Village stocks',			content = '#REDIRECT: Village stocks',		},		mMockTitle.patchTitleObject( mw.title.new('Main Page'), {				isRedirect = true, redirectTarget = 'Wikipedia:Village stocks', content = '#REDIRECT: Village stocks', }		)	) end

suite['test patchTitleObject: title arguments are ignored'] = function (self) self:assertEquals(		'User:Example',		mMockTitle.patchTitleObject( mw.title.new('User:Example'), {title = 'Wikipedia:Sandbox'} ).prefixedText	) end

-- Tests for registering/deregistering mock titles

local MOCK_WP_SANDBOX_ARGS = { title = 'Wikipedia:Sandbox', content = 'Some random content: zbS8mJ31l8eY', isRedirect = true -- Cannot be true for a real page with the above content, so we can prove it's a mock } local MOCK_WP_SANDBOX = mMockTitle.MockTitle(MOCK_WP_SANDBOX_ARGS)

local MOCK_MAIN_PAGE_ARGS = { title = 'Main Page', content = 'Mock main page content: 38fgbhqwu8adb', } local MOCK_MAIN_PAGE = mMockTitle.MockTitle(MOCK_MAIN_PAGE_ARGS)

function suite:tearDownRegistrationTests mMockTitle.clearAllMockTitles end

suite['test registerMockTitle: real titles are used during patching when no mocks are registered'] = function (self) -- Setup local realTitle = mw.title.new('Wikipedia:Sandbox')

-- Test mMockTitle.patchTitleConstructors(function 		self:assertTitlesAreEqual( mw.title.new(MOCK_WP_SANDBOX_ARGS.title), realTitle )	end) -- Teardown self:tearDownRegistrationTests end

local registerMockTitleTestData = { {argType = 'option table', arg = MOCK_WP_SANDBOX_ARGS}, {argType = 'mock title', arg = MOCK_WP_SANDBOX}, }

for _, testData in ipairs(registerMockTitleTestData) do	suite[string.format(		'test registerMockTitle: mocks are registered when specified using %s',		testData.argType	)] = function (self) -- Setup mMockTitle.registerMockTitle(testData.arg)

-- Test mMockTitle.patchTitleConstructors(function 			self:assertTitlesAreEqual( mw.title.new(MOCK_WP_SANDBOX_ARGS.title), MOCK_WP_SANDBOX )		end) -- Teardown self:tearDownRegistrationTests end end

for _, testData in ipairs(registerMockTitleTestData) do	suite[string.format(		'test registerMockCurrentTitle: mocks are registered when specified using %s',		testData.argType	)] = function (self) -- Setup mMockTitle.registerMockCurrentTitle(testData.arg)

-- Test mMockTitle.patchTitleConstructors(function 			self:assertTitlesAreEqual( mw.title.getCurrentTitle, MOCK_WP_SANDBOX )		end) -- Teardown self:tearDownRegistrationTests end end

function suite:setUpDeregistrationTests mMockTitle.registerMockTitles(MOCK_WP_SANDBOX_ARGS,	MOCK_MAIN_PAGE_ARGS) mMockTitle.registerMockCurrentTitle(MOCK_WP_SANDBOX_ARGS) end

suite['test deregisterMockTitle: previously registered titles are not deregistered if a deregistration function is not called'] = function (self) -- Setup self:setUpDeregistrationTests

-- Test mMockTitle.patchTitleConstructors(function 		self:assertTitlesAreEqual( mw.title.new(MOCK_WP_SANDBOX_ARGS.title), MOCK_WP_SANDBOX )	end)

-- Teardown self:tearDownRegistrationTests end

local deregisterMockTitleTestData = { {argType = 'title', arg = MOCK_WP_SANDBOX_ARGS.title}, {argType = 'args table', arg = MOCK_WP_SANDBOX_ARGS}, {argType = 'ID', arg = MOCK_WP_SANDBOX.id}, {argType = 'title object', arg = mw.title.new(MOCK_WP_SANDBOX_ARGS.title)}, {argType = 'mock title object', arg = MOCK_WP_SANDBOX}, }

for _, testData in ipairs(deregisterMockTitleTestData) do	suite[ string.format(			'test deregisterMockTitle: previously registered titles are deregistered when specified by %s',			testData.argType		) ] = function (self) -- Setup self:setUpDeregistrationTests local realTitle = mw.title.new(MOCK_WP_SANDBOX_ARGS.title) mMockTitle.deregisterMockTitle(testData.arg)

-- Test mMockTitle.patchTitleConstructors(function 			self:assertTitlesAreEqual( mw.title.new(MOCK_WP_SANDBOX_ARGS.title), realTitle )		end)

-- Teardown self:tearDownRegistrationTests end end

suite['test deregisterMockCurrentTitle: the previously registered current title is not deregistered if a deregistration function is not called'] = function (self) -- Setup self:setUpDeregistrationTests

-- Test mMockTitle.patchTitleConstructors(function 		self:assertTitlesAreEqual(mw.title.getCurrentTitle, MOCK_WP_SANDBOX)	end)

-- Teardown self:tearDownRegistrationTests end

suite['test deregisterMockCurrentTitle: the previously registered current title is deregistered if deregisterMockCurrentTitle is called'] = function (self) -- Setup self:setUpDeregistrationTests local realTitle = mw.title.getCurrentTitle mMockTitle.deregisterMockCurrentTitle

-- Test mMockTitle.patchTitleConstructors(function 		self:assertTitlesAreEqual(mw.title.getCurrentTitle, realTitle)	end)

-- Teardown self:tearDownRegistrationTests end

local registerMockTitlesTestData = { {argType = 'option table', args = {MOCK_WP_SANDBOX_ARGS, MOCK_MAIN_PAGE_ARGS}}, {argType = 'mock title', args = {MOCK_WP_SANDBOX, MOCK_MAIN_PAGE}}, }

for _, testData in ipairs(registerMockTitlesTestData) do	suite[string.format(		'test registerMockTitles: mocks are registered when specified using %s',		testData.argType	)] = function (self) -- Setup mMockTitle.registerMockTitles(unpack(testData.args))

-- Test mMockTitle.patchTitleConstructors(function 			self:assertTitlesAreEqual( mw.title.new(MOCK_WP_SANDBOX_ARGS.title), MOCK_WP_SANDBOX )			self:assertTitlesAreEqual( mw.title.new(MOCK_MAIN_PAGE_ARGS.title), MOCK_MAIN_PAGE )		end) -- Teardown self:tearDownRegistrationTests end end

local deregisterMockTitlesTestData = { {		argType = 'title', args = {MOCK_WP_SANDBOX_ARGS.title, MOCK_MAIN_PAGE_ARGS.title}, },	{argType = 'args table', args = {MOCK_WP_SANDBOX_ARGS, MOCK_MAIN_PAGE_ARGS}}, {argType = 'ID', args = {MOCK_WP_SANDBOX.id, MOCK_MAIN_PAGE.id}}, {		argType = 'title object', args = { mw.title.new(MOCK_WP_SANDBOX_ARGS.title), mw.title.new(MOCK_MAIN_PAGE_ARGS.title), },	},	{argType = 'mock title object', args = {MOCK_WP_SANDBOX, MOCK_MAIN_PAGE}}, }

for _, testData in ipairs(deregisterMockTitlesTestData) do	suite[ string.format(			'test deregisterMockTitle: previously registered titles are deregistered when specified by %s',			testData.argType		) ] = function (self) -- Setup self:setUpDeregistrationTests local realSandboxTitle = mw.title.new(MOCK_WP_SANDBOX_ARGS.title) local realMainPageTitle = mw.title.new(MOCK_MAIN_PAGE_ARGS.title) mMockTitle.deregisterMockTitles(unpack(testData.args))

-- Test mMockTitle.patchTitleConstructors(function 			self:assertTitlesAreEqual( mw.title.new(MOCK_WP_SANDBOX_ARGS.title), realSandboxTitle )			self:assertTitlesAreEqual( mw.title.new(MOCK_MAIN_PAGE_ARGS.title), realMainPageTitle )		end)

-- Teardown self:tearDownRegistrationTests end end

suite['test clearMockTitleRegistry: all mock titles are cleared'] = function (self) -- Setup self:setUpDeregistrationTests local realSandboxTitle = mw.title.new(MOCK_WP_SANDBOX_ARGS.title) local realMainPageTitle = mw.title.new(MOCK_MAIN_PAGE_ARGS.title) mMockTitle.clearMockTitleRegistry

-- Test mMockTitle.patchTitleConstructors(function 		self:assertTitlesAreEqual( mw.title.new(MOCK_WP_SANDBOX_ARGS.title), realSandboxTitle )		self:assertTitlesAreEqual( mw.title.new(MOCK_MAIN_PAGE_ARGS.title), realMainPageTitle )	end)

-- Teardown self:tearDownRegistrationTests end

suite['test clearAllMockTitles: all registered titles are deregistered when clearAllMockTitles is called'] = function (self) -- Setup self:setUpDeregistrationTests local realSandboxTitle = mw.title.new(MOCK_WP_SANDBOX_ARGS.title) local realMainPageTitle = mw.title.new(MOCK_MAIN_PAGE_ARGS.title) local realCurrentTitle = mw.title.getCurrentTitle mMockTitle.clearAllMockTitles

-- Test mMockTitle.patchTitleConstructors(function 		self:assertTitlesAreEqual( mw.title.new(MOCK_WP_SANDBOX_ARGS.title), realSandboxTitle )		self:assertTitlesAreEqual( mw.title.new(MOCK_MAIN_PAGE_ARGS.title), realMainPageTitle )		self:assertTitlesAreEqual(mw.title.getCurrentTitle, realCurrentTitle)	end)

-- Teardown self:tearDownRegistrationTests end

suite['test registered mocks do not share content with standalone mocks when title constructors are patched'] = function (self) mMockTitle.registerMockTitle{title = 'Wikipedia:Sandbox', content = 'Foo'} mMockTitle.patchTitleConstructors(function 		self:assertTitlesAreNotEqual( mw.title.new('Wikipedia:Sandbox'), mMockTitle.MockTitle{title = 'Wikipedia:Sandbox', content = 'Bar'} )	end) self:tearDownRegistrationTests end

-- Tests for patching functions

local patchingFunctionTestArgs = { {		patchFuncName = 'patchTitleNew', constructorName = 'new', constructorArgs = {'Wikipedia:Sandbox'}, expectedMockTitle = MOCK_WP_SANDBOX, expectedRealTitle = mw.title.new('Wikipedia:Sandbox'), },	{		patchFuncName = 'patchMakeTitle', constructorName = 'makeTitle', constructorArgs = {4, 'Sandbox'}, expectedMockTitle = MOCK_WP_SANDBOX, expectedRealTitle = mw.title.new('Wikipedia:Sandbox'), },	{		patchFuncName = 'patchGetCurrentTitle', constructorName = 'getCurrentTitle', constructorArgs = {}, expectedMockTitle = MOCK_WP_SANDBOX, expectedRealTitle = mw.title.getCurrentTitle, }, }

for _, testData in ipairs(patchingFunctionTestArgs) do	suite[ string.format(			'test %s: %s is patched when the func parameter is run',			testData.patchFuncName,			testData.constructorName		) ] = function (self) self:setUpDeregistrationTests mMockTitle[testData.patchFuncName](function 			self:assertTitlesAreEqual( mw.title[testData.constructorName](unpack(testData.constructorArgs)), testData.expectedMockTitle )		end) self:tearDownRegistrationTests end

suite[ string.format(			'test %s: %s is not patched before the function is run',			testData.patchFuncName,			testData.constructorName		) ] = function (self) -- Setup self:setUpDeregistrationTests local realSandboxTitle = mw.title.new('Wikipedia:Sandbox') self:assertTitlesAreEqual(			mw.title[testData.constructorName](unpack(testData.constructorArgs)),			testData.expectedRealTitle		) self:tearDownRegistrationTests end

suite[ string.format(			'test %s: %s is not patched after the function is run',			testData.patchFuncName,			testData.constructorName		) ] = function (self) -- Setup self:setUpDeregistrationTests local realSandboxTitle = mw.title.new('Wikipedia:Sandbox') mMockTitle[testData.patchFuncName](function end) -- Test self:assertTitlesAreEqual(			mw.title[testData.constructorName](unpack(testData.constructorArgs)),			testData.expectedRealTitle		) -- Teardown self:tearDownRegistrationTests end end

suite['test patchTitleConstructors: all title constructors are patched when the func parameter is run'] = function (self) self:setUpDeregistrationTests mMockTitle.patchTitleConstructors(function 		self:assertTitlesAreEqual( mw.title.new(MOCK_WP_SANDBOX_ARGS.title), MOCK_WP_SANDBOX )		self:assertTitlesAreEqual( mw.title.new(MOCK_MAIN_PAGE_ARGS.title), MOCK_MAIN_PAGE )		self:assertTitlesAreEqual(mw.title.getCurrentTitle, MOCK_WP_SANDBOX)	end) self:tearDownRegistrationTests end

suite['test patchTitleConstructors: title constructors are not patched after the function is run'] = function (self) -- Setup self:setUpDeregistrationTests local realSandboxTitle = mw.title.new('Wikipedia:Sandbox') local realCurrentTitle = mw.title.getCurrentTitle mMockTitle.patchTitleConstructors(function end)

-- Test self:assertTitlesAreEqual(		mw.title.new('Wikipedia:Sandbox'),		realSandboxTitle	) self:assertTitlesAreEqual(		mw.title.makeTitle(4, 'Sandbox'),		realSandboxTitle	) self:assertTitlesAreEqual(mw.title.getCurrentTitle, realCurrentTitle)

-- Teardown self:tearDownRegistrationTests end

local patchingFuncNames = { 'patchTitleNew', 'patchMakeTitle', 'patchGetCurrentTitle', 'patchTitleConstructors', }

for _, patchFuncName in ipairs(patchingFuncNames) do	suite[string.format('test %s: varargs are passed as arguments to the func parameter', patchFuncName)] = function (self) mMockTitle[patchFuncName](			function (a, b, c)				self:assertEquals('foo', a)				self:assertEquals('bar', b)				self:assertEquals('baz', c)			end,			'foo',			'bar',			'baz'		) end suite[string.format('test %s: the result of func is returned', patchFuncName)] = function (self) local result = mMockTitle[patchFuncName](function 			return 'some value'		end) self:assertEquals('some value', result) end end

return suite