Utilisateur:Seudo/sd dumplivre.js

La bibliothèque libre.

Note : après avoir enregistré vos modifications, il se peut que vous deviez forcer le rechargement complet du cache de votre navigateur pour voir les changements.

  • Firefox / Safari : Maintenez la touche Maj (Shift) en cliquant sur le bouton Actualiser ou pressez Ctrl-F5 ou Ctrl-R (⌘-R sur un Mac) ;
  • Google Chrome : Appuyez sur Ctrl-Maj-R (⌘-Shift-R sur un Mac) ;
  • Internet Explorer : Maintenez la touche Ctrl en cliquant sur le bouton Actualiser ou pressez Ctrl-F5 ;
  • Opera : Allez dans Menu → Settings (Opera → Préférences sur un Mac) et ensuite à Confidentialité & sécurité → Effacer les données d'exploration → Images et fichiers en cache.
/*
Ce script récupère le code wiki d'un ensemble de pages appartenant au même livre et le
copie dans une page séparée. Demande confirmation à chaque page, par sécurité.

La page de sortie est Wikisource:Bac à sable/<nom du livre>

*/
mw.loader.using(['oojs-ui', 'mediawiki.util'], function () {

$( function($) {
	nom_script = "Utilisateur:Seudo/sd dumplivre.js";
	
	mw.util.addPortletLink('p-cactions',
		'#',
		'Sd dump livre',
		'sd-dump-livre',
		'Récupère le code wiki d\'un livre');
		
	// À affiner probablement
	function newpage2url(page) {
		return "https://fr.wikisource.org/w/index.php?title=" + page + "&action=edit&redlink=1";
	}

	function ajaxPageWikiContent(page) {
		/* Exemple : api.php?action=query&prop=revisions&rvprop=content&format=jsonfm&formatversion=2&titles=Main%20Page */
		return $.ajax({
			url: mw.util.wikiScript('api'),
			type: 'GET',
			dataType: 'json',
			data: {
				action: 'query',
				format: 'json',
				formatversion: 2,
				titles:page
			}
		});
	}
	
	
	function alertmsg(msg, args = null, callback = null) {
		errmsg = msg;
		if(args) {
			pluriel = (args.nbdone >= 2 ? "s" : "");
			errmsg += " (" + args.nbdone + " page" + pluriel + " déjà traitée" + pluriel + ").";
		}
		
		displayMsg(errmsg, callback);
	}
	
	function displayMsg(msg, callback = null) {
		OO.ui.alert(msg).done(function() {
			if(callback) 
				callback();
		});
	}
	
	function updatePages(page, wikitxt, callback, args) {
		summary = 'Récupération du code wiki depuis ' + args.page_base + "/" + args.premier + ' avec ' + nom_script;
		// token = mw.user.tokens.get('editToken');
		token = mw.user.tokens.get('csrfToken');
		$.ajax({
			url: mw.util.wikiScript('api'),
			type: 'POST',
			dataType: 'json',
			data: {
				action: 'edit',
				title: page,
				format: 'json',
				summary: summary,
				text: wikitxt,
				token: token
			}
		})
		.done(function(data) {
			pluriel = (args.nbdone >= 2 ? "s" : "");
			alertmsg("Succès : " + args.nbdone + " page" + pluriel + " transférée" + pluriel + " vers " + page + ".");
		})
		.fail(function(data, textStatus, errorThrown) {
			console.log("Échec de la requête Ajax : " + textStatus + ", " + errorThrown);
			console.log(data);
			pluriel = (args.nbdone >= 2 ? "s" : "");
			errmsg = "La requête Ajax a échoué : " + JSON.stringify(data)
				+ " (" + args.nbdone + " page" + pluriel + " transféré" + pluriel + ").";
			alertmsg(errmsg, args);
		});
	}
	
	// Fonction appelée quand tout est terminé
	function fini(status, args) {
		if(status == false) {
			msg = "Erreur lors du transfert de " + args.frompage + " à " + args.topage + " vers " + args.output;
			if(args["message"])
				msg += " : " + args["message"];
			alertmsg(msg);
		}
		else {
			callback = function() {
				displayMsg("Le code wiki de " + args.nbdone + " pages vers " + args.output + " a été réalisé avec succès");
			}
			updatePages(args.output, args.wikitxt, callback, args);
		}
	}
	
	// Fonction de renommage (récursive, s'arrête à la première erreur)
	function getWikiCode(args) {
		// On renomme la page correspondant à args.premier, puis on passe à la suivante par récursion
		frompage = args.page_base + "/" + args.from;
		topage = args.page_base + "/" + args.to;
		output = args.output;

		/*
		OO.ui.confirm("Copie du code wiki de " + frompage + " ?")
		.done(function(confirmed) {
			if(confirmed) {
		*/
				$.ajax({
					/* https://fr.wikisource.org/w/api.php?action=query&prop=revisions&titles=Page:La%20Sainte%20Bible,%20trad%20Crampon,%20%C3%A9dition%201923.djvu/316&rvslots=*&rvprop=content&formatversion=2 */
					url: mw.util.wikiScript('api'),
					type: 'GET',
					// dataType: 'json',
					data: {
						action: 'query',
						prop: 'revisions',
						format: 'json',
						titles: frompage,
						rvslots: '*',
						rvprop: 'content',
						formatversion: '2', 
						// token: mw.user.tokens.get('editToken')
					}
				})
				.done(function(data) {
					wiki = data.query.pages[0].revisions[0].slots.main.content ;
					sep = "-*-*-*-*-*-*-*-*-*-*-*-*-*-*-*-*-*-*-*-*-*";
					args.wikitxt += "[[" + frompage + "]]\n\n<pre>\n" + wiki + "\n</pre>\n\n" + sep + "\n\n" ;
					args.nbdone += 1;
					args.from = args.from + 1;
					if(args.from > args.to) {
						fini(true, args);
					}
					else
						getWikiCode(args);
				})
				.fail(function(data) {
					alertmsg("La requête Ajax sur " + frompage + " a échoué : " + JSON.stringify(data), args);
				});
		/*		
			} 
			else {
				pluriel = (args.nbdone >= 2 ? "s" : "");
				alert("Arrêt : " + args.nbdone + " page" + pluriel + " renommée" + pluriel + ".");
			}
		});
		*/

	}
	
	
	function getUserPagePath() {
		username = RLCONF["wgUserName"];
		if(!username)
			throw "Impossible de récupérer le nom de l'utilisateur courant";
		return "User:" + username;
	}
	
	// Vérification des choix entrés par l'utilisateur et envoi
	function doit(form_dialog, document, from, to) {
		try {
			if(document.length == 0)
				throw "Vous n'avez pas entré le nom d'un document";
			document = document.trim();
			prefixe_livre = "Livre:";
			prefixe_user1 = "Utilisateur:";
			prefixe_user2 = "User:";
			if(document.startsWith(prefixe_livre))
				page_base = "Page:" + document.substring(prefixe_livre.length);
			else if(document.startsWith(prefixe_user1) || document.startsWith(prefixe_user2))
				page_base = document;
			else
				throw "Vous devez préciser un nom de livre (Livre:....djvu) ou une page de l'espace personnel (Utilisateur:...)";
			from = parseInt(from);
			to = parseInt(to);
			if(from === NaN || to === NaN) 
				throw "Veuillez entrer des entiers dans tous les champs numériques";
			if(from <= 0 || to <= 0)
				throw "Veuillez entrer des entiers strictement positifs comme numéros de page";
			if(to < from)
				throw "La dernière page doit avoir un numéro supérieur ou égal à la première";
            max = 200;
			if(to - from > max)
				throw "Par sécurité, veuillez ne pas récupérer plus de " + max + " pages à la fois";
			output = getUserPagePath() + "/dump_livre";
			question = "Êtes-vous sûr de vouloir récupérer le code wiki des pages " + from + " à " + to + " ?"
                + " Après avoir accepté, NE FERMEZ PAS LA FENÊTRE, le processus peut prendre "
                + "plusieurs dizaines de secondes.";
			//OO.ui.confirm(question).done(function(confirmed) {
			if(confirm(question)) {
				// Les données ont été validées, donc on peut fermer le formulaire
				form_dialog.close();

				// Fonction asynchrone, rend la main tout de suite
				getWikiCode({
					page_base: page_base,
					from: from,
					to: to,
					reason: 'Copie semi-automatisée avec [[' + nom_script + ']]...',
					nbdone: 0,
					output: output,
					wikitxt: ""
				});
			}
			else {
				form_dialog.close();
				alertmsg("Ok, rien n'a été fait.");
			}
			//} );
		}
		catch(exc) {
			form_dialog.close();
			alertmsg("Erreur : " + exc);
		}		
	}
	
	// Formulaire pour entrer les données
	function form() {
		function MyDialog( config ) {
			MyDialog.parent.call( this, config );
		}
		OO.inheritClass( MyDialog, OO.ui.Dialog );
		MyDialog.static.name = 'myDialog';
		MyDialog.prototype.initialize = function () {
			MyDialog.parent.prototype.initialize.call(this);
			this.content = new OO.ui.PanelLayout( { padded: true, expanded: false } );
			this.content.$element.append("<p><b>Attention</b> : ce script est expérimental.</p><p>Cet outil récupère la couche texte d'un ensemble de pages.</p>");
			dialog = this;

			pagename = RLCONF["wgPageName"];
			if(pagename.startsWith("Livre:"))
				livre_init = pagename;
			else
				livre_init = "";

			documentLabel = new OO.ui.LabelWidget({ label: 'Nom du document DjVu (ex. Livre:Mon livre.djvu)' });
			this.content.$element.append(documentLabel.$element);
			var livreInput = new OO.ui.TextInputWidget({ value: livre_init });
			this.content.$element.append(livreInput.$element);

			fromLabel = new OO.ui.LabelWidget({ label: 'Première page à récupérer (entier > 0)' });
			this.content.$element.append(fromLabel.$element);
			var fromInput = new OO.ui.TextInputWidget({ validate:'integer' });
			this.content.$element.append(fromInput.$element);
			
			toLabel = new OO.ui.LabelWidget({ label: 'Dernière page à récupérer (entier > 0). Pas plus de 100 pages à la fois.' });
			this.content.$element.append(toLabel.$element);
			var toInput = new OO.ui.TextInputWidget({ validate:'integer' });
			this.content.$element.append(toInput.$element);

			var validerButton = new OO.ui.ButtonInputWidget({
				label: 'Valider',
				icon: 'check',
				value: 'check'
			});
			validerButton.on('click', function() {
				doit(dialog, livreInput.value.trim(), fromInput.value, toInput.value);
			});
			this.content.$element.append(validerButton.$element);
			var cancelButton = new OO.ui.ButtonInputWidget({
				label: 'Annuler',
				icon: 'cancel',
				value: 'cancel'
			});
			cancelButton.on('click', function() {
				dialog.close();
			});
			this.content.$element.append(cancelButton.$element);
			this.$body.append(this.content.$element);
		};
		MyDialog.prototype.getBodyHeight = function () {
			return this.content.$element.outerHeight( true );
		};
		var myDialog = new MyDialog( {
			size: 'medium'
		} );
		var windowManager = new OO.ui.WindowManager();
		$( document.body ).append(windowManager.$element);
		windowManager.addWindows([myDialog]);
		windowManager.openWindow(myDialog);	
	}

	$('#sd-dump-livre').on('click', function(e) {
		// Code exécuté quand on clique sur la commande
		e.preventDefault();
		try {
			form();
		}
		catch(exc) {
			alert("Erreur : " + exc);
		}
	});
});

})