mirror of
https://gerrit.wikimedia.org/r/mediawiki/extensions/AbuseFilter.git
synced 2024-11-15 18:19:38 +00:00
21d7c08aa7
The main change is the addition of checkboxes to hide/show multiple entries at the same time. Also, tweaked some i18n and made the process return more useful success/error messages. This patch introduces some technical debt, caused by SpecialAbuseLog and AbuseLogPager being tightly coupled (which is a pre-existing problem, but it got worse here). Bug: T260904 Bug: T144096 Bug: T206945 Bug: T206938 Change-Id: I13f476d8126f81b0417e7509784c83d4f21cf348
195 lines
6 KiB
PHP
195 lines
6 KiB
PHP
<?php
|
|
|
|
namespace MediaWiki\Extension\AbuseFilter\View;
|
|
|
|
use DeferredUpdates;
|
|
use Html;
|
|
use HTMLForm;
|
|
use IContextSource;
|
|
use LogEventsList;
|
|
use LogPage;
|
|
use ManualLogEntry;
|
|
use MediaWiki\Extension\AbuseFilter\AbuseFilterPermissionManager;
|
|
use MediaWiki\Extension\AbuseFilter\Pager\AbuseLogPager;
|
|
use MediaWiki\Linker\LinkRenderer;
|
|
use MediaWiki\MediaWikiServices;
|
|
use Xml;
|
|
|
|
class HideAbuseLog extends AbuseFilterView {
|
|
|
|
/** @var int[] */
|
|
private $hideIDs;
|
|
|
|
/**
|
|
* @param AbuseFilterPermissionManager $afPermManager
|
|
* @param IContextSource $context
|
|
* @param LinkRenderer $linkRenderer
|
|
* @param string $basePageName
|
|
*/
|
|
public function __construct(
|
|
AbuseFilterPermissionManager $afPermManager,
|
|
IContextSource $context,
|
|
LinkRenderer $linkRenderer,
|
|
string $basePageName
|
|
) {
|
|
parent::__construct( $afPermManager, $context, $linkRenderer, $basePageName, [] );
|
|
$this->hideIDs = array_keys( $this->getRequest()->getArray( 'hideids', [] ) );
|
|
}
|
|
|
|
/**
|
|
* Shows the page
|
|
*/
|
|
public function show() : void {
|
|
$output = $this->getOutput();
|
|
$output->enableOOUI();
|
|
|
|
if ( !$this->afPermManager->canHideAbuseLog( $this->getUser() ) ) {
|
|
$output->addWikiMsg( 'abusefilter-log-hide-forbidden' );
|
|
return;
|
|
}
|
|
|
|
if ( !$this->hideIDs ) {
|
|
$output->addWikiMsg( 'abusefilter-log-hide-no-selected' );
|
|
return;
|
|
}
|
|
|
|
// TODO DI
|
|
$pager = new AbuseLogPager(
|
|
$this->getContext(),
|
|
MediaWikiServices::getInstance()->getLinkRenderer(),
|
|
[ 'afl_id' => $this->hideIDs ],
|
|
MediaWikiServices::getInstance()->getLinkBatchFactory(),
|
|
MediaWikiServices::getInstance()->getPermissionManager(),
|
|
$this->afPermManager,
|
|
$this->basePageName,
|
|
array_fill_keys( $this->hideIDs, $this->getRequest()->getVal( 'wpshoworhide' ) )
|
|
);
|
|
$pager->doQuery();
|
|
if ( $pager->getResult()->numRows() === 0 ) {
|
|
$output->addWikiMsg( 'abusefilter-log-hide-no-selected' );
|
|
return;
|
|
}
|
|
|
|
$output->wrapWikiMsg(
|
|
"<strong>$1</strong>",
|
|
[
|
|
'abusefilter-log-hide-selected',
|
|
$this->getLanguage()->formatNum( count( $this->hideIDs ) )
|
|
]
|
|
);
|
|
$output->addHTML( Xml::tags( 'ul', [ 'class' => 'plainlinks' ], $pager->getBody() ) );
|
|
|
|
$hideReasonsOther = $this->msg( 'revdelete-reasonotherlist' )->text();
|
|
$hideReasons = $this->msg( 'revdelete-reason-dropdown-suppress' )->inContentLanguage()->text();
|
|
$hideReasons = Xml::listDropDownOptions( $hideReasons, [ 'other' => $hideReasonsOther ] );
|
|
|
|
$formInfo = [
|
|
'showorhide' => [
|
|
'type' => 'radio',
|
|
'label-message' => 'abusefilter-log-hide-set-visibility',
|
|
'options-messages' => [
|
|
'abusefilter-log-hide-show' => 'show',
|
|
'abusefilter-log-hide-hide' => 'hide'
|
|
],
|
|
'default' => 'hide',
|
|
'flatlist' => true
|
|
],
|
|
'dropdownreason' => [
|
|
'type' => 'select',
|
|
'options' => $hideReasons,
|
|
'label-message' => 'abusefilter-log-hide-reason'
|
|
],
|
|
'reason' => [
|
|
'type' => 'text',
|
|
'label-message' => 'abusefilter-log-hide-reason-other',
|
|
],
|
|
];
|
|
|
|
$actionURL = $this->getTitle( 'hide' )->getFullURL( [ 'hideids' => array_fill_keys( $this->hideIDs, 1 ) ] );
|
|
HTMLForm::factory( 'ooui', $formInfo, $this->getContext() )
|
|
->setAction( $actionURL )
|
|
->setWrapperLegend( $this->msg( 'abusefilter-log-hide-legend' )->text() )
|
|
->setSubmitCallback( [ $this, 'saveHideForm' ] )
|
|
->showAlways();
|
|
|
|
// Show suppress log for this entry. Hack: since every suppression is performed on a
|
|
// totally different page (i.e. Special:AbuseLog/xxx), we use showLogExtract without
|
|
// specifying a title and then adding it in conds.
|
|
// This isn't shown if the request was posted because we update visibility in a DeferredUpdate, so it would
|
|
// display outdated info that might confuse the user.
|
|
// TODO Can we improve this somehow?
|
|
if ( !$this->getRequest()->wasPosted() ) {
|
|
$suppressLogPage = new LogPage( 'suppress' );
|
|
$output->addHTML( "<h2>" . $suppressLogPage->getName()->escaped() . "</h2>\n" );
|
|
$searchTitles = [];
|
|
foreach ( $this->hideIDs as $id ) {
|
|
$searchTitles[] = $this->getTitle( (string)$id )->getDBKey();
|
|
}
|
|
$conds = [ 'log_namespace' => NS_SPECIAL, 'log_title' => $searchTitles ];
|
|
LogEventsList::showLogExtract( $output, 'suppress', '', '', [ 'conds' => $conds ] );
|
|
}
|
|
}
|
|
|
|
/**
|
|
* Process the hide form after submission. This performs the actual visibility update. Used as callback by HTMLForm
|
|
*
|
|
* @param array $fields
|
|
* @return bool|array True on success, array of error message keys otherwise
|
|
*/
|
|
public function saveHideForm( array $fields ) {
|
|
// Determine which rows actually have to be changed
|
|
$dbw = wfGetDB( DB_MASTER );
|
|
$newValue = $fields['showorhide'] === 'hide' ? 1 : 0;
|
|
$actualIDs = $dbw->selectFieldValues(
|
|
'abuse_filter_log',
|
|
'afl_id',
|
|
[ 'afl_id' => $this->hideIDs, "afl_deleted != $newValue" ],
|
|
__METHOD__
|
|
);
|
|
if ( !count( $actualIDs ) ) {
|
|
return [ 'abusefilter-log-hide-no-change' ];
|
|
}
|
|
|
|
$dbw->update(
|
|
'abuse_filter_log',
|
|
[ 'afl_deleted' => $newValue ],
|
|
[ 'afl_id' => $actualIDs ],
|
|
__METHOD__
|
|
);
|
|
|
|
// Log in a DeferredUpdates to avoid potential flood
|
|
DeferredUpdates::addCallableUpdate( function () use ( $fields, $actualIDs ) {
|
|
$reason = $fields['dropdownreason'];
|
|
if ( $reason === 'other' ) {
|
|
$reason = $fields['reason'];
|
|
} elseif ( $fields['reason'] !== '' ) {
|
|
$reason .=
|
|
$this->msg( 'colon-separator' )->inContentLanguage()->text() . $fields['reason'];
|
|
}
|
|
|
|
$action = $fields['showorhide'] === 'hide' ? 'hide-afl' : 'unhide-afl';
|
|
foreach ( $actualIDs as $logid ) {
|
|
$logEntry = new ManualLogEntry( 'suppress', $action );
|
|
$logEntry->setPerformer( $this->getUser() );
|
|
$logEntry->setTarget( $this->getTitle( $logid ) );
|
|
$logEntry->setComment( $reason );
|
|
$logEntry->insert();
|
|
}
|
|
} );
|
|
|
|
$count = count( $actualIDs );
|
|
$this->getOutput()->prependHTML(
|
|
Html::successBox(
|
|
$this->msg( 'abusefilter-log-hide-done' )->params(
|
|
$this->getLanguage()->formatNum( $count ),
|
|
// Messages used: abusefilter-log-hide-done-hide, abusefilter-log-hide-done-show
|
|
$this->msg( 'abusefilter-log-hide-done-' . $fields['showorhide'] )->numParams( $count )->text()
|
|
)->escaped()
|
|
)
|
|
);
|
|
|
|
return true;
|
|
}
|
|
|
|
}
|