Dicographe

Dicographe:Matteo1234321/Gadget-RevertDiff.js

sur le Dico des Ados : ton dictionnaire collaboratif, libre et gratuit !

< Dicographe:Matteo1234321

Note : après avoir enregistré tes modifications, il se peut que tu doives forcer le rechargement complet du cache de ton navigateur pour voir les changements.

  • Google Chrome / Microsoft Edge : presse Ctrl-Maj-R (⌘-Shift-R sur un Mac).
  • Firefox / Safari : maintiens la touche Maj (aussi appelée Shift) en cliquant sur le bouton Actualiser ou bien presse Ctrl-F5 ou Ctrl-R (⌘-R sur un Mac).
  • Opera : va dans Menu → Settings (Opera → Préférences sur un Mac) et ensuite dans Confidentialité et sécurité → Effacer les données d’exploration → Images et fichiers en cache.
  • Internet Explorer : maintiens la touche Ctrl en cliquant sur le bouton Actualiser ou presse Ctrl-F5.
/**
 * Outils pour réverter
 *
 * Fournit des liens dans les pages de diff pour révoquer facilement une modification et avertir son auteur.
 *
 * Origine : Wikipedia, Lorian (en-wp), Chphe (fr-wp), https://fr.wikipedia.org/w/index.php?title=MediaWiki:Gadget-RevertDiff.js&diff=109676406&oldid=109657328, CC-BY-SA-4.0.
 * Voir la liste complète des auteurs et les dernières versions de WP en remplaçant &diff= avec ce qui suit par &action=history.
 * La version présente ici est dérivée de celle de Vikidia (elle même dérivée de Wikipédia) : https://fr.vikidia.org/w/index.php?title=MediaWiki:Gadget-RevertDiff.js&oldid=1630161, CC-BY-SA-4.0, auteurs : https://fr.vikidia.org/w/index.php?title=MediaWiki:Gadget-RevertDiff.js&action=history
 <nowiki>
 **/
