MediaWiki
Difference between revisions of "Gadget-LinguaImporter.js"
(Created page with "→* LangImporter * * Ajoute un onglet permettant d'importer automatiquement une langue sur * LinguaLibre depuis un élément Wikidata.: →<nowiki>: /* globals mw, OO, $...") |
|||
(16 intermediate revisions by 6 users not shown) | |||
Line 1: | Line 1: | ||
− | /* | + | /* ************************************************************************** */ |
− | * | + | // Description: Adds to the "Actions" menu (top right) a gadget to import a new language. Administrators only. |
− | * | + | // Usage: open Special:Preferences#mw-prefsection-gadgets > select "LanguageImporter" |
− | * | + | // See also : [[Help:Add_a_new_language]] |
− | |||
− | |||
− | + | mw.loader.using( [ 'oojs-ui', 'ext.recordWizard.wikibase', 'ext.recordWizard.widgets', 'wikibase.api.RepoApi', 'mediawiki.ForeignApi', 'mediawiki.widgets' ], function() { | |
− | |||
− | |||
− | mw.loader.using( [ 'oojs-ui', 'ext.recordWizard.wikibase', 'ext.recordWizard. | ||
'use strict'; | 'use strict'; | ||
Line 15: | Line 10: | ||
const messages = { | const messages = { | ||
'fr': { | 'fr': { | ||
− | ' | + | 'linguaimporter': 'LinguaImporter', |
− | ' | + | 'linguaimporter-action-import': 'Importer', |
− | ' | + | 'linguaimporter-action-cancel': 'Annuler', |
− | ' | + | 'linguaimporter-field-wd': 'Élément Wikidata', |
− | ' | + | 'linguaimporter-portlet-title': 'Importer une langue', |
− | ' | + | 'linguaimporter-notify-success': 'Langue importée avec succès - [[$1]]', |
}, | }, | ||
'en': { | 'en': { | ||
− | ' | + | 'linguaimporter': 'LinguaImporter', |
− | ' | + | 'linguaimporter-action-import': 'Import', |
− | ' | + | 'linguaimporter-action-cancel': 'Cancel', |
− | ' | + | 'linguaimporter-field-wd': 'Wikidata item', |
− | ' | + | 'linguaimporter-portlet-title': 'Import a language', |
− | ' | + | 'linguaimporter-notify-success': 'Language successfuly imported - [[$1]]', |
} | } | ||
}; | }; | ||
Line 38: | Line 33: | ||
− | // Instanciate | + | // Instanciate LinguaImporter and add it to MediaWiki's UI |
$( function ( $ ) { | $( function ( $ ) { | ||
− | var | + | var instanceLinguaImporter, |
instanceWindowManager = new OO.ui.WindowManager(), | instanceWindowManager = new OO.ui.WindowManager(), | ||
− | + | $portlet = $( '<a href="#">' + mw.msg( 'linguaimporter-portlet-title' ) + '</a>' ); | |
+ | $( '#actions' ).append( $( '<li>' ).append( $portlet ) ); | ||
$( 'body' ).append( instanceWindowManager.$element ); | $( 'body' ).append( instanceWindowManager.$element ); | ||
− | $ | + | $portlet.on( 'click', function ( e ) { |
e.preventDefault(); | e.preventDefault(); | ||
− | if ( | + | if ( instanceLinguaImporter === undefined ) { |
− | + | instanceLinguaImporter = new LinguaImporter(); | |
− | instanceWindowManager.addWindows( [ | + | instanceWindowManager.addWindows( [ instanceLinguaImporter ] ); |
} | } | ||
− | + | instanceLinguaImporter.open(); | |
} ); | } ); | ||
} ); | } ); | ||
− | var | + | var LinguaImporter = function() { |
// Initialize config | // Initialize config | ||
var config = { size: 'large' }; | var config = { size: 'large' }; | ||
// Parent constructor | // Parent constructor | ||
− | + | LinguaImporter.parent.call( this, config ); | |
// Properties | // Properties | ||
Line 77: | Line 73: | ||
/* Setup */ | /* Setup */ | ||
− | OO.inheritClass( | + | OO.inheritClass( LinguaImporter, OO.ui.ProcessDialog ); |
/* Static Properties */ | /* Static Properties */ | ||
− | + | LinguaImporter.static.name = 'linguaimporter'; | |
− | + | LinguaImporter.static.title = mw.msg( 'linguaimporter' ); | |
− | + | LinguaImporter.static.actions = [ | |
− | { action: 'import', label: mw.msg( ' | + | { action: 'import', label: mw.msg( 'linguaimporter-action-import' ), flags: [ 'primary', 'progressive' ] }, |
− | { action: 'cancel', label: mw.msg( ' | + | { action: 'cancel', label: mw.msg( 'linguaimporter-action-cancel' ), flags: [ 'safe', 'back' ] } |
]; | ]; | ||
Line 96: | Line 92: | ||
* Build the interface displayed inside the ProcessDialog box. | * Build the interface displayed inside the ProcessDialog box. | ||
*/ | */ | ||
− | + | LinguaImporter.prototype.initialize = function () { | |
− | + | LinguaImporter.parent.prototype.initialize.apply( this, arguments ); | |
− | this.wdInput = new mw.recordWizard. | + | this.wdInput = new mw.recordWizard.widgets.WikidataSearchWidget( { |
$overlay: $( 'body' ) | $overlay: $( 'body' ) | ||
} ); | } ); | ||
Line 108: | Line 104: | ||
this.wdInput, { | this.wdInput, { | ||
align: 'top', | align: 'top', | ||
− | label: mw.msg( ' | + | label: mw.msg( 'linguaimporter-field-wd' ), |
} | } | ||
) | ) | ||
Line 125: | Line 121: | ||
* | * | ||
* This method is called within the ProcessDialog when the user clicks | * This method is called within the ProcessDialog when the user clicks | ||
− | * on an action button (the one defined in | + | * on an action button (the one defined in LinguaImporter.static.actions). |
* Here is defined in which order each method of the category moving | * Here is defined in which order each method of the category moving | ||
* process is called. | * process is called. | ||
Line 131: | Line 127: | ||
* @return {OO.ui.Process} Action process. | * @return {OO.ui.Process} Action process. | ||
*/ | */ | ||
− | + | LinguaImporter.prototype.getActionProcess = function ( action ) { | |
var process = new OO.ui.Process(), | var process = new OO.ui.Process(), | ||
WID, wikidataItem; | WID, wikidataItem; | ||
Line 153: | Line 149: | ||
* @return {jQuery.Promise} Promise resolved when window is closed | * @return {jQuery.Promise} Promise resolved when window is closed | ||
*/ | */ | ||
− | + | LinguaImporter.prototype.closeDialog = function () { | |
var dialog = this; | var dialog = this; | ||
Line 167: | Line 163: | ||
* @return {number} Height in px the dialog should be. | * @return {number} Height in px the dialog should be. | ||
*/ | */ | ||
− | + | LinguaImporter.prototype.getBodyHeight = function () { | |
return this.content.$element.outerHeight( true ); | return this.content.$element.outerHeight( true ); | ||
}; | }; | ||
Line 173: | Line 169: | ||
− | + | LinguaImporter.prototype.createLang = function ( wikidataItem ) { | |
− | var newItem = new mw.recordWizard.wikibase.Item(), | + | var isoStatement, wmlangStatement, wmInstanceOfStatement, newMediaTypeStatement, |
+ | newItem = new mw.recordWizard.wikibase.Item(), | ||
dialog = this; | dialog = this; | ||
newItem.labels = wikidataItem.getLabels(); | newItem.labels = wikidataItem.getLabels(); | ||
+ | newItem.descriptions = wikidataItem.getDescriptions(); | ||
+ | newItem.aliases = wikidataItem.getAliases(); | ||
// instance of = language | // instance of = language | ||
Line 186: | Line 185: | ||
// ISO 639-3 | // ISO 639-3 | ||
− | isoStatement = wikidataItem.getStatements( 'P220' ) | + | isoStatement = wikidataItem.getStatements( 'P220' ); |
if ( isoStatement !== null ) { | if ( isoStatement !== null ) { | ||
newItem.addStatement( new mw.recordWizard.wikibase.Statement( 'P13' ).setType( 'external-id' ).setValue( isoStatement[ 0 ].getValue() ) ); | newItem.addStatement( new mw.recordWizard.wikibase.Statement( 'P13' ).setType( 'external-id' ).setValue( isoStatement[ 0 ].getValue() ) ); | ||
+ | } | ||
+ | |||
+ | //Commons category containing all recordings of the language | ||
+ | if ( isoStatement !== null ) { | ||
+ | newItem.addStatement( new mw.recordWizard.wikibase.Statement( 'P26' ).setType( 'external-id' ).setValue( isoStatement[ 0 ].getValue() ) ); | ||
} | } | ||
// Wikimedia language code | // Wikimedia language code | ||
− | wmlangStatement = wikidataItem.getStatements( 'P424' ) | + | wmlangStatement = wikidataItem.getStatements( 'P424' ); |
if ( wmlangStatement !== null ) { | if ( wmlangStatement !== null ) { | ||
newItem.addStatement( new mw.recordWizard.wikibase.Statement( 'P17' ).setType( 'external-id' ).setValue( wmlangStatement[ 0 ].getValue() ) ); | newItem.addStatement( new mw.recordWizard.wikibase.Statement( 'P17' ).setType( 'external-id' ).setValue( wmlangStatement[ 0 ].getValue() ) ); | ||
} | } | ||
+ | |||
+ | // Media type (depending on whether it is a sign language or not) | ||
+ | wmInstanceOfStatement = wikidataItem.getStatements( 'P31' ); | ||
+ | newMediaTypeStatement = new mw.recordWizard.wikibase.Statement( 'P24' ).setType( 'wikibase-item' ).setValue( 'Q88889' ); // audio | ||
+ | if ( wmInstanceOfStatement !== null ) { | ||
+ | if ( wmInstanceOfStatement[ 0 ].getValue() === 'Q33302' ) { | ||
+ | newMediaTypeStatement = new mw.recordWizard.wikibase.Statement( 'P24' ).setType( 'wikibase-item' ).setValue( 'Q88890' ); // video | ||
+ | } | ||
+ | } | ||
+ | newItem.addStatement( newMediaTypeStatement ); | ||
return newItem.createOrUpdate( this.api ).then( function( data ) { | return newItem.createOrUpdate( this.api ).then( function( data ) { | ||
− | console.log( 'https://lingualibre. | + | console.log( 'https://lingualibre.org/wiki/' + data.entity.id ); |
dialog.newEntityId = data.entity.id; | dialog.newEntityId = data.entity.id; | ||
} ); | } ); | ||
}; | }; | ||
− | + | LinguaImporter.prototype.success = function () { | |
− | mw.notify( mw.message( ' | + | mw.notify( mw.message( 'linguaimporter-notify-success', this.newEntityId ).text() ); |
}; | }; | ||
} ); | } ); |
Latest revision as of 21:46, 6 January 2022
/* ************************************************************************** */
// Description: Adds to the "Actions" menu (top right) a gadget to import a new language. Administrators only.
// Usage: open Special:Preferences#mw-prefsection-gadgets > select "LanguageImporter"
// See also : [[Help:Add_a_new_language]]
mw.loader.using( [ 'oojs-ui', 'ext.recordWizard.wikibase', 'ext.recordWizard.widgets', 'wikibase.api.RepoApi', 'mediawiki.ForeignApi', 'mediawiki.widgets' ], function() {
'use strict';
// Messages
const messages = {
'fr': {
'linguaimporter': 'LinguaImporter',
'linguaimporter-action-import': 'Importer',
'linguaimporter-action-cancel': 'Annuler',
'linguaimporter-field-wd': 'Élément Wikidata',
'linguaimporter-portlet-title': 'Importer une langue',
'linguaimporter-notify-success': 'Langue importée avec succès - [[$1]]',
},
'en': {
'linguaimporter': 'LinguaImporter',
'linguaimporter-action-import': 'Import',
'linguaimporter-action-cancel': 'Cancel',
'linguaimporter-field-wd': 'Wikidata item',
'linguaimporter-portlet-title': 'Import a language',
'linguaimporter-notify-success': 'Language successfuly imported - [[$1]]',
}
};
mw.messages.set( messages.en );
var lang = mw.config.get( 'wgUserLanguage' );
if ( lang !== 'en' && lang in messages ) {
mw.messages.set( messages[ lang ] );
}
// Instanciate LinguaImporter and add it to MediaWiki's UI
$( function ( $ ) {
var instanceLinguaImporter,
instanceWindowManager = new OO.ui.WindowManager(),
$portlet = $( '<a href="#">' + mw.msg( 'linguaimporter-portlet-title' ) + '</a>' );
$( '#actions' ).append( $( '<li>' ).append( $portlet ) );
$( 'body' ).append( instanceWindowManager.$element );
$portlet.on( 'click', function ( e ) {
e.preventDefault();
if ( instanceLinguaImporter === undefined ) {
instanceLinguaImporter = new LinguaImporter();
instanceWindowManager.addWindows( [ instanceLinguaImporter ] );
}
instanceLinguaImporter.open();
} );
} );
var LinguaImporter = function() {
// Initialize config
var config = { size: 'large' };
// Parent constructor
LinguaImporter.parent.call( this, config );
// Properties
this.api = new mw.Api( { timeout: 7000 } );
this.wikidataApi = new mw.ForeignApi( 'https://www.wikidata.org/w/api.php', {
anonymous: true,
parameters: { origin: '*' },
ajax: { timeout: 10000 }
} );
this.content = new OO.ui.PanelLayout( { padded: true, expanded: false } );
this.layout;
this.$body;
};
/* Setup */
OO.inheritClass( LinguaImporter, OO.ui.ProcessDialog );
/* Static Properties */
LinguaImporter.static.name = 'linguaimporter';
LinguaImporter.static.title = mw.msg( 'linguaimporter' );
LinguaImporter.static.actions = [
{ action: 'import', label: mw.msg( 'linguaimporter-action-import' ), flags: [ 'primary', 'progressive' ] },
{ action: 'cancel', label: mw.msg( 'linguaimporter-action-cancel' ), flags: [ 'safe', 'back' ] }
];
/* ProcessDialog-related Methods */
/**
* Build the interface displayed inside the ProcessDialog box.
*/
LinguaImporter.prototype.initialize = function () {
LinguaImporter.parent.prototype.initialize.apply( this, arguments );
this.wdInput = new mw.recordWizard.widgets.WikidataSearchWidget( {
$overlay: $( 'body' )
} );
this.layout = new OO.ui.Widget( {
content: [
new OO.ui.FieldLayout(
this.wdInput, {
align: 'top',
label: mw.msg( 'linguaimporter-field-wd' ),
}
)
],
} );
this.content.$element.append( this.layout.$element );
this.$body.append( this.content.$element );
this.updateSize();
};
/**
* Get a process for taking action.
*
* This method is called within the ProcessDialog when the user clicks
* on an action button (the one defined in LinguaImporter.static.actions).
* Here is defined in which order each method of the category moving
* process is called.
* @param {string} action Name of the action button clicked.
* @return {OO.ui.Process} Action process.
*/
LinguaImporter.prototype.getActionProcess = function ( action ) {
var process = new OO.ui.Process(),
WID, wikidataItem;
if ( action === 'import' ) {
WID = this.wdInput.getData();
wikidataItem = new mw.recordWizard.wikibase.Item( WID );
process.next( wikidataItem.getFromApi.bind( wikidataItem, this.wikidataApi ) );
process.next( this.createLang.bind( this, wikidataItem ) );
process.next( this.success.bind( this ) );
}
process.next( this.closeDialog, this );
return process;
};
/**
* Close the window.
*
* @return {jQuery.Promise} Promise resolved when window is closed
*/
LinguaImporter.prototype.closeDialog = function () {
var dialog = this;
var lifecycle = dialog.close();
return lifecycle.closed;
};
/**
* Get the height of the window body.
* Used by the ProcessDialog to set an accurate height to the dialog.
*
* @return {number} Height in px the dialog should be.
*/
LinguaImporter.prototype.getBodyHeight = function () {
return this.content.$element.outerHeight( true );
};
LinguaImporter.prototype.createLang = function ( wikidataItem ) {
var isoStatement, wmlangStatement, wmInstanceOfStatement, newMediaTypeStatement,
newItem = new mw.recordWizard.wikibase.Item(),
dialog = this;
newItem.labels = wikidataItem.getLabels();
newItem.descriptions = wikidataItem.getDescriptions();
newItem.aliases = wikidataItem.getAliases();
// instance of = language
newItem.addStatement( new mw.recordWizard.wikibase.Statement( 'P2' ).setType( 'wikibase-item' ).setValue( 'Q4' ) );
// wikidata id
newItem.addStatement( new mw.recordWizard.wikibase.Statement( 'P12' ).setType( 'external-id' ).setValue( wikidataItem.getId() ) );
// ISO 639-3
isoStatement = wikidataItem.getStatements( 'P220' );
if ( isoStatement !== null ) {
newItem.addStatement( new mw.recordWizard.wikibase.Statement( 'P13' ).setType( 'external-id' ).setValue( isoStatement[ 0 ].getValue() ) );
}
//Commons category containing all recordings of the language
if ( isoStatement !== null ) {
newItem.addStatement( new mw.recordWizard.wikibase.Statement( 'P26' ).setType( 'external-id' ).setValue( isoStatement[ 0 ].getValue() ) );
}
// Wikimedia language code
wmlangStatement = wikidataItem.getStatements( 'P424' );
if ( wmlangStatement !== null ) {
newItem.addStatement( new mw.recordWizard.wikibase.Statement( 'P17' ).setType( 'external-id' ).setValue( wmlangStatement[ 0 ].getValue() ) );
}
// Media type (depending on whether it is a sign language or not)
wmInstanceOfStatement = wikidataItem.getStatements( 'P31' );
newMediaTypeStatement = new mw.recordWizard.wikibase.Statement( 'P24' ).setType( 'wikibase-item' ).setValue( 'Q88889' ); // audio
if ( wmInstanceOfStatement !== null ) {
if ( wmInstanceOfStatement[ 0 ].getValue() === 'Q33302' ) {
newMediaTypeStatement = new mw.recordWizard.wikibase.Statement( 'P24' ).setType( 'wikibase-item' ).setValue( 'Q88890' ); // video
}
}
newItem.addStatement( newMediaTypeStatement );
return newItem.createOrUpdate( this.api ).then( function( data ) {
console.log( 'https://lingualibre.org/wiki/' + data.entity.id );
dialog.newEntityId = data.entity.id;
} );
};
LinguaImporter.prototype.success = function () {
mw.notify( mw.message( 'linguaimporter-notify-success', this.newEntityId ).text() );
};
} );