<?xml version="1.0"?>
<feed xmlns="http://www.w3.org/2005/Atom" xml:lang="en">
	<id>http://ml.sayahna.org/index.php?action=history&amp;feed=atom&amp;title=MediaWiki%3AGadget-twinkleunlink.js</id>
	<title>MediaWiki:Gadget-twinkleunlink.js - Revision history</title>
	<link rel="self" type="application/atom+xml" href="http://ml.sayahna.org/index.php?action=history&amp;feed=atom&amp;title=MediaWiki%3AGadget-twinkleunlink.js"/>
	<link rel="alternate" type="text/html" href="http://ml.sayahna.org/index.php?title=MediaWiki:Gadget-twinkleunlink.js&amp;action=history"/>
	<updated>2026-04-30T21:16:13Z</updated>
	<subtitle>Revision history for this page on the wiki</subtitle>
	<generator>MediaWiki 1.31.5</generator>
	<entry>
		<id>http://ml.sayahna.org/index.php?title=MediaWiki:Gadget-twinkleunlink.js&amp;diff=8139&amp;oldid=prev</id>
		<title>Cvr: 1 revision</title>
		<link rel="alternate" type="text/html" href="http://ml.sayahna.org/index.php?title=MediaWiki:Gadget-twinkleunlink.js&amp;diff=8139&amp;oldid=prev"/>
		<updated>2014-05-03T06:14:34Z</updated>

		<summary type="html">&lt;p&gt;1 revision&lt;/p&gt;
&lt;table class=&quot;diff diff-contentalign-left&quot; data-mw=&quot;interface&quot;&gt;
				&lt;tr class=&quot;diff-title&quot; lang=&quot;en&quot;&gt;
				&lt;td colspan=&quot;1&quot; style=&quot;background-color: #fff; color: #222; text-align: center;&quot;&gt;← Older revision&lt;/td&gt;
				&lt;td colspan=&quot;1&quot; style=&quot;background-color: #fff; color: #222; text-align: center;&quot;&gt;Revision as of 06:14, 3 May 2014&lt;/td&gt;
				&lt;/tr&gt;&lt;tr&gt;&lt;td colspan=&quot;2&quot; class=&quot;diff-notice&quot; lang=&quot;en&quot;&gt;&lt;div class=&quot;mw-diff-empty&quot;&gt;(No difference)&lt;/div&gt;
&lt;/td&gt;&lt;/tr&gt;&lt;/table&gt;</summary>
		<author><name>Cvr</name></author>
		
	</entry>
	<entry>
		<id>http://ml.sayahna.org/index.php?title=MediaWiki:Gadget-twinkleunlink.js&amp;diff=8138&amp;oldid=prev</id>
		<title>AzaToth: v2.0-556-g0beacc0: use .utc() for timestamps and format them the sme way as the wiki does</title>
		<link rel="alternate" type="text/html" href="http://ml.sayahna.org/index.php?title=MediaWiki:Gadget-twinkleunlink.js&amp;diff=8138&amp;oldid=prev"/>
		<updated>2013-07-13T18:10:00Z</updated>

		<summary type="html">&lt;p&gt;v2.0-556-g0beacc0: use .utc() for timestamps and format them the sme way as the wiki does&lt;/p&gt;
