User:Equazcion/ScriptInstaller.js
Appearance
Code that you insert on this page could contain malicious content capable of compromising your account. If you import a script from another page with "importScript", "mw.loader.load", "iusc", or "lusc", take note that this causes you to dynamically load a remote script, which could be changed by others. Editors are responsible for all edits and actions they perform, including by scripts. User scripts are not centrally supported and may malfunction or become inoperable due to software changes. A guide to help you find broken scripts is available. If you are unsure whether code you are adding to this page is safe, you can ask at the appropriate village pump. This code will be executed when previewing this page. |
This user script seems to have a documentation page at User:Equazcion/ScriptInstaller and an accompanying .css page at User:Equazcion/ScriptInstaller.css. |
(function($, mw){
'use strict';
var wgPageName = mw.config.get('wgPageName');
var wgUserName = mw.config.get('wgUserName');
var wgNamespaceNumber = mw.config.get('wgNamespaceNumber');
var jsPage = false;
// Never do anything in article space
if (wgNamespaceNumber === 0){
return;
}
// Handle .js pages
if ((wgPageName.lastIndexOf('.js') == wgPageName.length - 3) && (mw.config.get('wgAction') == 'view') && (wgNamespaceNumber > -1)) {
// Exclude users' own common.js and skin.js pages
var fixedUn = wgUserName.replace(/ /g,'_');
if ((wgPageName != 'User:' + fixedUn + '/common.js') &&
(wgPageName != 'User:' + fixedUn + '/monobook.js') &&
(wgPageName != 'User:' + fixedUn + '/minerva.js') &&
(wgPageName != 'User:' + fixedUn + '/vector.js') &&
(wgPageName != 'User:' + fixedUn + '/modern.js') &&
(wgPageName != 'User:' + fixedUn + '/cologneblue.js') &&
(wgPageName != 'User:' + fixedUn + '/timeless.js') &&
(wgPageName != 'User:Equazcion/ScriptInstaller.js')){
importStylesheet('User:Equazcion/ScriptInstaller.css');
// Set a flag so the rest of the script knows we're on a .js page
jsPage = true;
// Append the install link to the header, along with a "scriptInstallerLink" class for use by the rest of the script
$('h1#firstHeading').append('<span style="font-size:0.8em;font-weight:bold;" id="' + wgPageName + '" class="scriptInstallerLink jsPage"></span>');
}
}
// If script links are found on the page, start the music. Detection is based on span tags with "scriptInstallerLink" class, which are added by {{userscript}}.
// Also run if we're on User:Equazcion/scriptInstaller, where we'll simply provide access to the installed script list and uninstall links
if ((($('span.scriptInstallerLink').length > 0) && (mw.config.get('wgAction') != 'submit') && (mw.config.get('wgAction') != 'edit')) || (wgPageName == 'User:Equazcion/ScriptInstaller')){
if (jsPage !== true) {
importStylesheet('User:Equazcion/ScriptInstaller.css'); // Stylesheet already fetched above on .js pages
}
if (wgPageName == 'User:Equazcion/ScriptInstaller') {
var homePage = true; // Set a flag if we're running the limited User:Equazcion/ScriptInstaller functions
}
// Set URL prefix
var pre = location.protocol + '//' + mw.config.get('wgPageContentLanguage') + '.' + mw.config.get('wgNoticeProject') + '.org' + '/w/index.php?title=';
// Set interface text
var installerTitle = 'You currently have the following scripts installed <div class="titleBadge"><a href="' + pre + 'User:Equazcion/ScriptInstaller' + '">Script Installer</a></div>';
var installerMessage = 'Only scripts installed using <span style="font-weight:bold">Script Installer</span> are shown here. To uninstall a script, click "Uninstall".';
var pipe = '<span style="font-size:1.1em;"> | </span>';
var installerLink = 'Install';
var installed = 'Installed';
var unInstallerLink = 'Uninstall';
var noauto = 'Must be installed manually';
// Set up the regex pattern for later
var regexObject = new RegExp( 'importScript\\(\'(.*)\'\\); \\/\\/Linkback: \\[\\[.*?\\]\\] Added by Script installer' , ["i"]);
// Create array for installed script paths
var installedScripts = [];
// Append the box of installed scripts. Hide unless we're on a designated installation page
$('div#contentSub').after('<div hidden="hidden" class="scriptInstaller"></div>');
// Set parameters for common.js ajax request
var request4 = {
action:"query",
titles: "User:" + mw.config.get("wgUserName") + "/common.js",
prop: "revisions|info",
intoken: "edit",
rvprop: "content",
indexpageids: 1,
format: "xml"
};
// Do common.js ajax request
$.get(mw.config.get("wgScriptPath")+"/api.php", request4, function(response4){
// Grab common.js content and split by lines
var lines = $(response4).find('rev').text().split('\n');
// Use the regex to iterate through the lines, looking for the ones that ScriptInstaller added
$.each(lines, function(index, value){
var match = regexObject.exec(value);
// Put the paths of the matches into the array of installed scripts
if (match !== null){
installedScripts.push(match[1]);
}
});
// If none were found, remove the installed script list box. Otherwise fade-in the box and set up the toggle link
if (installedScripts.length < 1){
$('div.scriptInstaller').remove();
} else if ((wgPageName == 'Wikipedia:WikiProject_User_scripts/Scripts') || (wgPageName == 'Wikipedia:WikiProject_User_scripts') ||
(wgPageName == 'Wikipedia:User_scripts') || (jsPage === true) || (homePage === true)){
// Insert script list toggle link
var toggleMessage = ((jsPage === true) || (homePage === true)) ? 'Show installed script list' : 'Hide installed script list';
$('.firstHeading').append(' <a style="font-weight:bold;font-size:10px" class="scriptinstallerTog" href="#bbx">' + toggleMessage + '</a>');
// The function to set the toggle link to
function setScriptInstallerToggle(){
$('.scriptinstallerTog').click(function(){
if ($('.scriptinstallerTog').html() == "Show installed script list"){
$('.scriptInstaller').fadeIn(500);
$('.scriptinstallerTog').html('Hide installed script list');
} else {
$('.scriptInstaller').fadeOut(200);
$('.scriptinstallerTog').html('Show installed script list');
}
});
}
// Set the toggle link function. Also fade the box in initially, if we're at the script listing page.
if ((jsPage !== true) && (homePage !== true)){
setTimeout(function(){
$('.scriptInstaller').fadeIn(800, function(){ setScriptInstallerToggle(); });
}, 500);
} else {
setScriptInstallerToggle();
}
}
// Start building the code for display of the installed list. Iterate through each installed script in the array
var installedList = '<ul style="list-style-type:none;">';
$.each(installedScripts, function(index, value){
// For each script already installed, change the install links (into "installed" messages) that are on the current page (if any)
$('span.scriptInstallerLink[id="' + encodeURIComponent(value).replace('%3A',':').replace(/\//g,'.2F').replace(/ /g,'_').replace(/%/g,'.').replace(/\.20/g,'_') + '"]')
.attr('id','installed' + index)
.addClass('installed')
.html(installed)
.css('font-weight','bold');
if (jsPage === true)
$('span.scriptInstallerLink[id="' + value.replace(/ /g,'_') + '"]')
.attr('id','installed' + index)
.addClass('installed')
.html(installed)
.css('font-weight','bold');
// Add an HTML list element for each installed script, containing .js and uninstall links
installedList = installedList + '<li>' +
'<a href="#installerLink" class="unInstallerLink">' + unInstallerLink + '</a>: ' +
'<a href="' + pre + value + '">' + decodeURIComponent(value) + '</a>' +
'</li>';
});
// Cap off the list of installed scripts
installedList = installedList + '</ul>';
// Build and append the rest if the list box code, and insert our constructed list of installed scripts
$('.scriptInstaller').html('<div class="installerTitle">' + installerTitle + '</div>' +
'<div class="container1">' +
'<div class="installerMessage">' + installerMessage + '</div>' +
'<div class="uninstallList">' + installedList + '</div>' +
'</div>');
// Iterate through each line in the installed list and set the click function for their uninstall links
$('.scriptInstaller li').each(function(){
var path = $(this).find('a:last').html();
$(this).find('a:first').click(function(){
$('body').append('<div class="overlay" style="background-color:#000;opacity:.4;position:fixed;' +
'top:0;left:0;width:100%;height:100%;z-index:500;"></div>');
$('body').prepend('<div class="arcProg" style="font-weight:bold;box-shadow: 7px 7px 5px #000;font-size:0.9em;line-height:1.5em;' +
'z-index:501;opacity:1;position:fixed;width:50%;left:25%;top:30%;background:#F7F7F7;border:#222 ridge 1px;padding:20px;"></div>');
$('.arcProg').append('<div>Uninstalling <span style="font-weight:normal;color:#003366;">' + path + '</span>...</div>');
// Set parameters for the first uninstall ajax request that occurs when the uninstall link is clicked
var request5 = {
action:"query",
titles: "User:" + mw.config.get("wgUserName") + "/common.js",
prop: "revisions|info",
intoken: "edit",
rvprop: "content",
indexpageids: 1,
dataType: "xml",
format: "xml"
};
// Send the request
$.get(mw.config.get("wgScriptPath")+"/api.php", request5, function(response5){
//Grab common.js content and find/replace our line with nothing, thereby removing the script
var content = $(response5).find('rev').text();
var newText = content.replace("\n" + "importScript('" + path + "'); //Linkback: [[" + path + "]] Added by Script installer", "");
// Set paraemeters for the ajax post that replaces common.js with our edited version
var request6 = {
action : "edit",
title : "User:" + mw.config.get("wgUserName") + "/common.js",
text : newText,
summary : "[[User:Equazcion/ScriptInstaller|Script Installer]]: Removed [[" + path + "]]",
token: mw.user.tokens.get("csrfToken")
};
// Send the ajax post to save the new common.js, then reload the current page
$.post(mw.config.get("wgScriptPath")+"/api.php", request6, function(response6){
$('.arcProg').append('<div><span style="color:#00008C">Done!</span> Reloading...</div>');
location.reload();
});
});
});
});
});
// Iterate through each templated (via {{userscript}}) script on the page
$('span.scriptInstallerLink').each(function(){
// Get the script path, which the template places in the span's ID
var path = $(this).attr('id');
path = path.replace(/.2F/g,'/').replace(/\_/g,' ');
// If there's more than one dot left in the path, assume percent encoding was converted to dots. Leave the last dot for ".js"
if ((path.split(".").length - 1) > 1){
var parts = path.split('.');
path = parts.slice(0,-1).join('%') + '.' + parts.slice(-1);
}
// If this path leads to a valid en-wiki .js script in userspace or wikipedia space, add an install link
if (((path.toLowerCase().substring(0, 5) == "user:") || (path.toLowerCase().substring(0,10) == 'wikipedia:')) && (path.lastIndexOf('.js') == path.length - 3)){
//var pipe = (jsPage == true) ? '' : ' | ';
$(this).html('<a href="#installerLink" class="installerLink">' + installerLink + '</a>')
.before(pipe);
// Set the click function for the install link
$(this).find('a.installerLink').click(function(){
$('body').append('<div class="overlay" style="background-color:#000;opacity:.4;position:fixed;' +
'top:0;left:0;width:100%;height:100%;z-index:500;"></div>');
$('body').prepend('<div class="arcProg" style="font-weight:bold;box-shadow: 7px 7px 5px #000;font-size:0.9em;line-height:1.5em;' +
'z-index:501;opacity:1;position:fixed;width:50%;left:25%;top:30%;background:#F7F7F7;border:#222 ridge 1px;padding:20px;"></div>');
$('.arcProg').append('<div>Installing <span style="font-weight:normal;color:#003366;">' + path + '</span>...</div>');
// Set ajax parameters for the ajax post that occurs when the install link is clicked
var request1 = {
action:"edit",
title: "User:" + mw.config.get("wgUserName") + "/common.js",
appendtext: "\nimportScript('" + decodeURIComponent(path) + "'); //Linkback: [[" + decodeURIComponent(path) + "]] Added by Script installer",
summary: "[[User:Equazcion/ScriptInstaller|Script Installer]]: Added [[" + path + "]]",
token: mw.user.tokens.get("csrfToken")
};
// Send the ajax post, which appends our new importScript line to common.js, then reload the current page
$.post(mw.config.get("wgScriptPath")+"/api.php", request1, function(response1){
$('.arcProg').append('<div><span style="color:#00008C">Done!</span> Reloading...</div>');
location.reload();
});
});
} else {
// If this is not a valid path to an en-wiki .js script in user or wikipedia space, add a "must install manually" message
$(this).html(' | <span class="noauto">' + noauto + '</span>');
}
});
}
})(jQuery, mediaWiki);