MediaWiki:Gadget-slurpInterwiki.js
Jump to navigation
Jump to search
Note: After publishing, you may have to bypass your browser's cache to see the changes.
- Firefox / Safari: Hold Shift while clicking Reload, or press either Ctrl-F5 or Ctrl-R (⌘-R on a Mac)
- Google Chrome: Press Ctrl-Shift-R (⌘-Shift-R on a Mac)
- Internet Explorer / Edge: Hold Ctrl while clicking Refresh, or press Ctrl-F5
- Opera: Press Ctrl-F5.
/* _____________________________________________________________________________________________________
* | |
* | === WARNING: GLOBAL GADGET FILE === |
* | Changes to this page affect many users. |
* | Please discuss changes on the talk page or on [[MediaWiki talk:Gadgets-definition]] before editing. |
* |____________________________________________________________________________________________________ |
*
*/
( function ( mw, $ ) {
'use strict';
var itemId = mw.config.get( 'wbEntityId' );
if ( !itemId || mw.config.get( 'wgNamespaceNumber' ) !== 0 ||
!mw.config.get( 'wbIsEditView' ) ||
!mw.config.get( 'wgIsProbablyEditable' )
) {
return;
}
var i18nData = require( './slurpInterwiki-i18n.json' );
var chain = mw.language.getFallbackLanguageChain(),
len = chain.length,
messages = {},
i;
for ( i = len - 1; i >= 0; i-- ) {
if ( i18nData.hasOwnProperty( chain[ i ] ) ) {
$.extend( messages, i18nData[ chain[ i ] ] );
}
}
mw.messages.set( messages );
var specialWikis = {
'commonswiki': 'commons',
'metawiki': 'meta',
'mediawikiwiki': 'mediawiki',
'specieswiki': 'species',
'wikidatawiki': 'wikidata'
};
var notification = mw.util.getParamValue( 'slurpnotif' );
if ( notification !== null ) {
var notifications = notification.split( '|' );
for ( i in notifications ) {
mw.notify( mw.message( notifications[ i ] ) );
}
}
/**
* Return the language code from the ID of the Wiki
*/
function getLanguageCodeFromWikiId( wiki ) {
var splited = wiki.match( /^(.*)wik[it][a-z]*$/i );
if ( !splited[ 1 ] ) {
return '';
} else {
return splited[ 1 ].replace( /_/g, '-' );
}
}
/**
* Return the site group from the ID of the Wiki
*/
function getGroupFromWikiId( wiki ) {
if ( wiki.match( /^.*wikivoyage$/i ) ) {
return 'wikivoyage';
} else if ( wiki.match( /^.*wikisource$/i ) ) {
return 'wikisource';
} else if ( wiki.match( /^.*wikiquote$/i ) ) {
return 'wikiquote';
} else if ( wiki.match( /^.*wikinews$/i ) ) {
return 'wikinews';
} else if ( wiki.match( /^.*wikibooks$/i ) ) {
return 'wikibooks';
} else if ( wiki.match( /^.*wikiversity$/i ) ) {
return 'wikiversity';
} else if ( wiki.match( /^.*wiktionary$/i ) ) {
return 'wiktionary';
} else if ( wiki.match( /^.*wiki$/i ) ) {
return 'wikipedia';
} else { // TODO other groups
return '';
}
}
/**
* Called on error
*/
function onError() {
$.removeSpinner( 'slurpInterwiki' );
$( '#slurpInterwiki-button-import' ).button( 'option', 'disabled', false );
}
/**
* Called on API error
*/
function onApiError( jqXHR, textStatus, errorThrown ) {
alert( mw.msg( 'error-api' ) );
onError();
}
/**
* Return the item
* @param success function called on success
*/
function getItem( success ) {
new mw.Api().get( {
formatversion: 2,
action: 'wbgetentities',
ids: itemId
} )
.done( function ( data ) {
if ( data.success && data.entities[ itemId ] ) {
success( data.entities[ itemId ] );
} else {
onApiError();
}
} )
.fail( onApiError );
}
/**
* Return the existings links of a wiki
* @param success function called on success
*/
function getItemLinks( success ) {
getItem( function ( item ) {
success( item.sitelinks );
} );
}
/**
* Return the existings links in a page of a wiki
* @param language string language of the wiki.
* @param group string wiki group like 'wikipedia'
* @param page string name of the page
* @param success function called on success
*/
function getLanguageLinks( language, group, page, success ) {
$.ajax( {
url: '//' + language + '.' + group + '.org/w/api.php',
data: {
format: 'json',
formatversion: 2,
action: 'query',
titles: page,
prop: 'langlinks',
lllimit: 400
},
dataType: 'jsonp',
cache: true // Do not add the parameter _ which generates the warning "Unrecognized parameter: '_'"
} )
.done( function ( data ) {
if ( data.query.pages ) {
$.each( data.query.pages, function ( index, page ) {
if ( page.missing ) {
alert( mw.msg( 'error-page' ) );
onError();
} else {
success( page.langlinks || [] );
}
} );
} else {
onApiError();
}
} )
.fail( onApiError );
}
/**
* Set the item links
* @param item array the item
* @param success function called on success
* @param summary string
*/
function setItem( item, success, summary ) {
new mw.Api().postWithToken( 'csrf', {
formatversion: 2,
action: 'wbeditentity',
id: itemId,
data: JSON.stringify( item ),
summary: summary
} )
.done( success )
.fail( function ( code, data ) {
function link( match, $1, $2 ) {
return mw.html.element( 'a', { href: mw.util.getUrl( $1 ) }, $2 );
}
if ( data.error && data.error.info ) {
var errorInfo = data.error.info
.replace( /\[\[(([^\]\|]+))\]\]/g, link )
.replace( /\[\[([^\]\|]+)\|([^\]]*)\]\]/g, link )
.replace( /\wiki:/g, ':' ) // Correcting wiki link
.replace( /\*/g, '<br>*' ); // To have each errors in a line
$( '#slurpInterwiki-error' ).html( mw.message( 'error-save', errorInfo ).parse() );
onError();
} else {
onApiError();
}
} );
}
/**
* Update interLanguages links from the wiki selected in the box. Works only for Wikipedias.
*/
function work() {
$.createSpinner( {
size: 'large',
type: 'block',
id: 'slurpInterwiki'
} ).appendTo( 'div#slurpInterwiki' );
$( '#slurpInterwiki-button-import' ).button( 'option', 'disabled', true );
getItem( function ( item ) {
var links = {};
if ( item.sitelinks ) {
links = item.sitelinks;
}
var wiki = $( '#slurpInterwiki-lang' ).val();
if ( !links[ wiki ] ) {
alert( mw.msg( 'error-pageNotFound' ) );
onError();
return;
}
var page = links[ wiki ].title;
var langCode = getLanguageCodeFromWikiId( wiki );
var group = getGroupFromWikiId( wiki );
if ( specialWikis[ wiki ] || langCode === '' || group === '' ) {
alert( mw.msg( 'error-wiki' ) );
onError();
return [];
}
getLanguageLinks( langCode, group, page, function ( interlangLinks ) {
getItem( function ( item ) {
var itemValue = {};
var changed = [];
var itemLinks = {};
if ( item.sitelinks ) {
itemLinks = item.sitelinks;
}
var linkChanged = false;
$.each( interlangLinks, function ( i, link ) {
var regex = /^(.*)old$/i;
if ( regex.test( interlangLinks[ i ].lang ) && link.lang !== 'be-x-old' ) {
mw.log( 'Refused wiki: ' + link.lang );
} else {
var site = link.lang.replace( /-/g, '_' );
site = site === 'nb' ? 'no' : site;
site += ( group === 'wikipedia' ) ? 'wiki' : group;
if ( !itemLinks[ site ] && link.title.indexOf( '#' ) === -1 ) {
itemLinks[ site ] = {
'site': site,
'title': link.title
};
linkChanged = true;
}
}
} );
if ( linkChanged ) {
itemValue.sitelinks = itemLinks;
changed.push( 'sitelinks' );
}
// Update labels
if ( $( '#slurpInterwiki-updateLabels' ).prop( 'checked' ) ) {
var labels = {};
if ( item.labels ) {
labels = item.labels;
}
var labelChanged = false;
$.each( itemLinks, function ( site, link ) {
if ( specialWikis[ link.site ] ) {
return;
}
var langs = [ getLanguageCodeFromWikiId( link.site ) ];
if ( langs[ 0 ] === 'simple' ) {
return;
}
switch ( langs[ 0 ] ) {
case 'simple':
langs = [ 'en' ];
break;
/*case 'en':
case 'simple':
langs = [ 'en', 'en-ca', 'en-gb' ];
break;
case 'zh':
langs = [ 'zh', 'zh-cn', 'zh-tw', 'zh-sg', 'zh-mo', 'zh-hans', 'zh-hant', 'zh-hk' ];
break;
case 'pt':
langs = [ 'pt', 'pt-br' ];
break;
case 'de':
langs = [ 'de', 'de-ch' ];
break;*/
case 'no':
langs = [ 'nb' ];
break;
case 'als':
langs = [ 'gsw' ];
break;
case 'crh':
langs = [ 'crh-latn' ];
break;
case 'bat-smg':
langs = [ 'sgs' ];
break;
case 'be-x-old':
langs = [ 'be-tarask' ];
break;
case 'bh':
langs = [ 'bho' ];
break;
case 'fiu-vro':
langs = [ 'vro' ];
break;
case 'roa-rup':
langs = [ 'rup' ];
break;
case 'zh-classical':
langs = [ 'lzh' ];
break;
case 'zh-min-nan':
langs = [ 'nan' ];
break;
case 'zh-yue':
langs = [ 'yue' ];
break;
}
$.each( langs, function ( j, language ) {
if ( !labels[ language ] ) {
var value = itemLinks[ site ].title; // .replace( /\(.*\)/g, '' )
switch ( language ) {
case 'es':
case 'pt':
case 'pt-br':
value = value.replace( /^Anexo:/, '' );
break;
case 'cs':
value = value.replace( /^Příloha:/, '' );
break;
case 'de-ch':
value = value.replace( /ß/g, 'ss' );
break;
case 'fa':
value = itemLinks[ site ].title; // In Farsi () are important
break;
}
labels[ language ] = {
'language': language,
'value': value
};
labelChanged = true;
}
} );
} );
if ( labelChanged ) {
itemValue.labels = labels;
changed.push( 'labels' );
}
}
// Push changes
if ( changed.length !== 0 ) {
// Get list of notification and comment
var notif = [];
var comment = '';
if ( $.inArray( 'sitelinks', changed ) !== -1 ) {
notif.push( 'success-links' );
comment += 'Update of interwikis from ' + wiki + '.';
}
if ( $.inArray( 'labels', changed ) !== -1 ) {
notif.push( 'success-labels' );
comment += ' Update of labels.';
}
setItem( itemValue, function () {
location.href = mw.util.getUrl( mw.config.get( 'wgPageName' ) ) + '?slurpnotif=' + notif.join( '|' );
}, comment );
} else {
mw.notify( mw.message( 'nolinkstoupdate' ) );
$( 'div#slurpInterwiki' ).dialog( 'close' );
onError();
}
} );
} );
} );
}
/**
* Show the dialog
*/
function show() {
getItemLinks( function ( links ) {
var formFind = $( '#slurpInterwiki-lang' );
formFind.empty();
var languagesLabel = mw.config.get( 'wgULSLanguages' ) || {};
$.each( links, function ( i, link ) {
if ( specialWikis[ link.site ] ) {
return;
}
var languageCode = getLanguageCodeFromWikiId( link.site );
var label = link.site;
if ( languageCode !== '' ) {
label = languageCode + '.' + getGroupFromWikiId( link.site );
if ( languagesLabel[ languageCode ] ) {
label += ' (' + languagesLabel[ languageCode ] + ')';
}
}
formFind.append(
$( '<option>' )
.attr( 'value', links[ i ].site )
.text( label )
);
} );
$( '#slurpInterwiki-error' ).html( '' );
$( 'div#slurpInterwiki' ).dialog( 'open' );
} );
return false;
}
/**
* Create the dialog and add a link in toolBox
*/
function init() {
$( '<div>' ).attr( {
id: 'slurpInterwiki',
title: mw.msg( 'box-title' )
} ).append(
$( '<form>' ).append(
$( '<p>' ).append(
$( '<label for="slurpInterwiki-lang">' )
.text( mw.msg( 'box-lang' ) ),
$( '<select name="slurpInterwiki-lang" id="slurpInterwiki-lang">' )
),
$( '<p>' ).append(
$( '<input checked type="checkbox" name="slurpInterwiki-updateLabels" id="slurpInterwiki-updateLabels">' ),
' ',
$( '<label for="slurpInterwiki-updateLabels">' )
.text( mw.msg( 'box-updateLabels' ) )
),
$( '<p>' ).text( mw.msg( 'box-warning' ) ),
$( '<p class="error" id="slurpInterwiki-error">' )
)
)
.appendTo( '#content' )
.dialog( {
autoOpen: false,
modal: true,
width: 500,
buttons: [ {
id: 'slurpInterwiki-button-import',
text: mw.msg( 'import' ),
click: work
} ]
} );
var portletLink = mw.util.addPortletLink( 'p-tb', '#', mw.msg( 'box-title' ), 't-slurpInterwiki', mw.msg( 'box-title' ) );
$( portletLink ).click( show );
}
$( init );
} ( mediaWiki, jQuery ) );