&lt;p&gt;&lt;b&gt;New page&lt;/b&gt;&lt;/p&gt;&lt;div&gt;//&amp;lt;nowiki&amp;gt;&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
(function($){&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
/*&lt;br /&gt;
 ****************************************&lt;br /&gt;
 *** twinkleunlink.js: Unlink module&lt;br /&gt;
 ****************************************&lt;br /&gt;
 * Mode of invocation:     Tab (&amp;quot;Unlink&amp;quot;)&lt;br /&gt;
 * Active on:              Non-special pages&lt;br /&gt;
 * Config directives in:   TwinkleConfig&lt;br /&gt;
 */&lt;br /&gt;
&lt;br /&gt;
Twinkle.unlink = function twinkleunlink() {&lt;br /&gt;
	if( mw.config.get('wgNamespaceNumber') &amp;lt; 0 ) {&lt;br /&gt;
		return;&lt;br /&gt;
	}&lt;br /&gt;
	Twinkle.addPortletLink( Twinkle.unlink.callback, &amp;quot;Unlink&amp;quot;, &amp;quot;tw-unlink&amp;quot;, &amp;quot;Unlink backlinks&amp;quot; );&lt;br /&gt;
};&lt;br /&gt;
&lt;br /&gt;
Twinkle.unlink.getChecked2 = function twinkleunlinkGetChecked2( nodelist ) {&lt;br /&gt;
	if( !( nodelist instanceof NodeList ) &amp;amp;&amp;amp; !( nodelist instanceof HTMLCollection ) ) {&lt;br /&gt;
		return nodelist.checked ? [ nodelist.values ] : [];&lt;br /&gt;
	}&lt;br /&gt;
	var result = [];&lt;br /&gt;
	for(var i  = 0; i &amp;lt; nodelist.length; ++i ) {&lt;br /&gt;
		if( nodelist[i].checked ) {&lt;br /&gt;
			result.push( nodelist[i].values );&lt;br /&gt;
		}&lt;br /&gt;
	}&lt;br /&gt;
	return result;&lt;br /&gt;
};&lt;br /&gt;
&lt;br /&gt;
// the parameter is used when invoking unlink from admin speedy&lt;br /&gt;
Twinkle.unlink.callback = function(presetReason) {&lt;br /&gt;
	var Window = new Morebits.simpleWindow( 800, 400 );&lt;br /&gt;
	Window.setTitle( &amp;quot;Unlink backlinks&amp;quot; + (mw.config.get('wgNamespaceNumber') === 6 ? &amp;quot; and file usages&amp;quot; : &amp;quot;&amp;quot;) );&lt;br /&gt;
	Window.setScriptName( &amp;quot;Twinkle&amp;quot; );&lt;br /&gt;
	Window.addFooterLink( &amp;quot;Twinkle help&amp;quot;, &amp;quot;WP:TW/DOC#unlink&amp;quot; );&lt;br /&gt;
&lt;br /&gt;
	var form = new Morebits.quickForm( Twinkle.unlink.callback.evaluate );&lt;br /&gt;
	form.append( {&lt;br /&gt;
		type: 'textarea',&lt;br /&gt;
		name: 'reason',&lt;br /&gt;
		label: 'Reason: ',&lt;br /&gt;
		value: (presetReason ? presetReason : '')&lt;br /&gt;
	} );&lt;br /&gt;
&lt;br /&gt;
	var query;&lt;br /&gt;
	if(mw.config.get('wgNamespaceNumber') === 6) {  // File:&lt;br /&gt;
		query = {&lt;br /&gt;
			'action': 'query',&lt;br /&gt;
			'list': [ 'backlinks', 'imageusage' ],&lt;br /&gt;
			'bltitle': mw.config.get('wgPageName'),&lt;br /&gt;
			'iutitle': mw.config.get('wgPageName'),&lt;br /&gt;
			'bllimit': Morebits.userIsInGroup( 'sysop' ) ? 5000 : 500, // 500 is max for normal users, 5000 for bots and sysops&lt;br /&gt;
			'iulimit': Morebits.userIsInGroup( 'sysop' ) ? 5000 : 500, // 500 is max for normal users, 5000 for bots and sysops&lt;br /&gt;
			'blnamespace': Twinkle.getPref('unlinkNamespaces'),&lt;br /&gt;
			'iunamespace': Twinkle.getPref('unlinkNamespaces')&lt;br /&gt;
		};&lt;br /&gt;
	} else {&lt;br /&gt;
		query = {&lt;br /&gt;
			'action': 'query',&lt;br /&gt;
			'list': 'backlinks',&lt;br /&gt;
			'bltitle': mw.config.get('wgPageName'),&lt;br /&gt;
			'blfilterredir': 'nonredirects',&lt;br /&gt;
			'bllimit': Morebits.userIsInGroup( 'sysop' ) ? 5000 : 500, // 500 is max for normal users, 5000 for bots and sysops&lt;br /&gt;
			'blnamespace': Twinkle.getPref('unlinkNamespaces')&lt;br /&gt;
		};&lt;br /&gt;
	}&lt;br /&gt;
	var wikipedia_api = new Morebits.wiki.api( 'Grabbing backlinks', query, Twinkle.unlink.callbacks.display.backlinks );&lt;br /&gt;
	wikipedia_api.params = { form: form, Window: Window, image: mw.config.get('wgNamespaceNumber') === 6 };&lt;br /&gt;
	wikipedia_api.post();&lt;br /&gt;
&lt;br /&gt;
	var root = document.createElement( 'div' );&lt;br /&gt;
	root.style.padding = '15px';  // just so it doesn't look broken&lt;br /&gt;
	Morebits.status.init( root );&lt;br /&gt;
	wikipedia_api.statelem.status( &amp;quot;loading...&amp;quot; );&lt;br /&gt;
	Window.setContent( root );&lt;br /&gt;
	Window.display();&lt;br /&gt;
};&lt;br /&gt;
&lt;br /&gt;
Twinkle.unlink.callback.evaluate = function twinkleunlinkCallbackEvaluate(event) {&lt;br /&gt;
	Twinkle.unlink.backlinksdone = 0;&lt;br /&gt;
	Twinkle.unlink.imageusagedone = 0;&lt;br /&gt;
&lt;br /&gt;
	function processunlink(pages, imageusage) {&lt;br /&gt;
		var statusIndicator = new Morebits.status((imageusage ? 'Unlinking instances of file usage' : 'Unlinking backlinks'), '0%');&lt;br /&gt;
		var total = pages.length;  // removing doubling of this number - no apparent reason for it&lt;br /&gt;
&lt;br /&gt;
		Morebits.wiki.addCheckpoint();&lt;br /&gt;
&lt;br /&gt;
		if( !pages.length ) {&lt;br /&gt;
			statusIndicator.info( '100% (completed)' );&lt;br /&gt;
			Morebits.wiki.removeCheckpoint();&lt;br /&gt;
			return;&lt;br /&gt;
		}&lt;br /&gt;
&lt;br /&gt;
		// get an edit token&lt;br /&gt;
		var params = { reason: reason, imageusage: imageusage, globalstatus: statusIndicator, current: 0, total: total };&lt;br /&gt;
		for (var i = 0; i &amp;lt; pages.length; ++i)&lt;br /&gt;
		{&lt;br /&gt;
			var myparams = $.extend({}, params);&lt;br /&gt;
			var articlepage = new Morebits.wiki.page(pages[i], 'Unlinking in article &amp;quot;' + pages[i] + '&amp;quot;');&lt;br /&gt;
			articlepage.setCallbackParameters(myparams);&lt;br /&gt;
			articlepage.setBotEdit(true);  // unlink considered a floody operation&lt;br /&gt;
			articlepage.load(imageusage ? Twinkle.unlink.callbacks.unlinkImageInstances : Twinkle.unlink.callbacks.unlinkBacklinks);&lt;br /&gt;
		}&lt;br /&gt;
	}&lt;br /&gt;
&lt;br /&gt;
	var reason = event.target.reason.value;&lt;br /&gt;
	if (!reason) {&lt;br /&gt;
		alert(&amp;quot;You must specify a reason for unlinking.&amp;quot;);&lt;br /&gt;
		return;&lt;br /&gt;
	}&lt;br /&gt;
&lt;br /&gt;
	var backlinks, imageusage;&lt;br /&gt;
	if( event.target.backlinks ) {&lt;br /&gt;
		backlinks = Twinkle.unlink.getChecked2(event.target.backlinks);&lt;br /&gt;
	}&lt;br /&gt;
	if( event.target.imageusage ) {&lt;br /&gt;
		imageusage = Twinkle.unlink.getChecked2(event.target.imageusage);&lt;br /&gt;
	}&lt;br /&gt;
&lt;br /&gt;
	Morebits.simpleWindow.setButtonsEnabled( false );&lt;br /&gt;
	Morebits.status.init( event.target );&lt;br /&gt;
	Morebits.wiki.addCheckpoint();&lt;br /&gt;
	if (backlinks) {&lt;br /&gt;
		processunlink(backlinks, false);&lt;br /&gt;
	}&lt;br /&gt;
	if (imageusage) {&lt;br /&gt;
		processunlink(imageusage, true);&lt;br /&gt;
	}&lt;br /&gt;
	Morebits.wiki.removeCheckpoint();&lt;br /&gt;
};&lt;br /&gt;
&lt;br /&gt;
Twinkle.unlink.backlinksdone = 0;&lt;br /&gt;
Twinkle.unlink.imageusagedone = 0;&lt;br /&gt;
&lt;br /&gt;
Twinkle.unlink.callbacks = {&lt;br /&gt;
	display: {&lt;br /&gt;
		backlinks: function twinkleunlinkCallbackDisplayBacklinks(apiobj) {&lt;br /&gt;
			var xmlDoc = apiobj.responseXML;&lt;br /&gt;
			var havecontent = false;&lt;br /&gt;
			var list, namespaces, i;&lt;br /&gt;
&lt;br /&gt;
			if( apiobj.params.image ) {&lt;br /&gt;
				var imageusage = $(xmlDoc).find('query imageusage iu');&lt;br /&gt;
				list = [];&lt;br /&gt;
				for ( i = 0; i &amp;lt; imageusage.length; ++i ) {&lt;br /&gt;
					var usagetitle = imageusage[i].getAttribute('title');&lt;br /&gt;
					list.push( { label: usagetitle, value: usagetitle, checked: true } );&lt;br /&gt;
				}&lt;br /&gt;
				if (!list.length)&lt;br /&gt;
				{&lt;br /&gt;
					apiobj.params.form.append( { type: 'div', label: 'No instances of file usage found.' } );&lt;br /&gt;
				}&lt;br /&gt;
				else&lt;br /&gt;
				{&lt;br /&gt;
					apiobj.params.form.append( { type:'header', label: 'File usage' } );&lt;br /&gt;
					namespaces = [];&lt;br /&gt;
					$.each(Twinkle.getPref('unlinkNamespaces'), function(k, v) {&lt;br /&gt;
						namespaces.push(Morebits.wikipedia.namespacesFriendly[v]);&lt;br /&gt;
					});&lt;br /&gt;
					apiobj.params.form.append( {&lt;br /&gt;
						type: 'div',&lt;br /&gt;
						label: &amp;quot;Selected namespaces: &amp;quot; + namespaces.join(', '),&lt;br /&gt;
						tooltip: &amp;quot;You can change this with your Twinkle preferences, at [[WP:TWPREFS]]&amp;quot;&lt;br /&gt;
					});&lt;br /&gt;
					if ($(xmlDoc).find('query-continue').length) {&lt;br /&gt;
						apiobj.params.form.append( {&lt;br /&gt;
							type: 'div',&lt;br /&gt;
							label: &amp;quot;First &amp;quot; + list.length.toString() + &amp;quot; file usages shown.&amp;quot;&lt;br /&gt;
						});&lt;br /&gt;
					}&lt;br /&gt;
					apiobj.params.form.append( {&lt;br /&gt;
						type: 'checkbox',&lt;br /&gt;
						name: 'imageusage',&lt;br /&gt;
						list: list&lt;br /&gt;
					} );&lt;br /&gt;
					havecontent = true;&lt;br /&gt;
				}&lt;br /&gt;
			}&lt;br /&gt;
&lt;br /&gt;
			var backlinks = $(xmlDoc).find('query backlinks bl');&lt;br /&gt;
			if( backlinks.length &amp;gt; 0 ) {&lt;br /&gt;
				list = [];&lt;br /&gt;
				for ( i = 0; i &amp;lt; backlinks.length; ++i ) {&lt;br /&gt;
					var title = backlinks[i].getAttribute('title');&lt;br /&gt;
					list.push( { label: title, value: title, checked: true } );&lt;br /&gt;
				}&lt;br /&gt;
				apiobj.params.form.append( { type:'header', label: 'Backlinks' } );&lt;br /&gt;
				namespaces = [];&lt;br /&gt;
				$.each(Twinkle.getPref('unlinkNamespaces'), function(k, v) {&lt;br /&gt;
					namespaces.push(Morebits.wikipedia.namespacesFriendly[v]);&lt;br /&gt;
				});&lt;br /&gt;
				apiobj.params.form.append( {&lt;br /&gt;
					type: 'div',&lt;br /&gt;
					label: &amp;quot;Selected namespaces: &amp;quot; + namespaces.join(', '),&lt;br /&gt;
					tooltip: &amp;quot;You can change this with your Twinkle preferences, at [[WP:TWPREFS]]&amp;quot;&lt;br /&gt;
				});&lt;br /&gt;
				if ($(xmlDoc).find('query-continue').length) {&lt;br /&gt;
					apiobj.params.form.append( {&lt;br /&gt;
						type: 'div',&lt;br /&gt;
						label: &amp;quot;First &amp;quot; + list.length.toString() + &amp;quot; backlinks shown.&amp;quot;&lt;br /&gt;
					});&lt;br /&gt;
				}&lt;br /&gt;
				apiobj.params.form.append( {&lt;br /&gt;
					type: 'checkbox',&lt;br /&gt;
					name: 'backlinks',&lt;br /&gt;
					list: list&lt;br /&gt;
				});&lt;br /&gt;
				havecontent = true;&lt;br /&gt;
			}&lt;br /&gt;
			else&lt;br /&gt;
			{&lt;br /&gt;
				apiobj.params.form.append( { type: 'div', label: 'No backlinks found.' } );&lt;br /&gt;
			}&lt;br /&gt;
&lt;br /&gt;
			if (havecontent) {&lt;br /&gt;
				apiobj.params.form.append( { type:'submit' } );&lt;br /&gt;
			}&lt;br /&gt;
&lt;br /&gt;
			var result = apiobj.params.form.render();&lt;br /&gt;
			apiobj.params.Window.setContent( result );&lt;br /&gt;
		}&lt;br /&gt;
	},&lt;br /&gt;
	unlinkBacklinks: function twinkleunlinkCallbackUnlinkBacklinks(pageobj) {&lt;br /&gt;
		var text, oldtext;&lt;br /&gt;
		text = oldtext = pageobj.getPageText();&lt;br /&gt;
		var params = pageobj.getCallbackParameters();&lt;br /&gt;
&lt;br /&gt;
		var wikiPage = new Morebits.wikitext.page(text);&lt;br /&gt;
		wikiPage.removeLink(Morebits.pageNameNorm);&lt;br /&gt;
		text = wikiPage.getText();&lt;br /&gt;
		if (text === oldtext) {&lt;br /&gt;
			// Nothing to do, return&lt;br /&gt;
			Twinkle.unlink.callbacks.success(pageobj);&lt;br /&gt;
			Morebits.wiki.actionCompleted();&lt;br /&gt;
			return;&lt;br /&gt;
		}&lt;br /&gt;
&lt;br /&gt;
		pageobj.setPageText(text);&lt;br /&gt;
		pageobj.setEditSummary(&amp;quot;Removing link(s) to \&amp;quot;&amp;quot; + Morebits.pageNameNorm + &amp;quot;\&amp;quot;: &amp;quot; + params.reason + &amp;quot;.&amp;quot; + Twinkle.getPref('summaryAd'));&lt;br /&gt;
		pageobj.setCreateOption('nocreate');&lt;br /&gt;
		pageobj.save(Twinkle.unlink.callbacks.success);&lt;br /&gt;
	},&lt;br /&gt;
	unlinkImageInstances: function twinkleunlinkCallbackUnlinkImageInstances(pageobj) {&lt;br /&gt;
		var text, oldtext;&lt;br /&gt;
		text = oldtext = pageobj.getPageText();&lt;br /&gt;
		var params = pageobj.getCallbackParameters();&lt;br /&gt;
&lt;br /&gt;
		var wikiPage = new Morebits.wikitext.page(text);&lt;br /&gt;
		wikiPage.commentOutImage(mw.config.get('wgTitle'), 'Commented out');&lt;br /&gt;
		text = wikiPage.getText();&lt;br /&gt;
		if (text === oldtext) {&lt;br /&gt;
			// Nothing to do, return&lt;br /&gt;
			Twinkle.unlink.callbacks.success(pageobj);&lt;br /&gt;
			Morebits.wiki.actionCompleted();&lt;br /&gt;
			return;&lt;br /&gt;
		}&lt;br /&gt;
&lt;br /&gt;
		pageobj.setPageText(text);&lt;br /&gt;
		pageobj.setEditSummary(&amp;quot;Commenting out use(s) of file \&amp;quot;&amp;quot; + Morebits.pageNameNorm + &amp;quot;\&amp;quot;: &amp;quot; + params.reason + &amp;quot;.&amp;quot; + Twinkle.getPref('summaryAd'));&lt;br /&gt;
		pageobj.setCreateOption('nocreate');&lt;br /&gt;
		pageobj.save(Twinkle.unlink.callbacks.success);&lt;br /&gt;
	},&lt;br /&gt;
	success: function twinkleunlinkCallbackSuccess(pageobj) {&lt;br /&gt;
		var params = pageobj.getCallbackParameters();&lt;br /&gt;
		var total = params.total;&lt;br /&gt;
		var now = parseInt( 100 * (params.imageusage ? ++(Twinkle.unlink.imageusagedone) : ++(Twinkle.unlink.backlinksdone))/total, 10 ) + '%';&lt;br /&gt;
		params.globalstatus.update( now );&lt;br /&gt;
		if((params.imageusage ? Twinkle.unlink.imageusagedone : Twinkle.unlink.backlinksdone) &amp;gt;= total) {&lt;br /&gt;
			params.globalstatus.info( now + ' (completed)' );&lt;br /&gt;
			Morebits.wiki.removeCheckpoint();&lt;br /&gt;
		}&lt;br /&gt;
	}&lt;br /&gt;
};&lt;br /&gt;
})(jQuery);&lt;br /&gt;
&lt;br /&gt;
&lt;br /&gt;
//&amp;lt;/nowiki&amp;gt;&lt;/div&gt;</summary>
		<author><name>AzaToth</name></author>
		
	</entry>
</feed>