diff options
author | Dayllan Maza <dmaza@wikimedia.org> | 2024-12-11 17:13:55 -0500 |
---|---|---|
committer | Dayllan Maza <dmaza@wikimedia.org> | 2025-01-14 12:06:33 -0500 |
commit | 37f44a0a3ec9ffd741a464abd6c9959982d045e9 (patch) | |
tree | 1cfd5f98192d41b9f87bb2245267a8ca00c3e8bd /includes/block/UnblockUser.php | |
parent | 5bb154a8780989d379741cf4dad11b3b0f3fa58f (diff) | |
download | mediawikicore-37f44a0a3ec9ffd741a464abd6c9959982d045e9.tar.gz mediawikicore-37f44a0a3ec9ffd741a464abd6c9959982d045e9.zip |
ApiUnblock: Add support for multiblocks
* Re-purpose the existing id parameter to support block ID. If both id,
and username are provided the request will fail
* If a target has more than one block and a specific block is not
provided it will fail with ipb_cant_unblock_multiple_blocks
Bug: T378148
Change-Id: I04928d989e6764ac93ec243a5fec9c7fe2b0b9b0
Diffstat (limited to 'includes/block/UnblockUser.php')
-rw-r--r-- | includes/block/UnblockUser.php | 79 |
1 files changed, 63 insertions, 16 deletions
diff --git a/includes/block/UnblockUser.php b/includes/block/UnblockUser.php index fa3d01cbb49d..b3532e2f9e90 100644 --- a/includes/block/UnblockUser.php +++ b/includes/block/UnblockUser.php @@ -25,6 +25,7 @@ use ChangeTags; use ManualLogEntry; use MediaWiki\HookContainer\HookContainer; use MediaWiki\HookContainer\HookRunner; +use MediaWiki\Message\Message; use MediaWiki\Permissions\Authority; use MediaWiki\Status\Status; use MediaWiki\Title\TitleValue; @@ -50,8 +51,9 @@ class UnblockUser { /** @var int */ private $targetType; - /** @var DatabaseBlock|null */ - private $block; + private ?DatabaseBlock $block; + + private ?DatabaseBlock $blockToRemove = null; /** @var Authority */ private $performer; @@ -68,7 +70,8 @@ class UnblockUser { * @param BlockUtils $blockUtils * @param UserFactory $userFactory * @param HookContainer $hookContainer - * @param UserIdentity|string $target + * @param DatabaseBlock|null $blockToRemove + * @param UserIdentity|string|null $target * @param Authority $performer * @param string $reason * @param string[] $tags @@ -79,6 +82,7 @@ class UnblockUser { BlockUtils $blockUtils, UserFactory $userFactory, HookContainer $hookContainer, + ?DatabaseBlock $blockToRemove, $target, Authority $performer, string $reason, @@ -96,15 +100,22 @@ class UnblockUser { $this->hookRunner = new HookRunner( $hookContainer ); // Process params - [ $this->target, $this->targetType ] = $this->blockUtils->parseBlockTarget( $target ); - if ( - $this->targetType === AbstractBlock::TYPE_AUTO && - is_numeric( $this->target ) - ) { - // Needed, because BlockUtils::parseBlockTarget will strip the # from autoblocks. - $this->target = '#' . $this->target; + if ( $blockToRemove !== null ) { + $this->blockToRemove = $blockToRemove; + $this->target = $blockToRemove->getTargetUserIdentity() + ?? $blockToRemove->getTargetName(); + $this->targetType = $blockToRemove->getType() ?? -1; + } else { + [ $this->target, $this->targetType ] = $this->blockUtils->parseBlockTarget( $target ); + if ( + $this->targetType === AbstractBlock::TYPE_AUTO && + is_numeric( $this->target ) + ) { + // Needed, because BlockUtils::parseBlockTarget will strip the # from autoblocks. + $this->target = '#' . $this->target; + } } - $this->block = $this->blockStore->newFromTarget( $this->target ); + $this->performer = $performer; $this->reason = $reason; $this->tags = $tags; @@ -118,11 +129,9 @@ class UnblockUser { public function unblock(): Status { $status = Status::newGood(); - $basePermissionCheckResult = $this->blockPermissionChecker->checkBasePermissions( - $this->block instanceof DatabaseBlock && $this->block->getHideName() - ); - if ( $basePermissionCheckResult !== true ) { - return $status->fatal( $basePermissionCheckResult ); + $this->block = $this->getBlockToRemove( $status ); + if ( !$status->isOK() ) { + return $status; } $blockPermissionCheckResult = $this->blockPermissionChecker->checkBlockPermissions(); @@ -130,6 +139,14 @@ class UnblockUser { return $status->fatal( $blockPermissionCheckResult ); } + $basePermissionCheckResult = $this->blockPermissionChecker->checkBasePermissions( + $this->block instanceof DatabaseBlock && $this->block->getHideName() + ); + + if ( $basePermissionCheckResult !== true ) { + return $status->fatal( $basePermissionCheckResult ); + } + if ( count( $this->tags ) !== 0 ) { $status->merge( ChangeTags::canAddTagsAccompanyingChange( @@ -142,6 +159,7 @@ class UnblockUser { if ( !$status->isOK() ) { return $status; } + return $this->unblockUnsafe(); } @@ -154,6 +172,11 @@ class UnblockUser { public function unblockUnsafe(): Status { $status = Status::newGood(); + $this->block ??= $this->getBlockToRemove( $status ); + if ( !$status->isOK() ) { + return $status; + } + if ( $this->block === null ) { return $status->fatal( 'ipb_cant_unblock', $this->target ); } @@ -218,4 +241,28 @@ class UnblockUser { $logEntry->publish( $logId ); } + private function getBlockToRemove( Status $status ): ?DatabaseBlock { + if ( $this->blockToRemove !== null ) { + return $this->blockToRemove; + } + + $activeBlocks = $this->blockStore->newListFromTarget( $this->target ); + if ( !$activeBlocks ) { + $status->fatal( 'ipb_cant_unblock', $this->target ); + return null; + } + + if ( count( $activeBlocks ) > 1 ) { + $status->fatal( 'ipb_cant_unblock_multiple_blocks', + count( $activeBlocks ), Message::listParam( + array_map( + static function ( $block ) { + return $block->getId(); + }, $activeBlocks ) + ) + ); + } + + return $activeBlocks[0]; + } } |