From fd130247c28da68c351029124d8ddf1ad77db3f7 Mon Sep 17 00:00:00 2001 From: Petr Pchelko Date: Wed, 21 Aug 2019 15:42:08 -0700 Subject: [PATCH] Deprecate and replace usages of User:isAllowed{All,Any} Bug: T220191 Change-Id: I197b8fadaa93e7b320fc19c10e3e09387fe09ad2 --- includes/Permissions/PermissionManager.php | 52 +++++++++++++++---- includes/api/ApiBase.php | 4 +- includes/api/ApiComparePages.php | 4 +- includes/api/ApiQueryAllDeletedRevisions.php | 4 +- includes/api/ApiQueryAllRevisions.php | 4 +- includes/api/ApiQueryBase.php | 3 +- includes/api/ApiQueryDeletedRevisions.php | 4 +- includes/api/ApiQueryDeletedrevs.php | 4 +- includes/api/ApiQueryFilearchive.php | 4 +- includes/api/ApiQueryInfo.php | 4 +- includes/api/ApiQueryLogEvents.php | 4 +- includes/api/ApiQueryRecentChanges.php | 8 ++- includes/api/ApiQueryRevisions.php | 4 +- includes/api/ApiQueryUserContribs.php | 4 +- includes/auth/AuthManager.php | 5 +- includes/logging/LogEventsList.php | 4 +- includes/logging/LogPager.php | 12 ++++- includes/page/ImageHistoryList.php | 9 +++- includes/page/WikiPage.php | 5 +- includes/skins/Skin.php | 4 +- includes/skins/SkinTemplate.php | 5 +- includes/specials/SpecialImport.php | 6 ++- includes/specials/SpecialLog.php | 5 +- includes/specials/SpecialWatchlist.php | 5 +- .../specials/forms/PreferencesFormOOUI.php | 7 ++- includes/specials/pagers/ContribsPager.php | 5 +- .../specials/pagers/DeletedContribsPager.php | 5 +- includes/user/User.php | 26 ++++------ tests/phpunit/includes/api/ApiOptionsTest.php | 3 +- .../specials/SpecialPreferencesTest.php | 5 +- 30 files changed, 161 insertions(+), 57 deletions(-) diff --git a/includes/Permissions/PermissionManager.php b/includes/Permissions/PermissionManager.php index 2d4885ecb1..bd88c17a9c 100644 --- a/includes/Permissions/PermissionManager.php +++ b/includes/Permissions/PermissionManager.php @@ -827,7 +827,7 @@ class PermissionManager { * Check restrictions on cascading pages. * * @param string $action The action to check - * @param User $user User to check + * @param UserIdentity $user User to check * @param array $errors List of current errors * @param string $rigor One of PermissionManager::RIGOR_ constants * - RIGOR_QUICK : does cheap permission checks from replica DBs (usable for GUI creation) @@ -841,7 +841,7 @@ class PermissionManager { */ private function checkCascadingSourcesRestrictions( $action, - User $user, + UserIdentity $user, $errors, $rigor, $short, @@ -870,7 +870,7 @@ class PermissionManager { if ( $right == 'autoconfirmed' ) { $right = 'editsemiprotected'; } - if ( $right != '' && !$user->isAllowedAll( 'protect', $right ) ) { + if ( $right != '' && !$this->userHasAllRights( $user, 'protect', $right ) ) { $wikiPages = ''; /** @var Title $wikiPage */ foreach ( $cascadingSources as $wikiPage ) { @@ -1086,7 +1086,7 @@ class PermissionManager { * Check CSS/JSON/JS sub-page permissions * * @param string $action The action to check - * @param User $user User to check + * @param UserIdentity $user User to check * @param array $errors List of current errors * @param string $rigor One of PermissionManager::RIGOR_ constants * - RIGOR_QUICK : does cheap permission checks from replica DBs (usable for GUI creation) @@ -1100,7 +1100,7 @@ class PermissionManager { */ private function checkUserConfigPermissions( $action, - User $user, + UserIdentity $user, $errors, $rigor, $short, @@ -1120,22 +1120,22 @@ class PermissionManager { // Users need editmyuser* to edit their own CSS/JSON/JS subpages. if ( $title->isUserCssConfigPage() - && !$user->isAllowedAny( 'editmyusercss', 'editusercss' ) + && !$this->userHasAnyRight( $user, 'editmyusercss', 'editusercss' ) ) { $errors[] = [ 'mycustomcssprotected', $action ]; } elseif ( $title->isUserJsonConfigPage() - && !$user->isAllowedAny( 'editmyuserjson', 'edituserjson' ) + && !$this->userHasAnyRight( $user, 'editmyuserjson', 'edituserjson' ) ) { $errors[] = [ 'mycustomjsonprotected', $action ]; } elseif ( $title->isUserJsConfigPage() - && !$user->isAllowedAny( 'editmyuserjs', 'edituserjs' ) + && !$this->userHasAnyRight( $user, 'editmyuserjs', 'edituserjs' ) ) { $errors[] = [ 'mycustomjsprotected', $action ]; } elseif ( $title->isUserJsConfigPage() - && !$user->isAllowedAny( 'edituserjs', 'editmyuserjsredirect' ) + && !$this->userHasAnyRight( $user, 'edituserjs', 'editmyuserjsredirect' ) ) { // T207750 - do not allow users to edit a redirect if they couldn't edit the target $rev = $this->revisionLookup->getRevisionByTitle( $title ); @@ -1195,6 +1195,40 @@ class PermissionManager { return in_array( $action, $this->getUserPermissions( $user ), true ); } + /** + * Check if user is allowed to make any action + * + * @param UserIdentity $user + * @param string[] ...$actions + * @return bool True if user is allowed to perform *any* of the given actions + * @since 1.34 + */ + public function userHasAnyRight( UserIdentity $user, ...$actions ) { + foreach ( $actions as $action ) { + if ( $this->userHasRight( $user, $action ) ) { + return true; + } + } + return false; + } + + /** + * Check if user is allowed to make all actions + * + * @param UserIdentity $user + * @param string[] ...$actions + * @return bool True if user is allowed to perform *all* of the given actions + * @since 1.34 + */ + public function userHasAllRights( UserIdentity $user, ...$actions ) { + foreach ( $actions as $action ) { + if ( !$this->userHasRight( $user, $action ) ) { + return false; + } + } + return true; + } + /** * Get the permissions this user has. * diff --git a/includes/api/ApiBase.php b/includes/api/ApiBase.php index a7b872ce15..8b6a3e582f 100644 --- a/includes/api/ApiBase.php +++ b/includes/api/ApiBase.php @@ -2126,7 +2126,9 @@ abstract class ApiBase extends ContextSource { $user = $this->getUser(); } $rights = (array)$rights; - if ( !$user->isAllowedAny( ...$rights ) ) { + if ( !$this->getPermissionManager() + ->userHasAnyRight( $user, ...$rights ) + ) { $this->dieWithError( [ 'apierror-permissiondenied', $this->msg( "action-{$rights[0]}" ) ] ); } } diff --git a/includes/api/ApiComparePages.php b/includes/api/ApiComparePages.php index e09691558c..05eb4382b3 100644 --- a/includes/api/ApiComparePages.php +++ b/includes/api/ApiComparePages.php @@ -231,7 +231,9 @@ class ApiComparePages extends ApiBase { */ private function getRevisionById( $id ) { $rev = $this->revisionStore->getRevisionById( $id ); - if ( !$rev && $this->getUser()->isAllowedAny( 'deletedtext', 'undelete' ) ) { + if ( !$rev && $this->getPermissionManager() + ->userHasAnyRight( $this->getUser(), 'deletedtext', 'undelete' ) + ) { // Try the 'archive' table $arQuery = $this->revisionStore->getArchiveQueryInfo(); $row = $this->getDB()->selectRow( diff --git a/includes/api/ApiQueryAllDeletedRevisions.php b/includes/api/ApiQueryAllDeletedRevisions.php index 4eead4c1f6..d713b3aed1 100644 --- a/includes/api/ApiQueryAllDeletedRevisions.php +++ b/includes/api/ApiQueryAllDeletedRevisions.php @@ -239,7 +239,9 @@ class ApiQueryAllDeletedRevisions extends ApiQueryRevisionsBase { // check it again just in case) if ( !$this->getPermissionManager()->userHasRight( $user, 'deletedhistory' ) ) { $bitmask = RevisionRecord::DELETED_USER; - } elseif ( !$user->isAllowedAny( 'suppressrevision', 'viewsuppressed' ) ) { + } elseif ( !$this->getPermissionManager() + ->userHasAnyRight( $user, 'suppressrevision', 'viewsuppressed' ) + ) { $bitmask = RevisionRecord::DELETED_USER | RevisionRecord::DELETED_RESTRICTED; } else { $bitmask = 0; diff --git a/includes/api/ApiQueryAllRevisions.php b/includes/api/ApiQueryAllRevisions.php index 17a6e00090..3751102494 100644 --- a/includes/api/ApiQueryAllRevisions.php +++ b/includes/api/ApiQueryAllRevisions.php @@ -156,7 +156,9 @@ class ApiQueryAllRevisions extends ApiQueryRevisionsBase { // Paranoia: avoid brute force searches (T19342) if ( !$this->getPermissionManager()->userHasRight( $this->getUser(), 'deletedhistory' ) ) { $bitmask = RevisionRecord::DELETED_USER; - } elseif ( !$this->getUser()->isAllowedAny( 'suppressrevision', 'viewsuppressed' ) ) { + } elseif ( !$this->getPermissionManager() + ->userHasAnyRight( $this->getUser(), 'suppressrevision', 'viewsuppressed' ) + ) { $bitmask = RevisionRecord::DELETED_USER | RevisionRecord::DELETED_RESTRICTED; } else { $bitmask = 0; diff --git a/includes/api/ApiQueryBase.php b/includes/api/ApiQueryBase.php index 846a8b134b..10db848d94 100644 --- a/includes/api/ApiQueryBase.php +++ b/includes/api/ApiQueryBase.php @@ -600,7 +600,8 @@ abstract class ApiQueryBase extends ApiBase { * @return bool */ public function userCanSeeRevDel() { - return $this->getUser()->isAllowedAny( + return $this->getPermissionManager()->userHasAnyRight( + $this->getUser(), 'deletedhistory', 'deletedtext', 'suppressrevision', diff --git a/includes/api/ApiQueryDeletedRevisions.php b/includes/api/ApiQueryDeletedRevisions.php index ac12b472f0..fc88499885 100644 --- a/includes/api/ApiQueryDeletedRevisions.php +++ b/includes/api/ApiQueryDeletedRevisions.php @@ -134,7 +134,9 @@ class ApiQueryDeletedRevisions extends ApiQueryRevisionsBase { // check it again just in case) if ( !$this->getPermissionManager()->userHasRight( $user, 'deletedhistory' ) ) { $bitmask = RevisionRecord::DELETED_USER; - } elseif ( !$user->isAllowedAny( 'suppressrevision', 'viewsuppressed' ) ) { + } elseif ( !$this->getPermissionManager() + ->userHasAnyRight( $this->getUser(), 'suppressrevision', 'viewsuppressed' ) + ) { $bitmask = RevisionRecord::DELETED_USER | RevisionRecord::DELETED_RESTRICTED; } else { $bitmask = 0; diff --git a/includes/api/ApiQueryDeletedrevs.php b/includes/api/ApiQueryDeletedrevs.php index aa88a51353..1af4d95971 100644 --- a/includes/api/ApiQueryDeletedrevs.php +++ b/includes/api/ApiQueryDeletedrevs.php @@ -199,7 +199,9 @@ class ApiQueryDeletedrevs extends ApiQueryBase { // check it again just in case) if ( !$this->getPermissionManager()->userHasRight( $user, 'deletedhistory' ) ) { $bitmask = RevisionRecord::DELETED_USER; - } elseif ( !$user->isAllowedAny( 'suppressrevision', 'viewsuppressed' ) ) { + } elseif ( !$this->getPermissionManager() + ->userHasAnyRight( $user, 'suppressrevision', 'viewsuppressed' ) + ) { $bitmask = RevisionRecord::DELETED_USER | RevisionRecord::DELETED_RESTRICTED; } else { $bitmask = 0; diff --git a/includes/api/ApiQueryFilearchive.php b/includes/api/ApiQueryFilearchive.php index fe484a81cc..f9087eb143 100644 --- a/includes/api/ApiQueryFilearchive.php +++ b/includes/api/ApiQueryFilearchive.php @@ -116,7 +116,9 @@ class ApiQueryFilearchive extends ApiQueryBase { // Exclude files this user can't view. if ( !$this->getPermissionManager()->userHasRight( $user, 'deletedtext' ) ) { $bitmask = File::DELETED_FILE; - } elseif ( !$user->isAllowedAny( 'suppressrevision', 'viewsuppressed' ) ) { + } elseif ( !$this->getPermissionManager() + ->userHasAnyRight( $user, 'suppressrevision', 'viewsuppressed' ) + ) { $bitmask = File::DELETED_FILE | File::DELETED_RESTRICTED; } else { $bitmask = 0; diff --git a/includes/api/ApiQueryInfo.php b/includes/api/ApiQueryInfo.php index 50bd63f696..ac7e5cc8c7 100644 --- a/includes/api/ApiQueryInfo.php +++ b/includes/api/ApiQueryInfo.php @@ -250,7 +250,9 @@ class ApiQueryInfo extends ApiQueryBase { */ public static function getImportToken( $pageid, $title ) { global $wgUser; - if ( !$wgUser->isAllowedAny( 'import', 'importupload' ) ) { + if ( !MediaWikiServices::getInstance() + ->getPermissionManager() + ->userHasAnyRight( $wgUser, 'import', 'importupload' ) ) { return false; } diff --git a/includes/api/ApiQueryLogEvents.php b/includes/api/ApiQueryLogEvents.php index c995ec5e8f..47a6f87296 100644 --- a/includes/api/ApiQueryLogEvents.php +++ b/includes/api/ApiQueryLogEvents.php @@ -223,7 +223,9 @@ class ApiQueryLogEvents extends ApiQueryBase { if ( !$this->getPermissionManager()->userHasRight( $this->getUser(), 'deletedhistory' ) ) { $titleBits = LogPage::DELETED_ACTION; $userBits = LogPage::DELETED_USER; - } elseif ( !$this->getUser()->isAllowedAny( 'suppressrevision', 'viewsuppressed' ) ) { + } elseif ( !$this->getPermissionManager() + ->userHasAnyRight( $this->getUser(), 'suppressrevision', 'viewsuppressed' ) + ) { $titleBits = LogPage::DELETED_ACTION | LogPage::DELETED_RESTRICTED; $userBits = LogPage::DELETED_USER | LogPage::DELETED_RESTRICTED; } else { diff --git a/includes/api/ApiQueryRecentChanges.php b/includes/api/ApiQueryRecentChanges.php index a74faf2f04..143d4662a1 100644 --- a/includes/api/ApiQueryRecentChanges.php +++ b/includes/api/ApiQueryRecentChanges.php @@ -363,7 +363,9 @@ class ApiQueryRecentChanges extends ApiQueryGeneratorBase { if ( !is_null( $params['user'] ) || !is_null( $params['excludeuser'] ) ) { if ( !$this->getPermissionManager()->userHasRight( $user, 'deletedhistory' ) ) { $bitmask = RevisionRecord::DELETED_USER; - } elseif ( !$user->isAllowedAny( 'suppressrevision', 'viewsuppressed' ) ) { + } elseif ( !$this->getPermissionManager() + ->userHasAnyRight( $user, 'suppressrevision', 'viewsuppressed' ) + ) { $bitmask = RevisionRecord::DELETED_USER | RevisionRecord::DELETED_RESTRICTED; } else { $bitmask = 0; @@ -376,7 +378,9 @@ class ApiQueryRecentChanges extends ApiQueryGeneratorBase { // LogPage::DELETED_ACTION hides the affected page, too. if ( !$this->getPermissionManager()->userHasRight( $user, 'deletedhistory' ) ) { $bitmask = LogPage::DELETED_ACTION; - } elseif ( !$user->isAllowedAny( 'suppressrevision', 'viewsuppressed' ) ) { + } elseif ( !$this->getPermissionManager() + ->userHasAnyRight( $user, 'suppressrevision', 'viewsuppressed' ) + ) { $bitmask = LogPage::DELETED_ACTION | LogPage::DELETED_RESTRICTED; } else { $bitmask = 0; diff --git a/includes/api/ApiQueryRevisions.php b/includes/api/ApiQueryRevisions.php index 3a06e3691d..d616ad4f9a 100644 --- a/includes/api/ApiQueryRevisions.php +++ b/includes/api/ApiQueryRevisions.php @@ -335,7 +335,9 @@ class ApiQueryRevisions extends ApiQueryRevisionsBase { // Paranoia: avoid brute force searches (T19342) if ( !$this->getPermissionManager()->userHasRight( $this->getUser(), 'deletedhistory' ) ) { $bitmask = RevisionRecord::DELETED_USER; - } elseif ( !$this->getUser()->isAllowedAny( 'suppressrevision', 'viewsuppressed' ) ) { + } elseif ( !$this->getPermissionManager() + ->userHasAnyRight( $this->getUser(), 'suppressrevision', 'viewsuppressed' ) + ) { $bitmask = RevisionRecord::DELETED_USER | RevisionRecord::DELETED_RESTRICTED; } else { $bitmask = 0; diff --git a/includes/api/ApiQueryUserContribs.php b/includes/api/ApiQueryUserContribs.php index cfefcb283c..919c7631b3 100644 --- a/includes/api/ApiQueryUserContribs.php +++ b/includes/api/ApiQueryUserContribs.php @@ -410,7 +410,9 @@ class ApiQueryUserContribs extends ApiQueryBase { $user = $this->getUser(); if ( !$this->getPermissionManager()->userHasRight( $user, 'deletedhistory' ) ) { $bitmask = RevisionRecord::DELETED_USER; - } elseif ( !$user->isAllowedAny( 'suppressrevision', 'viewsuppressed' ) ) { + } elseif ( !$this->getPermissionManager() + ->userHasAnyRight( $user, 'suppressrevision', 'viewsuppressed' ) + ) { $bitmask = RevisionRecord::DELETED_USER | RevisionRecord::DELETED_RESTRICTED; } else { $bitmask = 0; diff --git a/includes/auth/AuthManager.php b/includes/auth/AuthManager.php index c871ce1cb3..4fcaf4e9e9 100644 --- a/includes/auth/AuthManager.php +++ b/includes/auth/AuthManager.php @@ -1639,8 +1639,9 @@ class AuthManager implements LoggerAwareInterface { // Is the IP user able to create accounts? $anon = new User; - if ( $source !== self::AUTOCREATE_SOURCE_MAINT && - !$anon->isAllowedAny( 'createaccount', 'autocreateaccount' ) + if ( $source !== self::AUTOCREATE_SOURCE_MAINT && !MediaWikiServices::getInstance() + ->getPermissionManager() + ->userHasAnyRight( $anon, 'createaccount', 'autocreateaccount' ) ) { $this->logger->debug( __METHOD__ . ': IP lacks the ability to create or autocreate accounts', [ 'username' => $username, diff --git a/includes/logging/LogEventsList.php b/includes/logging/LogEventsList.php index e66bd69cd5..66be436da4 100644 --- a/includes/logging/LogEventsList.php +++ b/includes/logging/LogEventsList.php @@ -565,7 +565,9 @@ class LogEventsList extends ContextSource { } $permissionlist = implode( ', ', $permissions ); wfDebug( "Checking for $permissionlist due to $field match on $bitfield\n" ); - return $user->isAllowedAny( ...$permissions ); + return MediaWikiServices::getInstance() + ->getPermissionManager() + ->userHasAnyRight( $user, ...$permissions ); } return true; } diff --git a/includes/logging/LogPager.php b/includes/logging/LogPager.php index 4ecc368d4e..15b149e134 100644 --- a/includes/logging/LogPager.php +++ b/includes/logging/LogPager.php @@ -23,6 +23,8 @@ * @file */ +use MediaWiki\MediaWikiServices; + /** * @ingroup Pager */ @@ -462,7 +464,10 @@ class LogPager extends ReverseChronologicalPager { $user = $this->getUser(); if ( !$user->isAllowed( 'deletedhistory' ) ) { $this->mConds[] = $this->mDb->bitAnd( 'log_deleted', LogPage::DELETED_ACTION ) . ' = 0'; - } elseif ( !$user->isAllowedAny( 'suppressrevision', 'viewsuppressed' ) ) { + } elseif ( !MediaWikiServices::getInstance() + ->getPermissionManager() + ->userHasAnyRight( $user, 'suppressrevision', 'viewsuppressed' ) + ) { $this->mConds[] = $this->mDb->bitAnd( 'log_deleted', LogPage::SUPPRESSED_ACTION ) . ' != ' . LogPage::SUPPRESSED_USER; } @@ -480,7 +485,10 @@ class LogPager extends ReverseChronologicalPager { $user = $this->getUser(); if ( !$user->isAllowed( 'deletedhistory' ) ) { $this->mConds[] = $this->mDb->bitAnd( 'log_deleted', LogPage::DELETED_USER ) . ' = 0'; - } elseif ( !$user->isAllowedAny( 'suppressrevision', 'viewsuppressed' ) ) { + } elseif ( !MediaWikiServices::getInstance() + ->getPermissionManager() + ->userHasAnyRight( $user, 'suppressrevision', 'viewsuppressed' ) + ) { $this->mConds[] = $this->mDb->bitAnd( 'log_deleted', LogPage::SUPPRESSED_USER ) . ' != ' . LogPage::SUPPRESSED_ACTION; } diff --git a/includes/page/ImageHistoryList.php b/includes/page/ImageHistoryList.php index e488b6c1f7..2de82bf760 100644 --- a/includes/page/ImageHistoryList.php +++ b/includes/page/ImageHistoryList.php @@ -91,7 +91,9 @@ class ImageHistoryList extends ContextSource { . Xml::openElement( 'table', [ 'class' => 'wikitable filehistory' ] ) . "\n" . '' . ( $this->current->isLocal() - && ( $this->getUser()->isAllowedAny( 'delete', 'deletedhistory' ) ) ? '' : '' ) + && ( MediaWikiServices::getInstance() + ->getPermissionManager() + ->userHasAnyRight( $this->getUser(), 'delete', 'deletedhistory' ) ) ? '' : '' ) . '' . $this->msg( 'filehist-datetime' )->escaped() . '' . ( $this->showThumb ? '' . $this->msg( 'filehist-thumb' )->escaped() . '' : '' ) . '' . $this->msg( 'filehist-dimensions' )->escaped() . '' @@ -126,7 +128,10 @@ class ImageHistoryList extends ContextSource { $row = $selected = ''; // Deletion link - if ( $local && ( $user->isAllowedAny( 'delete', 'deletedhistory' ) ) ) { + if ( $local && ( MediaWikiServices::getInstance() + ->getPermissionManager() + ->userHasAnyRight( $user, 'delete', 'deletedhistory' ) ) + ) { $row .= ''; # Link to remove from history if ( $user->isAllowed( 'delete' ) ) { diff --git a/includes/page/WikiPage.php b/includes/page/WikiPage.php index 8cc5a39b51..460753514c 100644 --- a/includes/page/WikiPage.php +++ b/includes/page/WikiPage.php @@ -3249,7 +3249,10 @@ class WikiPage implements Page, IDBAccessObject { $flags |= EDIT_MINOR; } - if ( $bot && ( $guser->isAllowedAny( 'markbotedits', 'bot' ) ) ) { + if ( $bot && ( MediaWikiServices::getInstance() + ->getPermissionManager() + ->userHasAnyRight( $guser, 'markbotedits', 'bot' ) ) + ) { $flags |= EDIT_FORCE_BOT; } diff --git a/includes/skins/Skin.php b/includes/skins/Skin.php index bbad648b0e..e46f99d14e 100644 --- a/includes/skins/Skin.php +++ b/includes/skins/Skin.php @@ -238,7 +238,9 @@ abstract class Skin extends ContextSource { // Add various resources if required if ( $user->isLoggedIn() - && $user->isAllowedAll( 'writeapi', 'viewmywatchlist', 'editmywatchlist' ) + && MediaWikiServices::getInstance() + ->getPermissionManager() + ->userHasAllRights( $user, 'writeapi', 'viewmywatchlist', 'editmywatchlist' ) && $this->getRelevantTitle()->canExist() ) { $modules['watch'][] = 'mediawiki.page.watch.ajax'; diff --git a/includes/skins/SkinTemplate.php b/includes/skins/SkinTemplate.php index af7ec294e9..f32f2ff352 100644 --- a/includes/skins/SkinTemplate.php +++ b/includes/skins/SkinTemplate.php @@ -1081,7 +1081,10 @@ class SkinTemplate extends Skin { } // Checks if the user is logged in - if ( $this->loggedin && $user->isAllowedAll( 'viewmywatchlist', 'editmywatchlist' ) ) { + if ( $this->loggedin && MediaWikiServices::getInstance() + ->getPermissionManager() + ->userHasAllRights( $user, 'viewmywatchlist', 'editmywatchlist' ) + ) { /** * The following actions use messages which, if made particular to * the any specific skins, would break the Ajax code which makes this diff --git a/includes/specials/SpecialImport.php b/includes/specials/SpecialImport.php index c3aec83c18..f21c20651b 100644 --- a/includes/specials/SpecialImport.php +++ b/includes/specials/SpecialImport.php @@ -24,6 +24,7 @@ * @ingroup SpecialPage */ +use MediaWiki\MediaWikiServices; use MediaWiki\Permissions\PermissionManager; /** @@ -76,7 +77,10 @@ class SpecialImport extends SpecialPage { Hooks::run( 'ImportSources', [ &$this->importSources ] ); $user = $this->getUser(); - if ( !$user->isAllowedAny( 'import', 'importupload' ) ) { + if ( !MediaWikiServices::getInstance() + ->getPermissionManager() + ->userHasAnyRight( $user, 'import', 'importupload' ) + ) { throw new PermissionsError( 'import' ); } diff --git a/includes/specials/SpecialLog.php b/includes/specials/SpecialLog.php index 2f0c2ced53..c6927c1717 100644 --- a/includes/specials/SpecialLog.php +++ b/includes/specials/SpecialLog.php @@ -21,6 +21,7 @@ * @ingroup SpecialPage */ +use MediaWiki\MediaWikiServices; use Wikimedia\Timestamp\TimestampException; /** @@ -264,7 +265,9 @@ class SpecialLog extends SpecialPage { private function getActionButtons( $formcontents ) { $user = $this->getUser(); - $canRevDelete = $user->isAllowedAll( 'deletedhistory', 'deletelogentry' ); + $canRevDelete = MediaWikiServices::getInstance() + ->getPermissionManager() + ->userHasAllRights( $user, 'deletedhistory', 'deletelogentry' ); $showTagEditUI = ChangeTags::showTagEditingUI( $user ); # If the user doesn't have the ability to delete log entries nor edit tags, # don't bother showing them the button(s). diff --git a/includes/specials/SpecialWatchlist.php b/includes/specials/SpecialWatchlist.php index 2443470ef5..f5239b4713 100644 --- a/includes/specials/SpecialWatchlist.php +++ b/includes/specials/SpecialWatchlist.php @@ -382,7 +382,10 @@ class SpecialWatchlist extends ChangesListSpecialPage { // the necessary rights. if ( !$user->isAllowed( 'deletedhistory' ) ) { $bitmask = LogPage::DELETED_ACTION; - } elseif ( !$user->isAllowedAny( 'suppressrevision', 'viewsuppressed' ) ) { + } elseif ( !MediaWikiServices::getInstance() + ->getPermissionManager() + ->userHasAnyRight( $user, 'suppressrevision', 'viewsuppressed' ) + ) { $bitmask = LogPage::DELETED_ACTION | LogPage::DELETED_RESTRICTED; } else { $bitmask = 0; diff --git a/includes/specials/forms/PreferencesFormOOUI.php b/includes/specials/forms/PreferencesFormOOUI.php index 5dae156993..ea23973de4 100644 --- a/includes/specials/forms/PreferencesFormOOUI.php +++ b/includes/specials/forms/PreferencesFormOOUI.php @@ -18,6 +18,8 @@ * @file */ +use MediaWiki\MediaWikiServices; + /** * Form to edit user preferences. * @@ -71,7 +73,10 @@ class PreferencesFormOOUI extends OOUIHTMLForm { * @return string */ function getButtons() { - if ( !$this->getModifiedUser()->isAllowedAny( 'editmyprivateinfo', 'editmyoptions' ) ) { + if ( !MediaWikiServices::getInstance() + ->getPermissionManager() + ->userHasAnyRight( $this->getModifiedUser(), 'editmyprivateinfo', 'editmyoptions' ) + ) { return ''; } diff --git a/includes/specials/pagers/ContribsPager.php b/includes/specials/pagers/ContribsPager.php index 1cb78b88db..1fd87f6051 100644 --- a/includes/specials/pagers/ContribsPager.php +++ b/includes/specials/pagers/ContribsPager.php @@ -351,7 +351,10 @@ class ContribsPager extends RangeChronologicalPager { $queryInfo['conds'][] = $this->mDb->bitAnd( 'rev_deleted', RevisionRecord::DELETED_USER ) . ' = 0'; - } elseif ( !$user->isAllowedAny( 'suppressrevision', 'viewsuppressed' ) ) { + } elseif ( !MediaWikiServices::getInstance() + ->getPermissionManager() + ->userHasAnyRight( $user, 'suppressrevision', 'viewsuppressed' ) + ) { $queryInfo['conds'][] = $this->mDb->bitAnd( 'rev_deleted', RevisionRecord::SUPPRESSED_USER ) . ' != ' . RevisionRecord::SUPPRESSED_USER; diff --git a/includes/specials/pagers/DeletedContribsPager.php b/includes/specials/pagers/DeletedContribsPager.php index 88e1ea881c..2f40aceaa8 100644 --- a/includes/specials/pagers/DeletedContribsPager.php +++ b/includes/specials/pagers/DeletedContribsPager.php @@ -90,7 +90,10 @@ class DeletedContribsPager extends IndexPager { // Paranoia: avoid brute force searches (T19792) if ( !$user->isAllowed( 'deletedhistory' ) ) { $conds[] = $this->mDb->bitAnd( 'ar_deleted', RevisionRecord::DELETED_USER ) . ' = 0'; - } elseif ( !$user->isAllowedAny( 'suppressrevision', 'viewsuppressed' ) ) { + } elseif ( !MediaWikiServices::getInstance() + ->getPermissionManager() + ->userHasAnyRight( $user, 'suppressrevision', 'viewsuppressed' ) + ) { $conds[] = $this->mDb->bitAnd( 'ar_deleted', RevisionRecord::SUPPRESSED_USER ) . ' != ' . RevisionRecord::SUPPRESSED_USER; } diff --git a/includes/user/User.php b/includes/user/User.php index 7c2f0380fa..3ed3896407 100644 --- a/includes/user/User.php +++ b/includes/user/User.php @@ -3601,32 +3601,28 @@ class User implements IDBAccessObject, UserIdentity { /** * Check if user is allowed to access a feature / make an action * + * @deprecated since 1.34, use MediaWikiServices::getInstance() + * ->getPermissionManager()->userHasAnyRights(...) instead + * * @param string $permissions,... Permissions to test * @return bool True if user is allowed to perform *any* of the given actions */ public function isAllowedAny() { - $permissions = func_get_args(); - foreach ( $permissions as $permission ) { - if ( $this->isAllowed( $permission ) ) { - return true; - } - } - return false; + return MediaWikiServices::getInstance() + ->getPermissionManager() + ->userHasAnyRight( $this, ...func_get_args() ); } /** - * + * @deprecated since 1.34, use MediaWikiServices::getInstance() + * ->getPermissionManager()->userHasAllRights(...) instead * @param string $permissions,... Permissions to test * @return bool True if the user is allowed to perform *all* of the given actions */ public function isAllowedAll() { - $permissions = func_get_args(); - foreach ( $permissions as $permission ) { - if ( !$this->isAllowed( $permission ) ) { - return false; - } - } - return true; + return MediaWikiServices::getInstance() + ->getPermissionManager() + ->userHasAllRights( $this, ...func_get_args() ); } /** diff --git a/tests/phpunit/includes/api/ApiOptionsTest.php b/tests/phpunit/includes/api/ApiOptionsTest.php index 30ba1c1b66..bdce70c6be 100644 --- a/tests/phpunit/includes/api/ApiOptionsTest.php +++ b/tests/phpunit/includes/api/ApiOptionsTest.php @@ -29,8 +29,6 @@ class ApiOptionsTest extends MediaWikiLangTestCase { // Set up groups and rights $this->mUserMock->expects( $this->any() ) ->method( 'getEffectiveGroups' )->will( $this->returnValue( [ '*', 'user' ] ) ); - $this->mUserMock->expects( $this->any() ) - ->method( 'isAllowedAny' )->will( $this->returnValue( true ) ); // Set up callback for User::getOptionKinds $this->mUserMock->expects( $this->any() ) @@ -49,6 +47,7 @@ class ApiOptionsTest extends MediaWikiLangTestCase { $this->mContext->getContext()->setTitle( Title::newFromText( 'Test' ) ); $this->mContext->setUser( $this->mUserMock ); + $this->overrideUserPermissions( $this->mUserMock, [ 'editmyoptions' ] ); $main = new ApiMain( $this->mContext ); // Empty session diff --git a/tests/phpunit/includes/specials/SpecialPreferencesTest.php b/tests/phpunit/includes/specials/SpecialPreferencesTest.php index 90f6ad9c84..510a2f291c 100644 --- a/tests/phpunit/includes/specials/SpecialPreferencesTest.php +++ b/tests/phpunit/includes/specials/SpecialPreferencesTest.php @@ -24,7 +24,6 @@ class SpecialPreferencesTest extends MediaWikiTestCase { public function testT43337() { // Set a low limit $this->setMwGlobals( 'wgMaxSigChars', 2 ); - $user = $this->createMock( User::class ); $user->expects( $this->any() ) ->method( 'isAnon' ) @@ -47,6 +46,10 @@ class SpecialPreferencesTest extends MediaWikiTestCase { $user->method( 'getOptions' ) ->willReturn( [] ); + // isAnyAllowed used to return null from the mock, + // thus revoke it's permissions. + $this->overrideUserPermissions( $user, [] ); + # Forge a request to call the special page $context = new RequestContext(); $context->setRequest( new FauxRequest() ); -- 2.20.1