MediaWiki  REL1_19
SpecialBlockList.php
Go to the documentation of this file.
00001 <?php
00029 class SpecialBlockList extends SpecialPage {
00030 
00031         protected $target, $options;
00032 
00033         function __construct() {
00034                 parent::__construct( 'BlockList' );
00035         }
00036 
00042         public function execute( $par ) {
00043                 $this->setHeaders();
00044                 $this->outputHeader();
00045                 $out = $this->getOutput();
00046                 $lang = $this->getLanguage();
00047                 $out->setPageTitle( $this->msg( 'ipblocklist' ) );
00048                 $out->addModuleStyles( 'mediawiki.special' );
00049 
00050                 $request = $this->getRequest();
00051                 $par = $request->getVal( 'ip', $par );
00052                 $this->target = trim( $request->getVal( 'wpTarget', $par ) );
00053 
00054                 $this->options = $request->getArray( 'wpOptions', array() );
00055 
00056                 $action = $request->getText( 'action' );
00057 
00058                 if( $action == 'unblock' || $action == 'submit' && $request->wasPosted() ) {
00059                         # B/C @since 1.18: Unblock interface is now at Special:Unblock
00060                         $title = SpecialPage::getTitleFor( 'Unblock', $this->target );
00061                         $out->redirect( $title->getFullUrl() );
00062                         return;
00063                 }
00064 
00065                 # Just show the block list
00066                 $fields = array(
00067                         'Target' => array(
00068                                 'type' => 'text',
00069                                 'label-message' => 'ipadressorusername',
00070                                 'tabindex' => '1',
00071                                 'size' => '45',
00072                                 'default' => $this->target,
00073                         ),
00074                         'Options' => array(
00075                                 'type' => 'multiselect',
00076                                 'options' => array(
00077                                         $this->msg( 'blocklist-userblocks' )->text() => 'userblocks',
00078                                         $this->msg( 'blocklist-tempblocks' )->text() => 'tempblocks',
00079                                         $this->msg( 'blocklist-addressblocks' )->text() => 'addressblocks',
00080                                         $this->msg( 'blocklist-rangeblocks' )->text() => 'rangeblocks',
00081                                 ),
00082                                 'flatlist' => true,
00083                         ),
00084                         'Limit' => array(
00085                                 'class' => 'HTMLBlockedUsersItemSelect',
00086                                 'label-message' => 'table_pager_limit_label',
00087                                 'options' => array(
00088                                         $lang->formatNum( 20 ) => 20,
00089                                         $lang->formatNum( 50 ) => 50,
00090                                         $lang->formatNum( 100 ) => 100,
00091                                         $lang->formatNum( 250 ) => 250,
00092                                         $lang->formatNum( 500 ) => 500,
00093                                 ),
00094                                 'name' => 'limit',
00095                                 'default' => 50,
00096                         ),
00097                 );
00098                 $form = new HTMLForm( $fields, $this->getContext() );
00099                 $form->setMethod( 'get' );
00100                 $form->setWrapperLegendMsg( 'ipblocklist-legend' );
00101                 $form->setSubmitTextMsg( 'ipblocklist-submit' );
00102                 $form->prepareForm();
00103 
00104                 $form->displayForm( '' );
00105                 $this->showList();
00106         }
00107 
00108         function showList() {
00109                 # Purge expired entries on one in every 10 queries
00110                 if ( !mt_rand( 0, 10 ) ) {
00111                         Block::purgeExpired();
00112                 }
00113 
00114                 $conds = array();
00115                 # Is the user allowed to see hidden blocks?
00116                 if ( !$this->getUser()->isAllowed( 'hideuser' ) ){
00117                         $conds['ipb_deleted'] = 0;
00118                 }
00119 
00120                 if ( $this->target !== '' ){
00121                         list( $target, $type ) = Block::parseTarget( $this->target );
00122 
00123                         switch( $type ){
00124                                 case Block::TYPE_ID:
00125                                 case Block::TYPE_AUTO:
00126                                         $conds['ipb_id'] = $target;
00127                                         break;
00128 
00129                                 case Block::TYPE_IP:
00130                                 case Block::TYPE_RANGE:
00131                                         list( $start, $end ) = IP::parseRange( $target );
00132                                         $dbr = wfGetDB( DB_SLAVE );
00133                                         $conds[] = $dbr->makeList(
00134                                                 array(
00135                                                         'ipb_address' => $target,
00136                                                         Block::getRangeCond( $start, $end )
00137                                                 ),
00138                                                 LIST_OR
00139                                         );
00140                                         $conds['ipb_auto'] = 0;
00141                                         break;
00142 
00143                                 case Block::TYPE_USER:
00144                                         $conds['ipb_address'] = (string)$this->target;
00145                                         $conds['ipb_auto'] = 0;
00146                                         break;
00147                         }
00148                 }
00149 
00150                 # Apply filters
00151                 if( in_array( 'userblocks', $this->options ) ) {
00152                         $conds['ipb_user'] = 0;
00153                 }
00154                 if( in_array( 'tempblocks', $this->options ) ) {
00155                         $conds['ipb_expiry'] = 'infinity';
00156                 }
00157                 if( in_array( 'addressblocks', $this->options ) ) {
00158                         $conds[] = "ipb_user != 0 OR ipb_range_end > ipb_range_start";
00159                 }
00160                 if( in_array( 'rangeblocks', $this->options ) ) {
00161                         $conds[] = "ipb_range_end = ipb_range_start";
00162                 }
00163 
00164                 # Check for other blocks, i.e. global/tor blocks
00165                 $otherBlockLink = array();
00166                 wfRunHooks( 'OtherBlockLogLink', array( &$otherBlockLink, $this->target ) );
00167 
00168                 $out = $this->getOutput();
00169 
00170                 # Show additional header for the local block only when other blocks exists.
00171                 # Not necessary in a standard installation without such extensions enabled
00172                 if( count( $otherBlockLink ) ) {
00173                         $out->addHTML(
00174                                 Html::element( 'h2', array(), $this->msg( 'ipblocklist-localblock' )->text() ) . "\n"
00175                         );
00176                 }
00177 
00178                 $pager = new BlockListPager( $this, $conds );
00179                 if ( $pager->getNumRows() ) {
00180                         $out->addHTML(
00181                                 $pager->getNavigationBar() .
00182                                 $pager->getBody().
00183                                 $pager->getNavigationBar()
00184                         );
00185 
00186                 } elseif ( $this->target ) {
00187                         $out->addWikiMsg( 'ipblocklist-no-results' );
00188 
00189                 } else {
00190                         $out->addWikiMsg( 'ipblocklist-empty' );
00191                 }
00192 
00193                 if( count( $otherBlockLink ) ) {
00194                         $out->addHTML(
00195                                 Html::rawElement(
00196                                         'h2',
00197                                         array(),
00198                                         $this->msg( 'ipblocklist-otherblocks', count( $otherBlockLink ) )->parse()
00199                                 ) . "\n"
00200                         );
00201                         $list = '';
00202                         foreach( $otherBlockLink as $link ) {
00203                                 $list .= Html::rawElement( 'li', array(), $link ) . "\n";
00204                         }
00205                         $out->addHTML( Html::rawElement( 'ul', array( 'class' => 'mw-ipblocklist-otherblocks' ), $list ) . "\n" );
00206                 }
00207         }
00208 }
00209 
00210 class BlockListPager extends TablePager {
00211         protected $conds;
00212         protected $page;
00213 
00218         function __construct( $page, $conds ) {
00219                 $this->page = $page;
00220                 $this->conds = $conds;
00221                 $this->mDefaultDirection = true;
00222                 parent::__construct( $page->getContext() );
00223         }
00224 
00225         function getFieldNames() {
00226                 static $headers = null;
00227 
00228                 if ( $headers == array() ) {
00229                         $headers = array(
00230                                 'ipb_timestamp' => 'blocklist-timestamp',
00231                                 'ipb_target' => 'blocklist-target',
00232                                 'ipb_expiry' => 'blocklist-expiry',
00233                                 'ipb_by' => 'blocklist-by',
00234                                 'ipb_params' => 'blocklist-params',
00235                                 'ipb_reason' => 'blocklist-reason',
00236                         );
00237                         foreach( $headers as $key => $val ) {
00238                                 $headers[$key] = $this->msg( $val )->text();
00239                         }
00240                 }
00241 
00242                 return $headers;
00243         }
00244 
00245         function formatValue( $name, $value ) {
00246                 static $msg = null;
00247                 if ( $msg === null ) {
00248                         $msg = array(
00249                                 'anononlyblock',
00250                                 'createaccountblock',
00251                                 'noautoblockblock',
00252                                 'emailblock',
00253                                 'blocklist-nousertalk',
00254                                 'unblocklink',
00255                                 'change-blocklink',
00256                                 'infiniteblock',
00257                         );
00258                         $msg = array_combine( $msg, array_map( array( $this, 'msg' ), $msg ) );
00259                 }
00260 
00262                 $row = $this->mCurrentRow;
00263 
00264                 $formatted = '';
00265 
00266                 switch( $name ) {
00267                         case 'ipb_timestamp':
00268                                 $formatted = $this->getLanguage()->userTimeAndDate( $value, $this->getUser() );
00269                                 break;
00270 
00271                         case 'ipb_target':
00272                                 if( $row->ipb_auto ){
00273                                         $formatted = $this->msg( 'autoblockid', $row->ipb_id )->parse();
00274                                 } else {
00275                                         list( $target, $type ) = Block::parseTarget( $row->ipb_address );
00276                                         switch( $type ){
00277                                                 case Block::TYPE_USER:
00278                                                 case Block::TYPE_IP:
00279                                                         $formatted = Linker::userLink( $target->getId(), $target );
00280                                                         $formatted .= Linker::userToolLinks(
00281                                                                 $target->getId(),
00282                                                                 $target,
00283                                                                 false,
00284                                                                 Linker::TOOL_LINKS_NOBLOCK
00285                                                         );
00286                                                         break;
00287                                                 case Block::TYPE_RANGE:
00288                                                         $formatted = htmlspecialchars( $target );
00289                                         }
00290                                 }
00291                                 break;
00292 
00293                         case 'ipb_expiry':
00294                                 $formatted = $this->getLanguage()->formatExpiry( $value, /* User preference timezone */ true );
00295                                 if( $this->getUser()->isAllowed( 'block' ) ){
00296                                         if( $row->ipb_auto ){
00297                                                 $links[] = Linker::linkKnown(
00298                                                         SpecialPage::getTitleFor( 'Unblock' ),
00299                                                         $msg['unblocklink'],
00300                                                         array(),
00301                                                         array( 'wpTarget' => "#{$row->ipb_id}" )
00302                                                 );
00303                                         } else {
00304                                                 $links[] = Linker::linkKnown(
00305                                                         SpecialPage::getTitleFor( 'Unblock', $row->ipb_address ),
00306                                                         $msg['unblocklink']
00307                                                 );
00308                                                 $links[] = Linker::linkKnown(
00309                                                         SpecialPage::getTitleFor( 'Block', $row->ipb_address ),
00310                                                         $msg['change-blocklink']
00311                                                 );
00312                                         }
00313                                         $formatted .= ' ' . Html::rawElement(
00314                                                 'span',
00315                                                 array( 'class' => 'mw-blocklist-actions' ),
00316                                                 $this->msg( 'parentheses' )->rawParams(
00317                                                         $this->getLanguage()->pipeList( $links ) )->escaped()
00318                                         );
00319                                 }
00320                                 break;
00321 
00322                         case 'ipb_by':
00323                                 if ( isset( $row->by_user_name ) ) {
00324                                         $formatted = Linker::userLink( $value, $row->by_user_name );
00325                                         $formatted .= Linker::userToolLinks( $value, $row->by_user_name );
00326                                 } else {
00327                                         $formatted = htmlspecialchars( $row->ipb_by_text ); // foreign user?
00328                                 }
00329                                 break;
00330 
00331                         case 'ipb_reason':
00332                                 $formatted = Linker::commentBlock( $value );
00333                                 break;
00334 
00335                         case 'ipb_params':
00336                                 $properties = array();
00337                                 if ( $row->ipb_anon_only ) {
00338                                         $properties[] = $msg['anononlyblock'];
00339                                 }
00340                                 if ( $row->ipb_create_account ) {
00341                                         $properties[] = $msg['createaccountblock'];
00342                                 }
00343                                 if ( $row->ipb_user && !$row->ipb_enable_autoblock ) {
00344                                         $properties[] = $msg['noautoblockblock'];
00345                                 }
00346 
00347                                 if ( $row->ipb_block_email ) {
00348                                         $properties[] = $msg['emailblock'];
00349                                 }
00350 
00351                                 if ( !$row->ipb_allow_usertalk ) {
00352                                         $properties[] = $msg['blocklist-nousertalk'];
00353                                 }
00354 
00355                                 $formatted = $this->getLanguage()->commaList( $properties );
00356                                 break;
00357 
00358                         default:
00359                                 $formatted = "Unable to format $name";
00360                                 break;
00361                 }
00362 
00363                 return $formatted;
00364         }
00365 
00366         function getQueryInfo() {
00367                 $info = array(
00368                         'tables' => array( 'ipblocks', 'user' ),
00369                         'fields' => array(
00370                                 'ipb_id',
00371                                 'ipb_address',
00372                                 'ipb_user',
00373                                 'ipb_by',
00374                                 'ipb_by_text',
00375                                 'user_name AS by_user_name',
00376                                 'ipb_reason',
00377                                 'ipb_timestamp',
00378                                 'ipb_auto',
00379                                 'ipb_anon_only',
00380                                 'ipb_create_account',
00381                                 'ipb_enable_autoblock',
00382                                 'ipb_expiry',
00383                                 'ipb_range_start',
00384                                 'ipb_range_end',
00385                                 'ipb_deleted',
00386                                 'ipb_block_email',
00387                                 'ipb_allow_usertalk',
00388                         ),
00389                         'conds' => $this->conds,
00390                         'join_conds' => array( 'user' => array( 'LEFT JOIN', 'user_id = ipb_by' ) )
00391                 );
00392 
00393                 # Is the user allowed to see hidden blocks?
00394                 if ( !$this->getUser()->isAllowed( 'hideuser' ) ){
00395                         $info['conds']['ipb_deleted'] = 0;
00396                 }
00397 
00398                 return $info;
00399         }
00400 
00401         public function getTableClass(){
00402                 return 'TablePager mw-blocklist';
00403         }
00404 
00405         function getIndexField() {
00406                 return 'ipb_timestamp';
00407         }
00408 
00409         function getDefaultSort() {
00410                 return 'ipb_timestamp';
00411         }
00412 
00413         function isFieldSortable( $name ) {
00414                 return false;
00415         }
00416 
00421         function preprocessResults( $result ){
00422                 wfProfileIn( __METHOD__ );
00423                 # Do a link batch query
00424                 $lb = new LinkBatch;
00425                 $lb->setCaller( __METHOD__ );
00426 
00427                 $userids = array();
00428 
00429                 foreach ( $result as $row ) {
00430                         $userids[] = $row->ipb_by;
00431 
00432                         # Usernames and titles are in fact related by a simple substitution of space -> underscore
00433                         # The last few lines of Title::secureAndSplit() tell the story.
00434                         $name = str_replace( ' ', '_', $row->ipb_address );
00435                         $lb->add( NS_USER, $name );
00436                         $lb->add( NS_USER_TALK, $name );
00437                 }
00438 
00439                 $ua = UserArray::newFromIDs( $userids );
00440                 foreach( $ua as $user ){
00441                         $name = str_replace( ' ', '_', $user->getName() );
00442                         $lb->add( NS_USER, $name );
00443                         $lb->add( NS_USER_TALK, $name );
00444                 } 
00445 
00446                 $lb->execute();
00447                 wfProfileOut( __METHOD__ );
00448         }
00449 }
00450 
00456 class HTMLBlockedUsersItemSelect extends HTMLSelectField {
00465         function validate( $value, $alldata ) {
00466                 if ( $value == '' ) {
00467                         return true;
00468                 }
00469 
00470                 // Let folks pick an explicit limit not from our list, as long as it's a real numbr.
00471                 if ( !in_array( $value, $this->mParams['options'] ) && $value == intval( $value ) && $value > 0 ) {
00472                         // This adds the explicitly requested limit value to the drop-down,
00473                         // then makes sure it's sorted correctly so when we output the list
00474                         // later, the custom option doesn't just show up last.
00475                         $this->mParams['options'][ $this->mParent->getLanguage()->formatNum( $value ) ] = intval($value);
00476                         asort( $this->mParams['options'] );
00477                 }
00478 
00479                 return true;
00480         }
00481 
00482 }