diff --git a/.eslintignore b/.eslintignore
index c56157704..9d2449b36 100644
--- a/.eslintignore
+++ b/.eslintignore
@@ -1,3 +1,2 @@
scripts/
-tests/
lib/
diff --git a/.eslintrc.json b/.eslintrc.json
index e3f7dd7bb..2df51e665 100644
--- a/.eslintrc.json
+++ b/.eslintrc.json
@@ -13,6 +13,7 @@
"rules": {
"array-bracket-spacing": "off",
"computed-property-spacing": "off",
+ "es-x/no-array-prototype-includes": "off",
"indent": "off",
"jsdoc/require-param": "off",
"jsdoc/require-returns": "off",
@@ -38,9 +39,9 @@
"selector": "MemberExpression > Identifier[name=\"fail\"]"
}
],
+ "unicorn/prefer-includes": "error",
"camelcase": ["warn", {"properties": "never"}],
- "es-x/no-array-prototype-includes": "warn",
"es-x/no-object-values": "warn",
"mediawiki/class-doc": "warn",
"new-cap": "warn",
diff --git a/modules/twinklebatchdelete.js b/modules/twinklebatchdelete.js
index ab7beafa9..b83d1a4d9 100644
--- a/modules/twinklebatchdelete.js
+++ b/modules/twinklebatchdelete.js
@@ -305,7 +305,7 @@ Twinkle.batchdelete.callback.toggleSubpages = function twDbatchToggleSubpages(e)
const pageTitle = mw.Title.newFromText(pageName);
// No need to look for subpages in main/file/mediawiki space
- if ([0, 6, 8].indexOf(pageTitle.namespace) > -1) {
+ if ([0, 6, 8].includes(pageTitle.namespace)) {
subpageLister.workerSuccess();
return;
}
diff --git a/modules/twinkleconfig.js b/modules/twinkleconfig.js
index d428ff0b3..06b405c18 100644
--- a/modules/twinkleconfig.js
+++ b/modules/twinkleconfig.js
@@ -753,12 +753,12 @@ Twinkle.config.init = function twinkleconfigInit() {
check.setAttribute('type', 'checkbox');
check.setAttribute('id', pref.name + '_' + itemkey);
check.setAttribute('name', pref.name + '_' + itemkey);
- if (gotPref && gotPref.indexOf(itemkey) !== -1) {
+ if (gotPref && gotPref.includes(itemkey)) {
check.setAttribute('checked', 'checked');
}
// cater for legacy integer array values for unlinkNamespaces (this can be removed a few years down the track...)
if (pref.name === 'unlinkNamespaces') {
- if (gotPref && gotPref.indexOf(parseInt(itemkey, 10)) !== -1) {
+ if (gotPref && gotPref.includes(parseInt(itemkey, 10))) {
check.setAttribute('checked', 'checked');
}
}
@@ -896,7 +896,7 @@ Twinkle.config.init = function twinkleconfigInit() {
box.appendChild(document.createTextNode(', or by editing this page.'));
$(box).insertAfter($('#contentSub'));
- } else if (['monobook', 'vector', 'vector-2022', 'cologneblue', 'modern', 'timeless', 'minerva', 'common'].indexOf(scriptPageName) !== -1) {
+ } else if (['monobook', 'vector', 'vector-2022', 'cologneblue', 'modern', 'timeless', 'minerva', 'common'].includes(scriptPageName)) {
// place "Looking for Twinkle options?" notice
box.setAttribute('class', 'config-userskin-box');
@@ -1119,7 +1119,7 @@ Twinkle.config.resetPref = function twinkleconfigResetPref(pref) {
case 'set':
$.each(pref.setValues, (itemkey) => {
if (document.getElementById(pref.name + '_' + itemkey)) {
- document.getElementById(pref.name + '_' + itemkey).checked = Twinkle.defaultConfig[pref.name].indexOf(itemkey) !== -1;
+ document.getElementById(pref.name + '_' + itemkey).checked = Twinkle.defaultConfig[pref.name].includes(itemkey);
}
});
break;
diff --git a/modules/twinkleimage.js b/modules/twinkleimage.js
index 546faf533..05dfb8b03 100644
--- a/modules/twinkleimage.js
+++ b/modules/twinkleimage.js
@@ -133,7 +133,7 @@ Twinkle.image.callback.evaluate = function twinkleimageCallbackEvaluate(event) {
throw new Error('Twinkle.image.callback.evaluate: unknown criterion');
}
- const lognomination = Twinkle.getPref('logSpeedyNominations') && Twinkle.getPref('noLogOnSpeedyNomination').indexOf(csdcrit.toLowerCase()) === -1;
+ const lognomination = Twinkle.getPref('logSpeedyNominations') && !Twinkle.getPref('noLogOnSpeedyNomination').includes(csdcrit.toLowerCase());
const templatename = input.derivative ? 'dw ' + input.type : input.type;
const params = $.extend({
diff --git a/modules/twinklerollback.js b/modules/twinklerollback.js
index 23bde47b5..2fa927acb 100644
--- a/modules/twinklerollback.js
+++ b/modules/twinklerollback.js
@@ -192,9 +192,9 @@ Twinkle.rollback.addLinks = {
if (mw.config.exists('wgRelevantUserName') || isRange) {
// Get the username these contributions are for
let username = mw.config.get('wgRelevantUserName');
- if (Twinkle.getPref('showRollbackLinks').indexOf('contribs') !== -1 ||
- (mw.config.get('wgUserName') !== username && Twinkle.getPref('showRollbackLinks').indexOf('others') !== -1) ||
- (mw.config.get('wgUserName') === username && Twinkle.getPref('showRollbackLinks').indexOf('mine') !== -1)) {
+ if (Twinkle.getPref('showRollbackLinks').includes('contribs') ||
+ (mw.config.get('wgUserName') !== username && Twinkle.getPref('showRollbackLinks').includes('others')) ||
+ (mw.config.get('wgUserName') === username && Twinkle.getPref('showRollbackLinks').includes('mine'))) {
const $list = $('#mw-content-text').find('ul li:has(span.mw-uctop):has(.mw-changeslist-diff)');
$list.each((key, current) => {
@@ -218,7 +218,7 @@ Twinkle.rollback.addLinks = {
},
recentchanges: function() {
- if (Twinkle.getPref('showRollbackLinks').indexOf('recent') !== -1) {
+ if (Twinkle.getPref('showRollbackLinks').includes('recent')) {
// Latest and revertable (not page creations, logs, categorizations, etc.)
let $list = $('.mw-changeslist .mw-changeslist-last.mw-changeslist-src-mw-edit');
// Exclude top-level header if "group changes" preference is used
@@ -238,7 +238,7 @@ Twinkle.rollback.addLinks = {
},
history: function() {
- if (Twinkle.getPref('showRollbackLinks').indexOf('history') !== -1) {
+ if (Twinkle.getPref('showRollbackLinks').includes('history')) {
// All revs
const histList = $('#pagehistory li').toArray();
@@ -286,7 +286,7 @@ Twinkle.rollback.addLinks = {
extraParams += xtitle === 'otitle' ? mw.config.get('wgDiffOldId') : mw.config.get('wgDiffNewId');
const href = $talkLink.attr('href');
- if (href.indexOf('?') === -1) {
+ if (!href.includes('?')) {
$talkLink.attr('href', href + '?' + extraParams);
} else {
$talkLink.attr('href', href + '&' + extraParams);
@@ -311,7 +311,7 @@ Twinkle.rollback.addLinks = {
// Not latest revision, add [restore this revision] link to newer revision
const newTitle = document.getElementById('mw-diff-ntitle1').parentNode;
newTitle.insertBefore(Twinkle.rollback.linkBuilder.restoreThisRevisionLink('wgDiffNewId'), newTitle.firstChild);
- } else if (Twinkle.getPref('showRollbackLinks').indexOf('diff') !== -1 && mw.config.get('wgDiffOldId') && (mw.config.get('wgDiffOldId') !== mw.config.get('wgDiffNewId') || document.getElementById('differences-prevlink'))) {
+ } else if (Twinkle.getPref('showRollbackLinks').includes('diff') && mw.config.get('wgDiffOldId') && (mw.config.get('wgDiffOldId') !== mw.config.get('wgDiffNewId') || document.getElementById('differences-prevlink'))) {
// Normally .mw-userlink is a link, but if the
// username is hidden, it will be a span with
// .history-deleted as well. When a sysop views the
@@ -459,11 +459,11 @@ Twinkle.rollback.callbacks = {
undoafter: revertToRevID,
basetimestamp: touched,
starttimestamp: loadtimestamp,
- minor: Twinkle.getPref('markRevertedPagesAsMinor').indexOf('torev') !== -1 ? true : undefined,
+ minor: Twinkle.getPref('markRevertedPagesAsMinor').includes('torev') ? true : undefined,
format: 'json'
};
// Handle watching, possible expiry
- if (Twinkle.getPref('watchRevertedPages').indexOf('torev') !== -1) {
+ if (Twinkle.getPref('watchRevertedPages').includes('torev')) {
const watchOrExpiry = Twinkle.getPref('watchRevertedExpiry');
if (!watchOrExpiry || watchOrExpiry === 'no') {
@@ -541,7 +541,7 @@ Twinkle.rollback.callbacks = {
} else if (params.type === 'vand' &&
// Okay to test on user since it will either fail or sysop will correctly access it
// Besides, none of the trusted bots are going to be revdel'd
- Twinkle.rollback.trustedBots.indexOf(top.user) !== -1 && revs.length > 1 &&
+ Twinkle.rollback.trustedBots.includes(top.user) && revs.length > 1 &&
revs[1].revid === params.revid) {
Morebits.Status.info('Info', [ 'Latest revision was made by ', Morebits.htmlNode('strong', lastuser), ', a trusted bot, and the revision before was made by our vandal, so we will proceed with the revert.' ]);
index = 2;
@@ -557,7 +557,7 @@ Twinkle.rollback.callbacks = {
userNorm = params.user || Twinkle.rollback.hiddenName;
}
- if (Twinkle.rollback.trustedBots.indexOf(params.user) !== -1) {
+ if (Twinkle.rollback.trustedBots.includes(params.user)) {
switch (params.type) {
case 'vand':
Morebits.Status.info('Info', [ 'Vandalism revert was chosen on ', Morebits.htmlNode('strong', userNorm), '. As this is a trusted bot, we assume you wanted to revert vandalism made by the previous user instead.' ]);
@@ -685,7 +685,7 @@ Twinkle.rollback.callbacks = {
}
// Decide whether to notify the user on success
- if (!Twinkle.rollback.skipTalk && Twinkle.getPref('openTalkPage').indexOf(params.type) !== -1 &&
+ if (!Twinkle.rollback.skipTalk && Twinkle.getPref('openTalkPage').includes(params.type) &&
!params.userHidden && mw.config.get('wgUserName') !== params.user) {
params.notifyUser = true;
// Pass along to the warn module
@@ -712,11 +712,11 @@ Twinkle.rollback.callbacks = {
undoafter: params.goodid,
basetimestamp: touched,
starttimestamp: loadtimestamp,
- minor: Twinkle.getPref('markRevertedPagesAsMinor').indexOf(params.type) !== -1 ? true : undefined,
+ minor: Twinkle.getPref('markRevertedPagesAsMinor').includes(params.type) ? true : undefined,
format: 'json'
};
// Handle watching, possible expiry
- if (Twinkle.getPref('watchRevertedPages').indexOf(params.type) !== -1) {
+ if (Twinkle.getPref('watchRevertedPages').includes(params.type)) {
const watchOrExpiry = Twinkle.getPref('watchRevertedExpiry');
if (!watchOrExpiry || watchOrExpiry === 'no') {
diff --git a/modules/twinklespeedy.js b/modules/twinklespeedy.js
index dcdd2d9f5..a55224ad8 100644
--- a/modules/twinklespeedy.js
+++ b/modules/twinklespeedy.js
@@ -441,10 +441,10 @@ Twinkle.speedy.generateCsdList = function twinklespeedyGenerateCsdList(list, mod
return null;
}
- if (criterion.showInNamespaces && criterion.showInNamespaces.indexOf(pageNamespace) < 0) {
+ if (criterion.showInNamespaces && !criterion.showInNamespaces.includes(pageNamespace)) {
return null;
}
- if (criterion.hideInNamespaces && criterion.hideInNamespaces.indexOf(pageNamespace) > -1) {
+ if (criterion.hideInNamespaces && criterion.hideInNamespaces.includes(pageNamespace)) {
return null;
}
@@ -728,7 +728,7 @@ Twinkle.speedy.userList = [
tooltip:
'User requested deletion of their own user page or user-subpage. User pages that are blanked by the user may also be deleted under this criterion.',
subgroup:
- mw.config.get('wgNamespaceNumber') === 3 && mw.config.get('wgTitle').indexOf('/') === -1 ? {
+ mw.config.get('wgNamespaceNumber') === 3 && !mw.config.get('wgTitle').includes('/') ? {
name: 'userreq_rationale',
parameter: '2',
type: 'input',
@@ -1283,12 +1283,12 @@ Twinkle.speedy.callbacks = {
params.utparams = buildData[1];
// Set the correct value for |ts= parameter in {{db-g13}}
- if (params.normalizeds.indexOf('g13') !== -1) {
+ if (params.normalizeds.includes('g13')) {
code = code.replace('$TIMESTAMP', pageobj.getLastEditTime());
}
// Tag if possible, post on talk if not
- if (pageobj.canEdit() && ['wikitext', 'Scribunto', 'javascript', 'css', 'sanitized-css'].indexOf(pageobj.getContentModel()) !== -1 && mw.config.get('wgNamespaceNumber') !== 710 /* TimedText */) {
+ if (pageobj.canEdit() && ['wikitext', 'Scribunto', 'javascript', 'css', 'sanitized-css'].includes(pageobj.getContentModel()) && mw.config.get('wgNamespaceNumber') !== 710 /* TimedText */) {
let text = pageobj.getPageText();
statelem.status('Checking for tags on the page...');
@@ -1326,11 +1326,11 @@ Twinkle.speedy.callbacks = {
if (mw.config.get('wgPageContentModel') === 'Scribunto') {
// Scribunto isn't parsed like wikitext, so CSD templates on modules need special handling to work
let equals = '';
- while (code.indexOf(']' + equals + ']') !== -1) {
+ while (code.includes(']' + equals + ']')) {
equals += '=';
}
code = "require('Module:Module wikitext')._addText([" + equals + '[' + code + ']' + equals + ']);';
- } else if (['javascript', 'css', 'sanitized-css'].indexOf(mw.config.get('wgPageContentModel')) !== -1) {
+ } else if (['javascript', 'css', 'sanitized-css'].includes(mw.config.get('wgPageContentModel'))) {
// Likewise for JS/CSS pages
code = '/* ' + code + ' */';
}
@@ -1351,7 +1351,7 @@ Twinkle.speedy.callbacks = {
}
// Blank attack pages
- if (params.normalizeds.indexOf('g10') !== -1) {
+ if (params.normalizeds.includes('g10')) {
text = code;
} else {
// Insert tag after short description or any hatnotes
@@ -1778,18 +1778,18 @@ Twinkle.speedy.callback.evaluateSysop = function twinklespeedyCallbackEvaluateSy
// analyse each criterion to determine whether to watch the page, prompt for summary, or notify the creator
let watchPage, promptForSummary;
normalizeds.forEach((norm) => {
- if (Twinkle.getPref('watchSpeedyPages').indexOf(norm) !== -1) {
+ if (Twinkle.getPref('watchSpeedyPages').includes(norm)) {
watchPage = Twinkle.getPref('watchSpeedyExpiry');
}
- if (Twinkle.getPref('promptForSpeedyDeletionSummary').indexOf(norm) !== -1) {
+ if (Twinkle.getPref('promptForSpeedyDeletionSummary').includes(norm)) {
promptForSummary = true;
}
});
- const warnusertalk = form.warnusertalk.checked && normalizeds.some((norm, index) => Twinkle.getPref('warnUserOnSpeedyDelete').indexOf(norm) !== -1 &&
+ const warnusertalk = form.warnusertalk.checked && normalizeds.some((norm, index) => Twinkle.getPref('warnUserOnSpeedyDelete').includes(norm) &&
!(norm === 'g6' && values[index] !== 'copypaste'));
- const welcomeuser = warnusertalk && normalizeds.some((norm) => Twinkle.getPref('welcomeUserOnSpeedyDeletionNotification').indexOf(norm) !== -1);
+ const welcomeuser = warnusertalk && normalizeds.some((norm) => Twinkle.getPref('welcomeUserOnSpeedyDeletionNotification').includes(norm));
const params = {
values: values,
@@ -1831,12 +1831,12 @@ Twinkle.speedy.callback.evaluateUser = function twinklespeedyCallbackEvaluateUse
const normalizeds = values.map((value) => Twinkle.speedy.normalizeHash[value]);
// analyse each criterion to determine whether to watch the page/notify the creator
- const watchPage = normalizeds.some((csdCriteria) => Twinkle.getPref('watchSpeedyPages').indexOf(csdCriteria) !== -1) && Twinkle.getPref('watchSpeedyExpiry');
+ const watchPage = normalizeds.some((csdCriteria) => Twinkle.getPref('watchSpeedyPages').includes(csdCriteria)) && Twinkle.getPref('watchSpeedyExpiry');
- const notifyuser = form.notify.checked && normalizeds.some((norm, index) => Twinkle.getPref('notifyUserOnSpeedyDeletionNomination').indexOf(norm) !== -1 &&
+ const notifyuser = form.notify.checked && normalizeds.some((norm, index) => Twinkle.getPref('notifyUserOnSpeedyDeletionNomination').includes(norm) &&
!(norm === 'g6' && values[index] !== 'copypaste'));
- const welcomeuser = notifyuser && normalizeds.some((norm) => Twinkle.getPref('welcomeUserOnSpeedyDeletionNotification').indexOf(norm) !== -1);
- const csdlog = Twinkle.getPref('logSpeedyNominations') && normalizeds.some((norm) => Twinkle.getPref('noLogOnSpeedyNomination').indexOf(norm) === -1);
+ const welcomeuser = notifyuser && normalizeds.some((norm) => Twinkle.getPref('welcomeUserOnSpeedyDeletionNotification').includes(norm));
+ const csdlog = Twinkle.getPref('logSpeedyNominations') && normalizeds.some((norm) => !Twinkle.getPref('noLogOnSpeedyNomination').includes(norm));
const params = {
values: values,
diff --git a/modules/twinkleunlink.js b/modules/twinkleunlink.js
index c531b97b0..2436c4749 100644
--- a/modules/twinkleunlink.js
+++ b/modules/twinkleunlink.js
@@ -122,8 +122,8 @@ Twinkle.unlink.callback.evaluate = function twinkleunlinkCallbackEvaluate(event)
const wikipedia_page = new Morebits.wiki.Page(pageName, 'Unlinking in page "' + pageName + '"');
wikipedia_page.setBotEdit(true); // unlink considered a floody operation
wikipedia_page.setCallbackParameters($.extend({
- doBacklinks: input.backlinks.indexOf(pageName) !== -1,
- doImageusage: input.imageusage.indexOf(pageName) !== -1
+ doBacklinks: input.backlinks.includes(pageName),
+ doImageusage: input.imageusage.includes(pageName)
}, params));
wikipedia_page.load(Twinkle.unlink.callbacks.unlinkBacklinks);
});
diff --git a/morebits.js b/morebits.js
index 8d0269ba0..e0285e7a5 100644
--- a/morebits.js
+++ b/morebits.js
@@ -131,7 +131,7 @@ Morebits.l10n = {
* @return {boolean}
*/
Morebits.userIsInGroup = function (group) {
- return mw.config.get('wgUserGroups').indexOf(group) !== -1;
+ return mw.config.get('wgUserGroups').includes(group);
};
/**
* Hardcodes whether the user is a sysop, used a lot.
@@ -269,7 +269,7 @@ Morebits.namespaceRegex = function(namespaces) {
const aliases = [];
let regex;
$.each(mw.config.get('wgNamespaceIds'), (name, number) => {
- if (namespaces.indexOf(number) !== -1) {
+ if (namespaces.includes(number)) {
// Namespaces are completely agnostic as to case,
// and a regex string is more useful/compatible than a RegExp object,
// so we accept any casing for any letter.
@@ -1557,7 +1557,7 @@ Morebits.string = {
* @return {boolean}
*/
isInfinity: function morebitsStringIsInfinity(expiry) {
- return ['indefinite', 'infinity', 'infinite', 'never'].indexOf(expiry) !== -1;
+ return ['indefinite', 'infinity', 'infinite', 'never'].includes(expiry);
},
/**
@@ -1653,7 +1653,7 @@ Morebits.select2 = {
const result = originalMatcher(params, data);
if (result && params.term &&
- data.text.toUpperCase().indexOf(params.term.toUpperCase()) !== -1) {
+ data.text.toUpperCase().includes(params.term.toUpperCase())) {
result.children = data.children;
}
return result;
@@ -2284,7 +2284,7 @@ Morebits.wiki.api = function(currentAction, query, onSuccess, statusElement, onE
this.query = query;
this.query.assert = 'user';
// Enforce newer error formats, preferring html
- if (!query.errorformat || ['wikitext', 'plaintext'].indexOf(query.errorformat) === -1) {
+ if (!query.errorformat || !['wikitext', 'plaintext'].includes(query.errorformat)) {
this.query.errorformat = 'html';
}
// Explicitly use the wiki's content language to minimize confusion,
@@ -2305,12 +2305,12 @@ Morebits.wiki.api = function(currentAction, query, onSuccess, statusElement, onE
this.query.format = 'xml';
} else if (query.format === 'json' && !query.formatversion) {
this.query.formatversion = '2';
- } else if (['xml', 'json'].indexOf(query.format) === -1) {
+ } else if (!['xml', 'json'].includes(query.format)) {
this.statelem.error('Invalid API format: only xml and json are supported.');
}
// Ignore tags for queries and most common unsupported actions, produces warnings
- if (query.action && ['query', 'review', 'stabilize', 'pagetriageaction', 'watch'].indexOf(query.action) !== -1) {
+ if (query.action && ['query', 'review', 'stabilize', 'pagetriageaction', 'watch'].includes(query.action)) {
delete query.tags;
} else if (!query.tags && morebitsWikiChangeTag) {
query.tags = morebitsWikiChangeTag;
@@ -2900,7 +2900,7 @@ Morebits.wiki.page = function(pageName, status) {
break;
}
- if (['recreate', 'createonly', 'nocreate'].indexOf(ctx.createOption) !== -1) {
+ if (['recreate', 'createonly', 'nocreate'].includes(ctx.createOption)) {
query[ctx.createOption] = '';
}
@@ -3432,7 +3432,7 @@ Morebits.wiki.page = function(pageName, status) {
/** @return {boolean} whether or not you can edit the page */
this.canEdit = function() {
- return !!ctx.testActions && ctx.testActions.indexOf('edit') !== -1;
+ return !!ctx.testActions && ctx.testActions.includes('edit');
};
/**
@@ -3594,7 +3594,7 @@ Morebits.wiki.page = function(pageName, status) {
*/
this.triage = function() {
// Fall back to patrol if not a valid triage namespace
- if (mw.config.get('pageTriageNamespaces').indexOf(new mw.Title(ctx.pageName).getNamespaceId()) === -1) {
+ if (!mw.config.get('pageTriageNamespaces').includes(new mw.Title(ctx.pageName).getNamespaceId())) {
this.patrol();
} else {
if (!Morebits.userIsSysop && !Morebits.userIsInGroup('patroller')) {
@@ -3778,7 +3778,7 @@ Morebits.wiki.page = function(pageName, status) {
// wgRestrictionEdit is null on non-existent pages,
// so this neatly handles nonexistent pages
const editRestriction = mw.config.get('wgRestrictionEdit');
- if (!editRestriction || editRestriction.indexOf('sysop') !== -1) {
+ if (!editRestriction || editRestriction.includes('sysop')) {
return false;
}
}
@@ -4231,7 +4231,7 @@ Morebits.wiki.page = function(pageName, status) {
const missing = response.pages[0].missing;
// No undelete as an existing page could have deleted revisions
- const actionMissing = missing && ['delete', 'stabilize', 'move'].indexOf(action) !== -1;
+ const actionMissing = missing && ['delete', 'stabilize', 'move'].includes(action);
const protectMissing = action === 'protect' && missing && (ctx.protectEdit || ctx.protectMove);
const saltMissing = action === 'protect' && !missing && ctx.protectCreate;
@@ -4944,7 +4944,7 @@ Morebits.wikitext.page.prototype = {
// For most namespaces, unlink both [[User:Test]] and [[:User:Test]]
// For files and categories, only unlink [[:Category:Test]]. Do not unlink [[Category:Test]]
- const isFileOrCategory = [6, 14].indexOf(namespaceID) !== -1;
+ const isFileOrCategory = [6, 14].includes(namespaceID);
const colon = isFileOrCategory ? ':' : ':?';
const simple_link_regex = new RegExp('\\[\\[' + colon + '(' + link_regex_string + ')\\]\\]', 'g');
diff --git a/tests/.eslintrc.json b/tests/.eslintrc.json
new file mode 100644
index 000000000..3e27609f3
--- /dev/null
+++ b/tests/.eslintrc.json
@@ -0,0 +1,25 @@
+{
+ "extends": [
+ "wikimedia/server"
+ ],
+ "env": {
+ "jest": true
+ },
+ "globals": {
+ "assert": "readonly",
+ "document": "readonly",
+ "jQuery": "readonly",
+ "Morebits": "readonly",
+ "mw": "readonly",
+ "Twinkle": "readonly",
+ "window": "readonly"
+ },
+ "root": true,
+ "rules": {
+ "array-bracket-spacing": "off",
+ "computed-property-spacing": "off",
+ "no-shadow": "off",
+ "object-curly-spacing": "off",
+ "space-in-parens": "off"
+ }
+}
diff --git a/tests/jest.setup.js b/tests/jest.setup.js
index 3b1780b03..cdbf0b532 100644
--- a/tests/jest.setup.js
+++ b/tests/jest.setup.js
@@ -1,7 +1,9 @@
+'use strict';
+
// Tweak some mw.configs as needed by tests
mw.config.set({
wgPageName: 'Macbeth,_King_of_Scotland',
- wgUserGroups: ['interface-admin', 'sysop', '*', 'user', 'autoconfirmed'],
+ wgUserGroups: ['interface-admin', 'sysop', '*', 'user', 'autoconfirmed']
});
require('../morebits.js');
@@ -16,9 +18,9 @@ assert.true = function (arg, message) {
if (arg !== true) {
throw new Error(message);
}
-}
+};
assert.false = function (arg, message) {
if (arg !== false) {
throw new Error(message);
}
-}
+};
diff --git a/tests/morebits.array.js b/tests/morebits.array.js
index c64b9d8a9..b8c29542c 100644
--- a/tests/morebits.array.js
+++ b/tests/morebits.array.js
@@ -1,3 +1,5 @@
+'use strict';
+
describe('Morebits.array', () => {
test('chunk', () => {
assert.deepEqual(Morebits.array.chunk([1, 2, 3, 4, 5, 6, 7, 8, 9, 10], 3), [[1, 2, 3], [4, 5, 6], [7, 8, 9], [10]], '10 over 3');
diff --git a/tests/morebits.batchOperation.js b/tests/morebits.batchOperation.js
index 38ec8e6b4..9fa045008 100644
--- a/tests/morebits.batchOperation.js
+++ b/tests/morebits.batchOperation.js
@@ -1,15 +1,17 @@
+'use strict';
+
describe('Morebits.batchOperation', () => {
test('Contruction', () => {
- assert.true(new Morebits.batchOperation() instanceof Morebits.batchOperation, 'Correct instance');
+ assert.true(new Morebits.BatchOperation() instanceof Morebits.batchOperation, 'Correct instance');
});
- var batch = new Morebits.batchOperation();
- var pageList = ['Macbeth', 'Hamlet', 'Romeo and Juliet', 'Much Ado About Nothing', 'Tempest'];
+ const batch = new Morebits.BatchOperation();
+ const pageList = ['Macbeth', 'Hamlet', 'Romeo and Juliet', 'Much Ado About Nothing', 'Tempest'];
batch.setPageList(pageList);
- var chunkLength = 2;
+ const chunkLength = 2;
batch.setOption('chunkSize', chunkLength);
test('Run', () => {
- var all = '';
- var runFunc = function (page) {
+ let all = '';
+ const runFunc = function (page) {
all += page;
batch.workerSuccess();
};
@@ -18,8 +20,8 @@ describe('Morebits.batchOperation', () => {
});
// Will leave a run hanging, who cares?
test('Chunksize', () => {
- var list = [];
- var runFunc = function (page) {
+ const list = [];
+ const runFunc = function (page) {
list.push(page);
};
batch.run(runFunc);
diff --git a/tests/morebits.createHtml.js b/tests/morebits.createHtml.js
index d6e2a97c5..07be8fe88 100644
--- a/tests/morebits.createHtml.js
+++ b/tests/morebits.createHtml.js
@@ -1,3 +1,5 @@
+'use strict';
+
describe('Morebits.createHtml', () => {
test('createHtml', () => {
@@ -23,17 +25,17 @@ describe('Morebits.createHtml', () => {
test('renderWikilinks', () => {
assert.strictEqual(
Morebits.createHtml.renderWikilinks('[[Main Page]]'),
- `Main Page`,
+ 'Main Page',
'simple link'
);
assert.strictEqual(
Morebits.createHtml.renderWikilinks('surrounding text [[Main Page|the main page]]'),
- `surrounding text the main page`,
+ 'surrounding text the main page',
'link with display text'
);
assert.strictEqual(
Morebits.createHtml.renderWikilinks('surrounding text [["Weird Al" Yankovic]]'),
- `surrounding text "Weird Al" Yankovic`,
+ 'surrounding text "Weird Al" Yankovic',
// jsdom in node turns " in title attribute into " whereas Chrome seems turns it into "
// but it works either way
'link with double quote'
@@ -41,7 +43,7 @@ describe('Morebits.createHtml', () => {
assert.strictEqual(
Morebits.createHtml.renderWikilinks('[[CODE]]
[[Yankovic]]'),
- `[[CODE]]
Yankovic`,
+ '[[CODE]]
Yankovic',
'wikilink in tag'
);
});
diff --git a/tests/morebits.date.js b/tests/morebits.date.js
index 6b7a2ef87..13f419ed3 100644
--- a/tests/morebits.date.js
+++ b/tests/morebits.date.js
@@ -1,24 +1,26 @@
+'use strict';
+
describe('Morebits.date', () => {
- var now = Date.now();
- var ts_mw = '16:26, 7 November 2020 (UTC)', ts_iso = '2020-11-07T16:26:00.000Z', naive = 20201107162600;
+ const now = Date.now();
+ const timestampMediaWiki = '16:26, 7 November 2020 (UTC)', timestampIso = '2020-11-07T16:26:00.000Z', naive = 20201107162600;
test('Construction', () => {
// getTime and toISOString imply testing of inherited methods
// Allow off-by-one values in milliseconds for not-quite-simultaneous date contructions
- expect(Math.abs(new Morebits.date().getTime() - new Date().getTime())).toBeLessThanOrEqual(1);
+ expect(Math.abs(new Morebits.Date().getTime() - Date.now())).toBeLessThanOrEqual(1);
- assert.strictEqual(new Morebits.date(now).getTime(), new Date(now).getTime(), 'Constructor from timestring');
- assert.strictEqual(new Morebits.date(2020, 11, 7, 16, 26).getTime(), new Date(2020, 11, 7, 16, 26).getTime(), 'Constructor from parts');
- assert.strictEqual(new Morebits.date(ts_mw).toISOString(), ts_iso, 'enWiki timestamp format');
- assert.strictEqual(new Morebits.date(naive).toISOString(), ts_iso, 'MediaWiki 14-digit number');
- assert.strictEqual(new Morebits.date(naive.toString()).toISOString(), ts_iso, 'MediaWiki 14-digit string');
- assert.strictEqual(new Morebits.date(parseInt(naive / 10, 10)).toISOString(), new Date(parseInt(naive / 10, 10)).toISOString(), 'native 13 digit');
- assert.strictEqual(new Morebits.date(naive * 10).toISOString(), new Date(naive * 10).toISOString(), 'native 15 digit');
+ assert.strictEqual(new Morebits.Date(now).getTime(), new Date(now).getTime(), 'Constructor from timestring');
+ assert.strictEqual(new Morebits.Date(2020, 11, 7, 16, 26).getTime(), new Date(2020, 11, 7, 16, 26).getTime(), 'Constructor from parts');
+ assert.strictEqual(new Morebits.Date(timestampMediaWiki).toISOString(), timestampIso, 'enWiki timestamp format');
+ assert.strictEqual(new Morebits.Date(naive).toISOString(), timestampIso, 'MediaWiki 14-digit number');
+ assert.strictEqual(new Morebits.Date(naive.toString()).toISOString(), timestampIso, 'MediaWiki 14-digit string');
+ assert.strictEqual(new Morebits.Date(parseInt(naive / 10, 10)).toISOString(), new Date(parseInt(naive / 10, 10)).toISOString(), 'native 13 digit');
+ assert.strictEqual(new Morebits.Date(naive * 10).toISOString(), new Date(naive * 10).toISOString(), 'native 15 digit');
});
- var date = new Morebits.date(ts_mw);
+ const date = new Morebits.Date(timestampMediaWiki);
test('Methods', () => {
assert.true(date.isValid(), 'Valid');
// Logs a message; not a failure, but annoying
- assert.false(new Morebits.date('no').isValid(), 'Invalid');
+ assert.false(new Morebits.Date('no').isValid(), 'Invalid');
// Ideally we would test the differences between UTC and non-UTC dates
assert.strictEqual(date.getUTCDayName(), 'Saturday', 'getUTCDayName');
@@ -26,7 +28,7 @@ describe('Morebits.date', () => {
assert.strictEqual(date.getUTCMonthName(), 'November', 'getUTCMonthName');
assert.strictEqual(date.getUTCMonthNameAbbrev(), 'Nov', 'getUTCMonthNameAbbrev');
- assert.true(new Morebits.date(now).isAfter(date), 'isAfter');
+ assert.true(new Morebits.Date(now).isAfter(date), 'isAfter');
assert.true(date.isBefore(new Date(now)), 'isBefore');
});
test('RegEx headers', () => {
@@ -41,25 +43,25 @@ describe('Morebits.date', () => {
assert.false(date.monthHeaderRegex().test('==December 2020=='), 'Wrong month');
});
test('add/subtract', () => {
- assert.strictEqual(new Morebits.date(ts_mw).add(1, 'day').toISOString(), '2020-11-08T16:26:00.000Z', 'Add 1 day');
- assert.strictEqual(new Morebits.date(ts_mw).add(1, 'DaY').toISOString(), '2020-11-08T16:26:00.000Z', 'Loudly add 1 day');
- assert.strictEqual(new Morebits.date(ts_mw).add('1', 'day').toISOString(), '2020-11-08T16:26:00.000Z', "Add 1 day but it's a string");
- assert.strictEqual(new Morebits.date(ts_mw).subtract(1, 'day').toISOString(), '2020-11-06T16:26:00.000Z', 'Subtract 1 day');
- assert.strictEqual(new Morebits.date(ts_mw).add(2, 'weeks').toISOString(), '2020-11-21T16:26:00.000Z', 'Add 2 weeks');
- assert.strictEqual(new Morebits.date(ts_mw).add(2, 'weeks').subtract(2, 'weeks').toISOString(), ts_iso, '2 weeks roundtrip'); // Note, this intentionally twice-crosses a US DST
+ assert.strictEqual(new Morebits.Date(timestampMediaWiki).add(1, 'day').toISOString(), '2020-11-08T16:26:00.000Z', 'Add 1 day');
+ assert.strictEqual(new Morebits.Date(timestampMediaWiki).add(1, 'DaY').toISOString(), '2020-11-08T16:26:00.000Z', 'Loudly add 1 day');
+ assert.strictEqual(new Morebits.Date(timestampMediaWiki).add('1', 'day').toISOString(), '2020-11-08T16:26:00.000Z', "Add 1 day but it's a string");
+ assert.strictEqual(new Morebits.Date(timestampMediaWiki).subtract(1, 'day').toISOString(), '2020-11-06T16:26:00.000Z', 'Subtract 1 day');
+ assert.strictEqual(new Morebits.Date(timestampMediaWiki).add(2, 'weeks').toISOString(), '2020-11-21T16:26:00.000Z', 'Add 2 weeks');
+ assert.strictEqual(new Morebits.Date(timestampMediaWiki).add(2, 'weeks').subtract(2, 'weeks').toISOString(), timestampIso, '2 weeks roundtrip'); // Note, this intentionally twice-crosses a US DST
- assert.strictEqual(new Morebits.date(ts_mw).add(1, 'second').toISOString(), '2020-11-07T16:26:01.000Z', 'Add 1 second');
- assert.strictEqual(new Morebits.date(ts_mw).add(1, 'minute').toISOString(), '2020-11-07T16:27:00.000Z', 'Add 1 minute');
- assert.strictEqual(new Morebits.date(ts_mw).add(1, 'hour').toISOString(), '2020-11-07T17:26:00.000Z', 'Add 1 hour');
- assert.strictEqual(new Morebits.date(ts_mw).add(1, 'month').toISOString(), '2020-12-07T16:26:00.000Z', 'Add 1 month');
- assert.strictEqual(new Morebits.date(ts_mw).add(1, 'year').toISOString(), '2021-11-07T16:26:00.000Z', 'Add 1 year');
+ assert.strictEqual(new Morebits.Date(timestampMediaWiki).add(1, 'second').toISOString(), '2020-11-07T16:26:01.000Z', 'Add 1 second');
+ assert.strictEqual(new Morebits.Date(timestampMediaWiki).add(1, 'minute').toISOString(), '2020-11-07T16:27:00.000Z', 'Add 1 minute');
+ assert.strictEqual(new Morebits.Date(timestampMediaWiki).add(1, 'hour').toISOString(), '2020-11-07T17:26:00.000Z', 'Add 1 hour');
+ assert.strictEqual(new Morebits.Date(timestampMediaWiki).add(1, 'month').toISOString(), '2020-12-07T16:26:00.000Z', 'Add 1 month');
+ assert.strictEqual(new Morebits.Date(timestampMediaWiki).add(1, 'year').toISOString(), '2021-11-07T16:26:00.000Z', 'Add 1 year');
- assert.throws(() => new Morebits.date(ts_mw).add('forty-two'), 'throws: non-number provided');
- assert.throws(() => new Morebits.date(ts_mw).add(1), 'throws: no unit');
- assert.throws(() => new Morebits.date(ts_mw).subtract(1, 'dayo'), 'throws: bad unit');
+ assert.throws(() => new Morebits.Date(timestampMediaWiki).add('forty-two'), 'throws: non-number provided');
+ assert.throws(() => new Morebits.Date(timestampMediaWiki).add(1), 'throws: no unit');
+ assert.throws(() => new Morebits.Date(timestampMediaWiki).subtract(1, 'dayo'), 'throws: bad unit');
});
test('Formats', () => {
- assert.strictEqual(new Morebits.date(now).format('YYYY-MM-DDTHH:mm:ss.SSSZ', 'utc'), new Date(now).toISOString(), 'ISO format');
+ assert.strictEqual(new Morebits.Date(now).format('YYYY-MM-DDTHH:mm:ss.SSSZ', 'utc'), new Date(now).toISOString(), 'ISO format');
assert.strictEqual(date.format('dddd D MMMM YY h:mA', 'utc'), 'Saturday 7 November 20 4:26PM', 'Some weirder stuff');
assert.strictEqual(date.format('MMt[h month], [d]a[y] D, h [o\'clock] A', 'utc'), '11th month, day 7, 4 o\'clock PM', 'Format escapes');
assert.strictEqual(date.format('dddd D MMMM YY h:mA', 600), 'Sunday 8 November 20 2:26AM', 'non-UTC formatting');
@@ -68,7 +70,7 @@ describe('Morebits.date', () => {
test('Calendar', () => {
assert.strictEqual(date.calendar('utc'), '2020-11-07', 'Old calendar');
assert.strictEqual(date.calendar(600), '2020-11-08', 'Old non-UTC');
- assert.strictEqual(new Morebits.date(now).calendar('utc'), 'Today at ' + new Morebits.date(now).format('h:mm A', 'utc'), 'New calendar');
- assert.strictEqual(new Morebits.date(now).subtract(1, 'day').calendar('utc'), 'Yesterday at ' + new Morebits.date(now).format('h:mm A', 'utc'), 'Close calendar');
+ assert.strictEqual(new Morebits.Date(now).calendar('utc'), 'Today at ' + new Morebits.Date(now).format('h:mm A', 'utc'), 'New calendar');
+ assert.strictEqual(new Morebits.Date(now).subtract(1, 'day').calendar('utc'), 'Yesterday at ' + new Morebits.Date(now).format('h:mm A', 'utc'), 'Close calendar');
});
});
diff --git a/tests/morebits.ip.js b/tests/morebits.ip.js
index 06e5b5516..d4f2da800 100644
--- a/tests/morebits.ip.js
+++ b/tests/morebits.ip.js
@@ -1,3 +1,5 @@
+'use strict';
+
describe('Morebits.ip', () => {
test('sanitizeIPv6', () => {
assert.strictEqual(Morebits.ip.sanitizeIPv6('2001:0db8:0010:0000:0000:0000:0000:0001'), '2001:DB8:10:0:0:0:0:1', 'Shorten IPv6');
diff --git a/tests/morebits.js b/tests/morebits.js
index 741eb212a..eb03a660f 100644
--- a/tests/morebits.js
+++ b/tests/morebits.js
@@ -1,3 +1,5 @@
+'use strict';
+
describe('constants', () => {
test('userIsSysop', () => {
assert.true(Morebits.userIsSysop, 'Is sysop');
@@ -18,7 +20,7 @@ describe('methods', () => {
assert.strictEqual(Morebits.pageNameRegex(''), '', 'Empty');
assert.strictEqual(Morebits.pageNameRegex('a'), '[Aa]', 'Single character');
assert.strictEqual(Morebits.pageNameRegex('#'), '#', 'Single same-case');
- assert.strictEqual(Morebits.pageNameRegex('*$, \{}(a) |.?+-^ [ ]'), '\\*\\$,[_ ]\\{\\}\\(a\\)[_ ]\\|\\.\\?\\+\\-\\^\[_ ]\\[[_ ]\\]', 'Special characters');
+ assert.strictEqual(Morebits.pageNameRegex('*$, {}(a) |.?+-^ [ ]'), '\\*\\$,[_ ]\\{\\}\\(a\\)[_ ]\\|\\.\\?\\+\\-\\^[_ ]\\[[_ ]\\]', 'Special characters');
});
test('namespaceRegex', () => {
assert.strictEqual(Morebits.namespaceRegex([6]), '(?:[Ff][Ii][Ll][Ee]|[Ii][Mm][Aa][Gg][Ee])', 'Files');
diff --git a/tests/morebits.quickForm.js b/tests/morebits.quickForm.js
index 42b7817aa..c3f2d5e4e 100644
--- a/tests/morebits.quickForm.js
+++ b/tests/morebits.quickForm.js
@@ -1,77 +1,83 @@
-/** Simple helper to render a quickform element */
+'use strict';
+
+/**
+ * Simple helper to render a quickform element
+ *
+ * @param data
+ */
function renderElement(data) {
- return new Morebits.quickForm.element(data).render();
+ return new Morebits.QuickForm.Element(data).render();
}
-describe("quickform", () => {
- let inputConfig = {
- type: "input",
- label: "Label",
- name: "inputname",
- value: "prefilled value",
+describe('quickform', () => {
+ const inputConfig = {
+ type: 'input',
+ label: 'Label',
+ name: 'inputname',
+ value: 'prefilled value'
};
- let selectConfig = {
- type: "select",
- label: "Select label",
- name: "selectname",
+ const selectConfig = {
+ type: 'select',
+ label: 'Select label',
+ name: 'selectname',
list: [
- { label: "select label 1", value: "selectvalue1" },
- { label: "select label 2", value: "selectvalue2" },
- ],
+ { label: 'select label 1', value: 'selectvalue1' },
+ { label: 'select label 2', value: 'selectvalue2' }
+ ]
};
- let checkboxListConfig = {
- type: "checkbox",
- name: "checkboxlist1",
+ const checkboxListConfig = {
+ type: 'checkbox',
+ name: 'checkboxlist1',
list: [
- { label: "checkbox 1", value: "checkval1" },
- { label: "checkbox 2", value: "checkval2", checked: true },
- ],
+ { label: 'checkbox 1', value: 'checkval1' },
+ { label: 'checkbox 2', value: 'checkval2', checked: true }
+ ]
};
- let checkboxesConfig = {
- type: "checkbox",
+ const checkboxesConfig = {
+ type: 'checkbox',
list: [
{
- label: "checkbox 1",
- value: "checkval1",
- name: "checkname1",
- checked: true,
+ label: 'checkbox 1',
+ value: 'checkval1',
+ name: 'checkname1',
+ checked: true
},
- { label: "checkbox 2", value: "checkval2", name: "checkname2" },
- ],
+ { label: 'checkbox 2', value: 'checkval2', name: 'checkname2' }
+ ]
};
- let radiosConfig = {
- type: "radio",
- name: "radiolist1",
+ const radiosConfig = {
+ type: 'radio',
+ name: 'radiolist1',
list: [
{
- label: "radio 1",
- value: "radioval1",
- name: "radioname1",
+ label: 'radio 1',
+ value: 'radioval1',
+ name: 'radioname1'
},
{
- label: "radio 2",
- value: "radioval2",
- name: "radioname2",
- checked: true,
- },
- ],
+ label: 'radio 2',
+ value: 'radioval2',
+ name: 'radioname2',
+ checked: true
+ }
+ ]
};
- let textareaConfig = {
- type: "textarea",
- name: "textareaname1",
- value: "textarea prefilled value",
- cols: 4,
+ const textareaConfig = {
+ type: 'textarea',
+ name: 'textareaname1',
+ value: 'textarea prefilled value',
+ cols: 4
};
- let submitConfig = {
- type: "submit",
+ const submitConfig = {
+ type: 'submit'
};
- let buttonConfig = {
- type: "button",
- label: "button label",
+ const buttonConfig = {
+ type: 'button',
+ label: 'button label'
};
- let getRenderedForm = () => {
- let form = new Morebits.quickForm(function () {});
+ const getRenderedForm = () => {
+ const form = new Morebits.QuickForm(() => {});
form.append(inputConfig);
form.append(checkboxesConfig);
form.append(checkboxListConfig);
@@ -80,42 +86,42 @@ describe("quickform", () => {
form.append(submitConfig);
form.append(buttonConfig);
return form.render();
- }
+ };
- test("input element", () => {
+ test('input element', () => {
expect(renderElement(inputConfig)).toMatchSnapshot();
});
- test("select element", () => {
+ test('select element', () => {
expect(renderElement(selectConfig)).toMatchSnapshot();
});
- test("checkbox elements", () => {
+ test('checkbox elements', () => {
expect(renderElement(checkboxListConfig)).toMatchSnapshot();
});
- test("checkbox elements (with data-single attribute)", () => {
+ test('checkbox elements (with data-single attribute)', () => {
expect(renderElement(checkboxesConfig)).toMatchSnapshot();
});
- test("radio elements", () => {
+ test('radio elements', () => {
expect(renderElement(radiosConfig)).toMatchSnapshot();
});
- test("textarea element", () => {
+ test('textarea element', () => {
expect(renderElement(textareaConfig)).toMatchSnapshot();
});
- test("submit", () => {
+ test('submit', () => {
expect(renderElement(submitConfig)).toMatchSnapshot();
});
- test("getInputData", () => {
+ test('getInputData', () => {
expect(Morebits.quickForm.getInputData(getRenderedForm())).toMatchSnapshot();
});
- test("getElements", () => {
- let form = getRenderedForm();
+ test('getElements', () => {
+ const form = getRenderedForm();
expect(Morebits.quickForm.getElements(form, 'checkboxlist1')).toMatchSnapshot();
});
diff --git a/tests/morebits.string.js b/tests/morebits.string.js
index 43505b9c7..bce71c9b9 100644
--- a/tests/morebits.string.js
+++ b/tests/morebits.string.js
@@ -1,27 +1,29 @@
+'use strict';
+
describe('Morebits.string', () => {
test('escapeRegExp', () => {
assert.strictEqual(Morebits.string.escapeRegExp('Four score and seven years ago'), 'Four[_ ]score[_ ]and[_ ]seven[_ ]years[_ ]ago', 'Spaces');
assert.strictEqual(Morebits.string.escapeRegExp('Four_score_and_seven_years_ago'), 'Four[_ ]score[_ ]and[_ ]seven[_ ]years[_ ]ago', 'Underscores');
});
test('formatReasonForLog', () => {
- var reason = 'They were wrong';
+ const reason = 'They were wrong';
assert.strictEqual(Morebits.string.formatReasonForLog(reason), reason, 'Simple, unchanged');
- var more = 'Really wrong';
+ const more = 'Really wrong';
assert.strictEqual(Morebits.string.formatReasonForLog(reason + '\n' + more), reason + '{{pb}}' + more, '\n -> {{pb}}');
assert.strictEqual(Morebits.string.formatReasonForLog('#' + reason + '\n' + more), '##' + reason + '{{pb}}' + more, 'Prepend extra #');
assert.strictEqual(Morebits.string.formatReasonForLog('*' + reason + '\n' + more), '#*' + reason + '{{pb}}' + more, 'Prepend extra #');
});
test('formatReasonText', () => {
- var reason = 'They were correct';
+ let reason = 'They were correct';
assert.strictEqual(Morebits.string.formatReasonText(reason), reason, 'Simple, unchanged');
assert.strictEqual(Morebits.string.formatReasonText(reason, true), reason + ' ~~~~', 'Simple');
- var more = 'Technically correct';
+ const more = 'Technically correct';
assert.strictEqual(Morebits.string.formatReasonText(reason + '|' + more), reason + '{{subst:!}}' + more, 'Replace pipe');
assert.strictEqual(Morebits.string.formatReasonText(reason + '|' + more, true), reason + '{{subst:!}}' + more + ' ~~~~', 'Replace pipe');
reason += 'The {{best|kind|of}} correct: ';
assert.strictEqual(Morebits.string.formatReasonText(reason + more), reason + more, 'No replace in nowiki');
assert.strictEqual(Morebits.string.formatReasonText(), '', 'Empty');
- var alreadySigned = 'already signed ~~~~';
+ const alreadySigned = 'already signed ~~~~';
assert.strictEqual(Morebits.string.formatReasonText(alreadySigned, true), alreadySigned, 'No sig duplication');
assert.strictEqual(Morebits.string.formatReasonText('alreadySigned~~~~ ', true), 'alreadySigned~~~~', 'trims and avoids duplicating sig');
assert.strictEqual(Morebits.string.formatReasonText('Wow', true), 'Wow ~~~~', '3-letter reason');
@@ -38,13 +40,13 @@ describe('Morebits.string', () => {
assert.false(Morebits.string.isInfinity('2020-04-17T09:31:00.000Z'), 'ISO string');
});
test('safeReplace', () => {
- var string = '{{subst:board|thread=$SECTION|but=$NOTTHIS}} ~~~~';
+ const string = '{{subst:board|thread=$SECTION|but=$NOTTHIS}} ~~~~';
assert.strictEqual(Morebits.string.safeReplace(string, '$SECTIONAL', 'thread$'), string, 'No replacement');
assert.strictEqual(Morebits.string.safeReplace(string, '$SECTION', 'thread$'), '{{subst:board|thread=thread$|but=$NOTTHIS}} ~~~~', 'Replacement');
});
test('splitWeightedByKeys', () => {
- var split = ['{{thisis|one|template}}', '{{another|one}}', '[[heresalink]]', '[[thislink|ispiped]]'];
- var text = split.join(' also ');
+ const split = ['{{thisis|one|template}}', '{{another|one}}', '[[heresalink]]', '[[thislink|ispiped]]'];
+ const text = split.join(' also ');
assert.deepEqual(Morebits.string.splitWeightedByKeys(text, '{{', '}}'), split.slice(0, 2), 'Templates');
assert.deepEqual(Morebits.string.splitWeightedByKeys(text, '[[', ']]'), split.slice(2), 'Links');
assert.deepEqual(Morebits.string.splitWeightedByKeys(text, '{{', '}}', split[0]), [split[1]], 'Skiplist, non-array');
diff --git a/tests/morebits.taskManager.js b/tests/morebits.taskManager.js
index e3d8e48bf..bcd03db49 100644
--- a/tests/morebits.taskManager.js
+++ b/tests/morebits.taskManager.js
@@ -1,13 +1,15 @@
+'use strict';
+
describe('Morebits.taskManager', () => {
test('Contruction', () => {
- var tm = new Morebits.taskManager();
+ const tm = new Morebits.TaskManager();
assert.true(tm instanceof Morebits.taskManager, 'Correct instance');
});
// Helper to generate functions as well as testing output in proper order;
// verifySteps not used because it would require some extra duplication
- var data = {};
- var generateFuncs = () => {
+ const data = {};
+ const generateFuncs = () => {
data.out = [];
['one', 'two', 'three', 'four'].forEach((step) => {
data[step] = () => {
@@ -19,7 +21,7 @@ describe('Morebits.taskManager', () => {
test('Simple', () => {
generateFuncs();
- var simple = new Morebits.taskManager();
+ const simple = new Morebits.TaskManager();
simple.add(data.one, []);
simple.add(data.two, [data.one]);
simple.add(data.three, [data.two]);
@@ -30,7 +32,7 @@ describe('Morebits.taskManager', () => {
});
test('Complex', () => {
generateFuncs();
- var complex = new Morebits.taskManager();
+ const complex = new Morebits.TaskManager();
complex.add(data.one, [data.two]);
complex.add(data.two, [data.three, data.four]);
complex.add(data.three, []);
diff --git a/tests/morebits.unbinder.js b/tests/morebits.unbinder.js
index fa3419557..4c4cd6644 100644
--- a/tests/morebits.unbinder.js
+++ b/tests/morebits.unbinder.js
@@ -1,19 +1,21 @@
+'use strict';
+
describe('Morebits.unbinder', () => {
test('Construction', () => {
- assert.throws(() => new Morebits.unbinder(), 'throws: no string');
- assert.throws(() => new Morebits.unbinder([42]), 'throws: not a string');
- var u = new Morebits.unbinder('Hello world');
+ assert.throws(() => new Morebits.Unbinder(), 'throws: no string');
+ assert.throws(() => new Morebits.Unbinder([42]), 'throws: not a string');
+ const u = new Morebits.Unbinder('Hello world');
assert.true(u instanceof Morebits.unbinder, 'Correct instance');
assert.throws(() => u.unbind(), 'throws: Missing prefix');
assert.throws(() => u.unbind('w'), 'throws: Missing postfix');
});
test('Run', () => {
- var u = new Morebits.unbinder('Hello world world');
+ let u = new Morebits.Unbinder('Hello world world');
u.unbind('');
u.content = u.content.replace(/world/g, 'earth');
assert.strictEqual(u.rebind(), 'Hello earth earth', 'Simple replace');
- u = new Morebits.unbinder('Hello world world [link link] [[link|link]]');
+ u = new Morebits.Unbinder('Hello world world [link link] [[link|link]]');
assert.true(u instanceof Morebits.unbinder, 'Correct instance');
u.unbind('');
u.unbind('\\[\\[', '\\]\\]');
diff --git a/tests/morebits.wikitext.js b/tests/morebits.wikitext.js
index c1942878d..a6e5a3b45 100644
--- a/tests/morebits.wikitext.js
+++ b/tests/morebits.wikitext.js
@@ -1,15 +1,17 @@
+'use strict';
+
describe('Morebits.wikitext', () => {
test('parseTemplate', () => {
// Function to help build a template from a sample object
- var makeTemplate = function (data) {
- var template = '{{' + data.name;
- Object.keys(data.parameters).forEach(function (key) {
+ const makeTemplate = function (data) {
+ let template = '{{' + data.name;
+ Object.keys(data.parameters).forEach((key) => {
template += '|' + key + '=' + data.parameters[key];
});
return template + '}}';
};
- var simple = {
+ const simple = {
name: 'prod',
parameters: {
reason: 'because',
@@ -19,7 +21,7 @@ describe('Morebits.wikitext', () => {
};
assert.deepEqual(Morebits.wikitext.parseTemplate('Template: ' + makeTemplate(simple) + ' in text', 10), simple, 'Basic parameters');
- var involved = {
+ const involved = {
name: 'Proposed deletion/dated',
parameters: {
concern: 'Text (paren) then [[piped|link]] and [[WP:WP/LINK]] {{{plural|with|a|template}}} then question?',
@@ -31,10 +33,10 @@ describe('Morebits.wikitext', () => {
assert.deepEqual(Morebits.wikitext.parseTemplate(makeTemplate(involved)), involved, 'Involved parameters');
// Try a variety of whitespace options
- var whitespace = '{{' + involved.name + ' |concern = ' + involved.parameters.concern + ' | timestamp =' + involved.parameters.timestamp + '| nom= ' + involved.parameters.nom + '|help = ' + involved.parameters.help + ' }}';
+ const whitespace = '{{' + involved.name + ' |concern = ' + involved.parameters.concern + ' | timestamp =' + involved.parameters.timestamp + '| nom= ' + involved.parameters.nom + '|help = ' + involved.parameters.help + ' }}';
assert.deepEqual(Morebits.wikitext.parseTemplate(whitespace), involved, 'Involved parameters with whitespace');
- var unnamed = {
+ const unnamed = {
name: 'db-meta',
parameters: {
criterion: 'G13',
@@ -43,10 +45,10 @@ describe('Morebits.wikitext', () => {
2: 'extra'
}
};
- var unnamedTemplate = '{{' + unnamed.name + '|criterion=' + unnamed.parameters.criterion + '||' + unnamed.parameters['1'] + '| middle =|2= ' + unnamed.parameters['2'] + '|}}';
+ const unnamedTemplate = '{{' + unnamed.name + '|criterion=' + unnamed.parameters.criterion + '||' + unnamed.parameters['1'] + '| middle =|2= ' + unnamed.parameters['2'] + '|}}';
assert.deepEqual(Morebits.wikitext.parseTemplate(unnamedTemplate), unnamed, 'Unnamed and empty parameters');
- var multiLevel = {
+ const multiLevel = {
name: 'toplevel',
parameters: {
named: '{{namedtop}}',
@@ -56,7 +58,7 @@ describe('Morebits.wikitext', () => {
}
};
assert.deepEqual(Morebits.wikitext.parseTemplate(makeTemplate(multiLevel)), multiLevel, 'Multiple levels');
- var parser = {
+ const parser = {
name: 'toplevel',
parameters: {
named: '{{namedtop}}',
@@ -67,7 +69,7 @@ describe('Morebits.wikitext', () => {
};
assert.deepEqual(Morebits.wikitext.parseTemplate(makeTemplate(parser)), parser, 'Parser function');
- var internal = {
+ const internal = {
name: 'internal',
parameters: {
named: 'parameter {{tq|with an internal}} template',
@@ -80,18 +82,18 @@ describe('Morebits.wikitext', () => {
});
test('Morebits.wikitext.page', () => {
- var text = '{{short description}}{{about}}[[File:Fee.svg]]O, [[Juliet|she]] doth {{plural|teach}} the torches to burn bright!';
- var page = new Morebits.wikitext.page(text);
+ const text = '{{short description}}{{about}}[[File:Fee.svg]]O, [[Juliet|she]] doth {{plural|teach}} the torches to burn bright!';
+ const page = new Morebits.wikitext.Page(text);
assert.true(page instanceof Morebits.wikitext.page, 'Correct instance');
assert.strictEqual(page.getText(), text, 'Got text');
// Throws
- assert.throws(() => new Morebits.wikitext.page(text).insertAfterTemplates(), 'throws: no tag');
- assert.throws(() => new Morebits.wikitext.page(text).insertAfterTemplates('tag'), 'throws: no regex');
+ assert.throws(() => new Morebits.wikitext.Page(text).insertAfterTemplates(), 'throws: no tag');
+ assert.throws(() => new Morebits.wikitext.Page(text).insertAfterTemplates('tag'), 'throws: no regex');
// Define all the tests individually, with the appropriate method,
// input, expected output, and (spreaded) parameters.
- var tests = [
+ const tests = [
{
name: 'simple',
method: 'removeLink',
@@ -354,7 +356,7 @@ describe('Morebits.wikitext', () => {
];
tests.forEach((test) => {
- var page = new Morebits.wikitext.page(test.input);
+ const page = new Morebits.wikitext.Page(test.input);
assert.strictEqual(page[test.method](...test.params).getText(), test.expected, test.method + ' - ' + test.name);
});
});
diff --git a/twinkle.js b/twinkle.js
index c6041c408..4e9e012c0 100644
--- a/twinkle.js
+++ b/twinkle.js
@@ -375,7 +375,7 @@ Twinkle.load = function () {
activeSpecialPageList = activeSpecialPageList.concat([ 'DeletedContributions', 'Prefixindex' ]);
}
if (mw.config.get('wgNamespaceNumber') === -1 &&
- activeSpecialPageList.indexOf(mw.config.get('wgCanonicalSpecialPageName')) === -1) {
+ !activeSpecialPageList.includes(mw.config.get('wgCanonicalSpecialPageName'))) {
return;
}
@@ -392,7 +392,7 @@ Twinkle.load = function () {
// Redefine addInitCallback so that any modules being loaded now on are directly
// initialised rather than added to initCallbacks array
Twinkle.addInitCallback = function(func, name) {
- if (!name || Twinkle.disabledModules.indexOf(name) === -1) {
+ if (!name || !Twinkle.disabledModules.includes(name)) {
func();
}
};