mw.loader.using(['mediawiki.util', 'mediawiki.api', 'mediawiki.notify'], function () {
	if (typeof window.RevertDiff === 'undefined' && location.href.match(/diff=/)) { //We're not already launched AND we're on a diff
		window.RevertDiff = true;//We're alive !

		//Some params.
		var RevertDiffParams = {

                                //Restore
				NoRestore: "Vous ne pouvez pas restaurer.",
				Restore: "Restaurer",
				RestoreConfirm: 'Restaurer les modifications de $0 ?',
				RestoreGGBtn: "C'est fait !",
				RestoreGGNotif: "L'ancienne modification a été restaurée avec succès !",
				RestoreNoChange: "Aucun changement effectué.",
				RestorePutReason: "Raison",
				RestoreReasonPrompt: 'Indiquez ici la raison :',
				RestoreSummary: 'Restauration (retour à la version de [[Special:Contributions/$0|$0]]).',
				Restoring: "Restauration…",

				//Patrol
				Patrolling: "Marquage de la révision comme relue…",

                                //Welcoming
				Welcome: "Bienvenuter",

				//Misc
				ItsYou: "C'est vous !",
				OuchError: "Aïe aïe aïe… ",

				//Errors
				ErrorInternal: "erreur interne.",
				ErrorEditFail: "échec de la modification.",

				//EditFail
				EditFailErrCode: "Code de l'erreur : ",
				'EditFail-abusefilter-disallowed': "Un filtre anti-abus a empêché la modification.",
				'EditFail-abusefilter-warning': "Un filtre anti-abus demande à ce que vous confirmiez votre action en la répétant.",
				'EditFail-default': "La page n'est peut-être pas modifiable par vous.",
				'EditFail-protectedpage': "La page est protégée.",
				'EditFail-undofailure': "Conflit d'édition."
			},

			//To put a welcome message. Title is section's, MsgUser/MsgIp msg for respectively a registred user and an IP.
			Welcome: {
				Title: "Bienvenue",
				MsgUser: '{{subst:Bienvenue|' + mw.config.get('wgUserName') + '}}',
				MsgIP: '{{subst:Bienvenue IP|' + mw.config.get('wgUserName') + '}}'
			}
		};

		//Return a text to be shown, with the id and the vals (values to replace the $.. in txt). Vals are given in the order it appears in the text ($0, $1...)
		function RDtxt(id, vals) {
			var Txt = RevertDiffParams.Texts[id];
			if (Txt) {
				if (Array.isArray(vals))
					for (var i = 0, l = vals.length; i < l; i++)
						Txt = Txt.split("$" + i.toString()).join(vals[i]); //replaceAll isn't currently supported enough
				return Txt;
			}
		}

		//Is the user sysop, bureaucrat... uses wgUserGroups to know it.
		function userIs(group) {
			return (mw.config.get("wgUserGroups").indexOf(group) !== -1);
		}

		//Simple function so as not to repeat a mw.notify().
		function Notify(text, type) {
			mw.notify(text, {title: "RevertDiff", type: (type === undefined ? "info" : type)});
		}
		function NotifyFail(text) {//Adds a txt before the actual error message.
			mw.notify(RDtxt('OuchError') + text, {title: "RevertDiff", type: "error"});
		}

		//Will update the max level available, depending on the type and if the user can block.
		function updateLevelList() {
			var TypeSelected = $("#sel-RD-type").val(), //Which Type of warn is selected
				$LevelNum = $("#num-RD-level")[0];

			
		//Function that edits the page with title title using params, and call successCallback on success (passing response in arg).
		//If there is a fail, call editFailed with the code for parameter.
		//Do not mess this with mw.Api.edit, as this last returns the current revisions to make edits on it, here we just send parameters.
		//And moreover Vikidia does not support mw.Api.edit (and not even mw.Api.newSection).
		function editPage(title, params, successCallback) {
			var Api = new mw.Api(),
				Settings = {
					action: "edit",
					format: "json",
					title: title
				};
			Object.assign(Settings, params);
			Api.postWithToken('csrf', Settings).then(function (response) {//Let's go !
				//We're sure of a success only if this is like this. Sometimes it fails (for example with AbuseFilter) but it doesn't send an "error" object.
				if (response.edit.result === "Success") {
					successCallback(response);
				} else {
					editFailed(response.edit.code);//If no success then fail.
				}
			}).fail(function (code) {
				editFailed(code);//Same here
			});
		}

		//Restores, but ask and check a given reason.
		function restoreReason(oldId, user1) {
			var Reason = prompt(RDtxt("RestoreReasonPrompt"));
			if (Reason) //putting a summary is mandatory (if you wanted to put a custom one)
				restore(oldId, user1, Reason); // We then just call the main function.
		}

		//Restores an older edit (oldId, made by user1) overriding all edits above, perhaps using a customReason.
		function restore(oldId, user1, customReason) {
			//If customReason is defined, then the user already "confirmed" by putting a summary.
			if (customReason === undefined && !confirm(RDtxt('RestoreConfirm', [user1])))
				return;

			Notify(RDtxt('Restoring'), "info");//So the users doesn't feel like waiting for nothing

			var Summary = (customReason ? customReason + ' - ' : "") + RDtxt('RestoreSummary', [user1]); //We always put the RestoreSummary but we may add a customReason.

			editPage(mw.config.get('wgPageName'), {
				undo: oldId, //Undo until oldId
				undoafter: mw.config.get('wgCurRevisionId'), //We need to tell mw from which edit to which edit we want to override
				summary: Summary
			}, function (response) {
				if (response.edit.nochange !== undefined)//Not very useful, just to be more precise.
					Notify(RDtxt('RestoreNoChange'), "info");
				else
					Notify(RDtxt('RestoreGGNotif'), 'success');

				$("#span-RD-restore").text(RDtxt('RestoreGGBtn')); //No need of it anymore

				var PatrolLinkElt = $("#mw-diff-ntitle4 > .patrollink > a"); //Can we patrol = is the button-link "Mark as patrolled" present ?
				if (PatrolLinkElt.length === 1) {
					Notify(RDtxt('Patrolling'));
					PatrolLinkElt[0].click();//The link already shows an animation and a notif when clicked.
				}
			});
		}

		}

		//Welcomes user, using a message for IPs if the user isIP, and has been triggered by the elt $triggerer.
		function welcomeUser(user, isIP, triggerer) {
			var Welcome = RevertDiffParams.Welcome;
			postMessage((isIP ? Welcome.MsgIP : Welcome.MsgUser), RevertDiffParams.Welcome.Title, user, null, triggerer);
		}

		//Protection against accidental usages of posting system. A non sysop user cannot post more than MaxMsgNonInGroup message(s).
		function confirmPost(user) {
			var UserCanPost = userIs(RevertDiffParams.GroupNoLimitMsg) || (RevertDiffParams.MsgPosted < RevertDiffParams.MaxMsgNonInGroup);

			if (UserCanPost) {
				var ConfirmMsg = "";
				if (RevertDiffParams.MsgPosted > 0) {//Already posted a message = confirmation's mandatory
					ConfirmMsg = RDtxt("MsgAlreadyPost", [RevertDiffParams.MsgPosted, user]);
				} else { // Otherwise: basic confirmation message
					ConfirmMsg = RDtxt('WarnConfirm', [user]);
				}

				return confirm(ConfirmMsg); //Asks for confirmation
			}
			alert(RDtxt('MaxWarnTrig'));
			return false; //No way: the user can't post anymore
		}

		//Posts to user a message, that contains msg and has for title title. Will add additionnalSuccessMsg to the success notif if it's set.
		//Triggered by elt $triggerer. 
		function postMessage(msg, title, user, additionnalSuccessMsg, triggerer) {
			if (!confirmPost(user))//Can the user post ?
				return;

			Notify(RDtxt('SendingMsg'), "info"); //Wait little user, be patient !

			editPage("User talk:" + user, {
				section: "new",
				sectiontitle: title,
				text: msg
			}, function () {
				switch (triggerer.nodeName) {//The action we do on the elt depends of what is it
					case "BUTTON": //We disable and change the text
						triggerer.disabled = true;
						triggerer.textContent = RDtxt('MsgGG');
						break;

					case "FORM": //We reset it
						triggerer.reset();
						break;
				}

				Notify(RDtxt('MsgGG') + (additionnalSuccessMsg ? ' ' + additionnalSuccessMsg : ''), 'success');
				RevertDiffParams.MsgPosted++;//To remind the user he already posted one !
			});
		}

		//Function to tell that an edit failed and gives a clue about why.
		function editFailed(code) {
			var Msg = "";
			switch (code) {
				case "abusefilter-disallowed":
				case "abusefilter-warning":
				case "undofailure":
				case "protectedpage":
					Msg = RDtxt("EditFail-" + code);
					break;

				default:
					Msg = RDtxt("EditFail-default") + (code ? (" " + RDtxt("EditFailErrCode") + code) : "");//If the code is defined then let's put it anyway.
			}

			NotifyFail(RDtxt("ErrorEditFail") + " " + Msg);
		}

		$(document).ready(function () { //Aight, let's init
			// Get username of submitter
			var User1TD = $('td.diff-otitle');
			var User2TD = $('td.diff-ntitle');

			if (!User2TD.length) {//Whoops
				NotifyFail(RDtxt("ErrorInternal"));
				return;
			} else if (!User1TD.length) {//"Fake" diffs (only one version)
				return;
			}

			// Fetching the oldid
			var OldId = mw.util.getParamValue("oldid", User1TD.find('span.mw-diff-edit a').attr('href')); //This is the link to edit the old version that we use ("(edit)" is displayed on the UI).

			var User1A = User1TD.find('a.mw-userlink'), //This time the link to the user page...
				User2A = User2TD.find('a.mw-userlink'),
				User1Name = User1A.text(), // Finnally the text
				User2Name = User2A.text(),
				RestoreHTML, MessagesHTML;//And let's init.

			//Can we edit the current page ? This variable may do false-positive (that will be catched anyway by a nice failure notification) but no false negative.
			if (mw.config.get("wgIsProbablyEditable")) {
				RestoreHTML = '(<span id=span-RD-restore><button id=btn-RD-restore>' + RDtxt('Restore') + '</button>'//The span will permit the override of the button when we will finish the restoration.
						+ '-'
						+ '<button id=btn-RD-restore-sum>' + RDtxt('RestorePutReason') + '</button></span>)';//We can choose a custom reason or not.
			} else {
				RestoreHTML = "(" + RDtxt("NoRestore") + ")";//If we can't it's a little easier
			}

				//Welcoming the user.
				var WelcomeTxt = '(<button id=btn-RD-welcome>' + RDtxt('Welcome') + '</button>)';

				MessagesHTML = WarnsHTML + " " + WelcomeTxt;//Now we have our html for the messages.
			} else {
				MessagesHTML = '(' + RDtxt('ItsYou') + ')';//Not gonna warn myself.
			}

			$("#contentSub").append("<div id=div-RD-main>" + RestoreHTML + " " + MessagesHTML + "</div>"); //Let's add ourself just below the title.

			//Now let's bind some events.
			if (mw.config.get("wgIsProbablyEditable")) //There is no btn if we can't edit.
				$("button[id^=btn-RD-restore]").on("click", function (e) {
					// If the id is btn-RD-restore-sum, we want to set a custom summarry.
					var Func = (e.target.id === "btn-RD-restore-sum" ? restoreReason : restore);//Which fn to use ?
					Func(OldId, User1Name);
				});


				$("#btn-RD-welcome").on("click", function (e) { //Welcome
					var IsIP = User2A.hasClass("mw-anonuserlink"); //Is the link for an IP ?
					welcomeUser(User2Name, IsIP, e.target);
				});

				$("#sel-RD-type").on("change", updateLevelList); //Change warn type = update the max lvl available

				$("#form-RD-warn").on("submit", function (e) {
					warnUser(User2Name, $("#sel-RD-type").val(), $("#num-RD-level").val(), e.target);
					e.returnValue = false;//We don't reload the page here !
					e.preventDefault();
				});
			}

		});
	}//End of testing if we can use RevertDiff
});//End of closure
//</nowiki>