Code Coverage
 
Lines
Functions and Methods
Classes and Traits
Total
0.00% covered (danger)
0.00%
0 / 44
0.00% covered (danger)
0.00%
0 / 4
CRAP
0.00% covered (danger)
0.00%
0 / 1
AceEditBoxBuilder
0.00% covered (danger)
0.00%
0 / 44
0.00% covered (danger)
0.00%
0 / 4
20
0.00% covered (danger)
0.00%
0 / 1
 __construct
0.00% covered (danger)
0.00%
0 / 2
0.00% covered (danger)
0.00%
0 / 1
2
 getEditBox
0.00% covered (danger)
0.00%
0 / 11
0.00% covered (danger)
0.00%
0 / 1
2
 getEditorControls
0.00% covered (danger)
0.00%
0 / 12
0.00% covered (danger)
0.00%
0 / 1
2
 getAceConfig
0.00% covered (danger)
0.00%
0 / 19
0.00% covered (danger)
0.00%
0 / 1
2
1<?php
2
3namespace MediaWiki\Extension\AbuseFilter\EditBox;
4
5use MediaWiki\Extension\AbuseFilter\AbuseFilterPermissionManager;
6use MediaWiki\Extension\AbuseFilter\KeywordsManager;
7use MediaWiki\Extension\AbuseFilter\Parser\AbuseFilterTokenizer;
8use MediaWiki\Extension\AbuseFilter\Parser\FilterEvaluator;
9use MediaWiki\Output\OutputPage;
10use MediaWiki\Permissions\Authority;
11use MessageLocalizer;
12use OOUI\ButtonWidget;
13use OOUI\HorizontalLayout;
14use OOUI\Widget;
15use Xml;
16
17/**
18 * Class responsible for building filter edit boxes with both the Ace and the plain version
19 */
20class AceEditBoxBuilder extends EditBoxBuilder {
21
22    /** @var PlainEditBoxBuilder */
23    private $plainBuilder;
24
25    /**
26     * @inheritDoc
27     * @param PlainEditBoxBuilder $plainBuilder
28     */
29    public function __construct(
30        AbuseFilterPermissionManager $afPermManager,
31        KeywordsManager $keywordsManager,
32        MessageLocalizer $messageLocalizer,
33        Authority $authority,
34        OutputPage $output,
35        PlainEditBoxBuilder $plainBuilder
36    ) {
37        parent::__construct( $afPermManager, $keywordsManager, $messageLocalizer, $authority, $output );
38        $this->plainBuilder = $plainBuilder;
39    }
40
41    /**
42     * @inheritDoc
43     */
44    protected function getEditBox( string $rules, bool $isUserAllowed, bool $externalForm ): string {
45        $rules = rtrim( $rules ) . "\n";
46
47        $attribs = [
48            // Rules are in English
49            'dir' => 'ltr',
50            'name' => 'wpAceFilterEditor',
51            'id' => 'wpAceFilterEditor',
52            'class' => 'mw-abusefilter-editor'
53        ];
54        $rulesContainer = Xml::element( 'div', $attribs, $rules );
55        $editorConfig = $this->getAceConfig( $isUserAllowed );
56        $this->output->addJsConfigVars( 'aceConfig', $editorConfig );
57        return $rulesContainer . $this->plainBuilder->getEditBox( $rules, $isUserAllowed, $externalForm );
58    }
59
60    /**
61     * @inheritDoc
62     */
63    protected function getEditorControls(): Widget {
64        $base = parent::getEditorControls();
65        $switchEditor = new ButtonWidget(
66            [
67                'label' => $this->localizer->msg( 'abusefilter-edit-switch-editor' )->text(),
68                'id' => 'mw-abusefilter-switcheditor'
69            ]
70        );
71        return new Widget( [
72            'content' => new HorizontalLayout( [
73                'items' => [ $switchEditor, $base ]
74            ] )
75        ] );
76    }
77
78    /**
79     * Extract values for syntax highlight
80     *
81     * @param bool $canEdit
82     * @return array
83     */
84    private function getAceConfig( bool $canEdit ): array {
85        $values = $this->keywordsManager->getBuilderValues();
86        $deprecatedVars = $this->keywordsManager->getDeprecatedVariables();
87
88        $builderVariables = implode( '|', array_keys( $values['vars'] ) );
89        $builderFunctions = implode( '|', array_keys( FilterEvaluator::FUNCTIONS ) );
90        // AbuseFilterTokenizer::KEYWORDS also includes constants (true, false and null),
91        // but Ace redefines these constants afterwards so this will not be an issue
92        $builderKeywords = implode( '|', AbuseFilterTokenizer::KEYWORDS );
93        // Extract operators from tokenizer like we do in AbuseFilterParserTest
94        $operators = implode( '|', array_map( static function ( $op ) {
95            return preg_quote( $op, '/' );
96        }, AbuseFilterTokenizer::OPERATORS ) );
97        $deprecatedVariables = implode( '|', array_keys( $deprecatedVars ) );
98        $disabledVariables = implode( '|', array_keys( $this->keywordsManager->getDisabledVariables() ) );
99
100        return [
101            'variables' => $builderVariables,
102            'functions' => $builderFunctions,
103            'keywords' => $builderKeywords,
104            'operators' => $operators,
105            'deprecated' => $deprecatedVariables,
106            'disabled' => $disabledVariables,
107            'aceReadOnly' => !$canEdit
108        ];
109    }
110}