jenkins-bot has submitted this change and it was merged.
Change subject: Allow IP whitelist to be modified on wiki
......................................................................
Allow IP whitelist to be modified on wiki
Local administrators can now use [[MediaWiki:Captcha-ip-whitelist]]
page to exempt specific IP addresses and IP ranges from captchas.
This is useful for modifying in a short notice such as editathons and
other events like this where captchas add unnecessary complexity for
new users.
The page is disabled by default and IPs should be added separated by
newlines. If any other character is found on a line, it will be ignored
but leading and trailing whitespace characters are allowed.
Bug: T103122
Change-Id: I54866b5bfca80debcf3d3fb7963932ed03b48548
---
M SimpleCaptcha/Captcha.php
M extension.json
M i18n/en.json
M i18n/qqq.json
M includes/ConfirmEditHooks.php
5 files changed, 110 insertions(+), 10 deletions(-)
Approvals:
Florianschmidtwelzow: Looks good to me, approved
jenkins-bot: Verified
diff --git a/SimpleCaptcha/Captcha.php b/SimpleCaptcha/Captcha.php
index cd61d02..7697ab7 100755
--- a/SimpleCaptcha/Captcha.php
+++ b/SimpleCaptcha/Captcha.php
@@ -281,26 +281,91 @@
}
/**
- * Check if the IP is allowed to skip captchas
+ * Check if the current IP is allowed to skip captchas. This checks
+ * the whitelist from two sources.
+ * 1) From the server-side config array $wgCaptchaWhitelistIP
+ * 2) From the local [[MediaWiki:Captcha-ip-whitelist]] message
+ *
+ * @return bool true if whitelisted, false if not
*/
function isIPWhitelisted() {
- global $wgCaptchaWhitelistIP;
+ global $wgCaptchaWhitelistIP, $wgRequest;
+ $ip = $wgRequest->getIP();
if ( $wgCaptchaWhitelistIP ) {
- global $wgRequest;
-
- $ip = $wgRequest->getIP();
-
- foreach ( $wgCaptchaWhitelistIP as $range ) {
- if ( IP::isInRange( $ip, $range ) ) {
- return true;
- }
+ if ( IP::isInRanges( $ip, $wgCaptchaWhitelistIP ) ) {
+ return true;
}
}
+
+ $whitelistMsg = wfMessage( 'captcha-ip-whitelist'
)->inContentLanguage();
+ if ( !$whitelistMsg->isDisabled() ) {
+ $whitelistedIPs = $this->getWikiIPWhitelist(
$whitelistMsg );
+ if ( IP::isInRanges( $ip, $whitelistedIPs ) ) {
+ return true;
+ }
+ }
+
return false;
}
/**
+ * Get the on-wiki IP whitelist stored in
[[MediaWiki:Captcha-ip-whitelist]]
+ * page from cache if possible.
+ *
+ * @param Message $msg whitelist Message on wiki
+ * @return array whitelisted IP addresses or IP ranges, empty array if
no whitelist
+ */
+ private function getWikiIPWhitelist( Message $msg ) {
+ $cache = ObjectCache::getMainWANInstance();
+ $cacheKey = $cache->makeKey( 'confirmedit', 'ipwhitelist' );
+
+ $cachedWhitelist = $cache->get( $cacheKey );
+ if ( $cachedWhitelist === false ) {
+ // Could not retrieve from cache so build the whitelist
directly
+ // from the wikipage
+ $whitelist = $this->buildValidIPs(
+ explode( "\n", $msg->plain() )
+ );
+ // And then store it in cache for one day. This cache
is cleared on
+ // modifications to the whitelist page.
+ // @see ConfirmEditHooks::onPageContentSaveComplete()
+ $cache->set( $cacheKey, $whitelist, 86400 );
+ } else {
+ // Whitelist from the cache
+ $whitelist = $cachedWhitelist;
+ }
+
+ return $whitelist;
+ }
+
+ /**
+ * From a list of unvalidated input, get all the valid
+ * IP addresses and IP ranges from it.
+ *
+ * Note that only lines with just the IP address or IP range is
considered
+ * as valid. Whitespace is allowed but if there is any other character
on
+ * the line, it's not considered as a valid entry.
+ *
+ * @param string[] $input
+ * @return string[] of valid IP addresses and IP ranges
+ */
+ private function buildValidIPs( array $input ) {
+ // Remove whitespace and blank lines first
+ $ips = array_map( 'trim', $input );
+ $ips = array_filter( $ips );
+
+ $validIPs = array();
+ foreach ( $ips as $ip ) {
+ if ( IP::isIPAddress( $ip ) ) {
+ $validIPs[] = $ip;
+ }
+ }
+
+ return $validIPs;
+ }
+
+ /**
* Internal cache key for badlogin checks.
* @return string
* @access private
diff --git a/extension.json b/extension.json
index 4eb01ef..89db1b0 100644
--- a/extension.json
+++ b/extension.json
@@ -79,6 +79,9 @@
"EmailUser": [
"ConfirmEditHooks::confirmEmailUser"
],
+ "PageContentSaveComplete": [
+ "ConfirmEditHooks::onPageContentSaveComplete"
+ ],
"EditPage::showEditForm:fields": [
"ConfirmEditHooks::showEditFormFields"
],
diff --git a/i18n/en.json b/i18n/en.json
index 8977ab5..84d27ab 100644
--- a/i18n/en.json
+++ b/i18n/en.json
@@ -6,6 +6,7 @@
"captcha-edit-fail": "Incorrect or missing CAPTCHA.",
"captcha-desc": "Provides CAPTCHA techniques to protect against spam
and password-guessing",
"captcha-label": "CAPTCHA",
+ "captcha-ip-whitelist": "-",
"captcha-addurl": "Your edit includes new external links.\nTo protect
the wiki against automated spam, we kindly ask you to solve the simple sum
below and enter the answer in the box in order to save your edit
([[Special:Captcha/help|more info]]):",
"captcha-badlogin": "To protect the wiki against automated password
cracking, we kindly ask you to solve the simple sum below and enter the answer
in the box ([[Special:Captcha/help|more info]]):",
"captcha-createaccount": "To protect the wiki against automated account
creation, we kindly ask you to solve the simple sum below and enter the answer
in the box ([[Special:Captcha/help|more info]]):",
diff --git a/i18n/qqq.json b/i18n/qqq.json
index 9890932..1b6c757 100644
--- a/i18n/qqq.json
+++ b/i18n/qqq.json
@@ -18,6 +18,7 @@
"captcha-edit-fail": "Used as failure message.\n\nSee also:\n*
{{msg-mw|Captcha-createaccount-fail}}\n* {{msg-mw|Captcha-sendemail-fail}}",
"captcha-desc": "{{desc|name=Confirm
Edit|url=https://www.mediawiki.org/wiki/Extension:ConfirmEdit}}",
"captcha-label": "Label field for input field shown in forms",
+ "captcha-ip-whitelist": "{{Notranslate}} This message is used for
storing a list of IP addresses and IP ranges whitelisted from CAPTCHA on the
wiki. New entries should be separated by newlines and the line should contain
only a valid IP address or IP range. Leading and trailing whitespace is allowed
but if there is any other character, that line will be ignored.",
"captcha-addurl": "The explanation of CAPTCHA shown to users trying to
add new external links.\n{{Related|ConfirmEdit-addurl}}",
"captcha-badlogin": "The explanation of CAPTCHA shown to users failed
three times to type in correct password.\n{{Related|ConfirmEdit-badlogin}}",
"captcha-createaccount": "The explanation of CAPTCHA shown to users
trying to create a new account.\n{{Related|ConfirmEdit-createaccount}}",
diff --git a/includes/ConfirmEditHooks.php b/includes/ConfirmEditHooks.php
index de5b36e..30585ca 100644
--- a/includes/ConfirmEditHooks.php
+++ b/includes/ConfirmEditHooks.php
@@ -24,6 +24,36 @@
$user, $minorEdit );
}
+ /**
+ * PageContentSaveComplete hook handler.
+ * Clear IP whitelist cache on page saves for
[[MediaWiki:captcha-ip-whitelist]].
+ *
+ * @param Page $wikiPage
+ * @param User $user
+ * @param Content $content
+ * @param string $summary
+ * @param bool $isMinor
+ * @param bool $isWatch
+ * @param string $section
+ * @param int $flags
+ * @param int $revision
+ * @param Status $status
+ * @param int $baseRevId
+ *
+ * @return bool true
+ */
+ static function onPageContentSaveComplete( Page $wikiPage, User $user,
Content $content, $summary,
+ $isMinor, $isWatch, $section, $flags, $revision, Status
$status, $baseRevId
+ ) {
+ $title = $wikiPage->getTitle();
+ if ( $title->getText() === 'Captcha-ip-whitelist' &&
$title->getNamespace() === NS_MEDIAWIKI ) {
+ $cache = ObjectCache::getMainWANInstance();
+ $cache->delete( $cache->makeKey( 'confirmedit',
'ipwhitelist' ) );
+ }
+
+ return true;
+ }
+
static function confirmEditPage( $editpage, $buttons, $tabindex ) {
self::getInstance()->editShowCaptcha( $editpage );
}
--
To view, visit https://gerrit.wikimedia.org/r/275528
To unsubscribe, visit https://gerrit.wikimedia.org/r/settings
Gerrit-MessageType: merged
Gerrit-Change-Id: I54866b5bfca80debcf3d3fb7963932ed03b48548
Gerrit-PatchSet: 4
Gerrit-Project: mediawiki/extensions/ConfirmEdit
Gerrit-Branch: master
Gerrit-Owner: Glaisher <[email protected]>
Gerrit-Reviewer: Florianschmidtwelzow <[email protected]>
Gerrit-Reviewer: Glaisher <[email protected]>
Gerrit-Reviewer: Siebrand <[email protected]>
Gerrit-Reviewer: jenkins-bot <>
_______________________________________________
MediaWiki-commits mailing list
[email protected]
https://lists.wikimedia.org/mailman/listinfo/mediawiki-commits