123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227 |
- <?php
- /**
- * Class for blocks composed from multiple blocks.
- *
- * This program is free software; you can redistribute it and/or modify
- * it under the terms of the GNU General Public License as published by
- * the Free Software Foundation; either version 2 of the License, or
- * (at your option) any later version.
- *
- * This program is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
- * GNU General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License along
- * with this program; if not, write to the Free Software Foundation, Inc.,
- * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
- * http://www.gnu.org/copyleft/gpl.html
- *
- * @file
- */
- namespace MediaWiki\Block;
- use IContextSource;
- use Title;
- /**
- * Multiple Block class.
- *
- * Multiple blocks exist to enforce restrictions from more than one block, if several
- * blocks apply to a user/IP. Multiple blocks are created temporarily on enforcement.
- *
- * @since 1.34
- */
- class CompositeBlock extends AbstractBlock {
- /** @var AbstractBlock[] */
- private $originalBlocks;
- /**
- * Create a new block with specified parameters on a user, IP or IP range.
- *
- * @param array $options Parameters of the block, with options supported by
- * `AbstractBlock::__construct`, and also:
- * - originalBlocks: (Block[]) Blocks that this block is composed from
- */
- public function __construct( array $options = [] ) {
- parent::__construct( $options );
- $defaults = [
- 'originalBlocks' => [],
- ];
- $options += $defaults;
- $this->originalBlocks = $options[ 'originalBlocks' ];
- $this->setHideName( $this->propHasValue( 'mHideName', true ) );
- $this->isSitewide( $this->propHasValue( 'isSitewide', true ) );
- $this->isEmailBlocked( $this->propHasValue( 'mBlockEmail', true ) );
- $this->isCreateAccountBlocked( $this->propHasValue( 'blockCreateAccount', true ) );
- $this->isUsertalkEditAllowed( !$this->propHasValue( 'allowUsertalk', false ) );
- }
- /**
- * Determine whether any original blocks have a particular property set to a
- * particular value.
- *
- * @param string $prop
- * @param mixed $value
- * @return bool At least one block has the property set to the value
- */
- private function propHasValue( $prop, $value ) {
- foreach ( $this->originalBlocks as $block ) {
- if ( $block->$prop == $value ) {
- return true;
- }
- }
- return false;
- }
- /**
- * Determine whether any original blocks have a particular method returning a
- * particular value.
- *
- * @param string $method
- * @param mixed $value
- * @param mixed ...$params
- * @return bool At least one block has the method returning the value
- */
- private function methodReturnsValue( $method, $value, ...$params ) {
- foreach ( $this->originalBlocks as $block ) {
- if ( $block->$method( ...$params ) == $value ) {
- return true;
- }
- }
- return false;
- }
- /**
- * Get the original blocks from which this block is composed
- *
- * @since 1.34
- * @return AbstractBlock[]
- */
- public function getOriginalBlocks() {
- return $this->originalBlocks;
- }
- /**
- * @inheritDoc
- */
- public function getExpiry() {
- $maxExpiry = null;
- foreach ( $this->originalBlocks as $block ) {
- $expiry = $block->getExpiry();
- if ( $maxExpiry === null || $expiry === '' || $expiry > $maxExpiry ) {
- $maxExpiry = $expiry;
- }
- }
- return $maxExpiry;
- }
- /**
- * Get the IDs for the original blocks, ignoring any that are null
- *
- * @return int[]
- */
- protected function getIds() {
- $ids = [];
- foreach ( $this->originalBlocks as $block ) {
- $id = $block->getId();
- if ( $id !== null ) {
- $ids[] = $id;
- }
- }
- return $ids;
- }
- /**
- * @inheritDoc
- */
- public function getPermissionsError( IContextSource $context ) {
- $params = $this->getBlockErrorParams( $context );
- $ids = implode( ', ', array_map( function ( $id ) {
- return '#' . $id;
- }, $this->getIds() ) );
- if ( $ids === '' ) {
- $idsMsg = $context->msg( 'blockedtext-composite-no-ids' )->plain();
- } else {
- $idsMsg = $context->msg( 'blockedtext-composite-ids', [ $ids ] )->plain();
- }
- // TODO: Clean up error messages params so we don't have to do this (T227174)
- $params[ 4 ] = $idsMsg;
- $msg = 'blockedtext-composite';
- array_unshift( $params, $msg );
- return $params;
- }
- /**
- * @inheritDoc
- *
- * Determines whether the CompositeBlock applies to a right by checking
- * whether the original blocks apply to that right. Each block can report
- * true (applies), false (does not apply) or null (unsure). Then:
- * - If any original blocks apply, this block applies
- * - If no original blocks apply but any are unsure, this block is unsure
- * - If all blocks do not apply, this block does not apply
- */
- public function appliesToRight( $right ) {
- $isUnsure = false;
- foreach ( $this->originalBlocks as $block ) {
- $appliesToRight = $block->appliesToRight( $right );
- if ( $appliesToRight ) {
- return true;
- } elseif ( $appliesToRight === null ) {
- $isUnsure = true;
- }
- }
- return $isUnsure ? null : false;
- }
- /**
- * @inheritDoc
- */
- public function appliesToUsertalk( Title $usertalk = null ) {
- return $this->methodReturnsValue( __FUNCTION__, true, $usertalk );
- }
- /**
- * @inheritDoc
- */
- public function appliesToTitle( Title $title ) {
- return $this->methodReturnsValue( __FUNCTION__, true, $title );
- }
- /**
- * @inheritDoc
- */
- public function appliesToNamespace( $ns ) {
- return $this->methodReturnsValue( __FUNCTION__, true, $ns );
- }
- /**
- * @inheritDoc
- */
- public function appliesToPage( $pageId ) {
- return $this->methodReturnsValue( __FUNCTION__, true, $pageId );
- }
- /**
- * @inheritDoc
- */
- public function appliesToPasswordReset() {
- return $this->methodReturnsValue( __FUNCTION__, true );
- }
- }
|