Code Coverage
 
Lines
Functions and Methods
Classes and Traits
Total
76.92% covered (warning)
76.92%
20 / 26
42.86% covered (danger)
42.86%
3 / 7
CRAP
0.00% covered (danger)
0.00%
0 / 1
AutoModeratorWikiConfigLoader
76.92% covered (warning)
76.92%
20 / 26
42.86% covered (danger)
42.86%
3 / 7
19.15
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
 variableIsAllowed
0.00% covered (danger)
0.00%
0 / 1
0.00% covered (danger)
0.00%
0 / 1
2
 isWikiConfigEnabled
100.00% covered (success)
100.00%
1 / 1
100.00% covered (success)
100.00%
1 / 1
1
 get
100.00% covered (success)
100.00%
1 / 1
100.00% covered (success)
100.00%
1 / 1
1
 getWithFlags
85.71% covered (warning)
85.71%
12 / 14
0.00% covered (danger)
0.00%
0 / 1
7.14
 has
100.00% covered (success)
100.00%
1 / 1
100.00% covered (success)
100.00%
1 / 1
1
 hasWithFlags
83.33% covered (warning)
83.33%
5 / 6
0.00% covered (danger)
0.00%
0 / 1
4.07
1<?php
2
3namespace AutoModerator\Config;
4
5use MediaWiki\Config\Config;
6use MediaWiki\Config\ConfigException;
7use MediaWiki\Settings\Config\MergeStrategy;
8
9/**
10 * Config loader for wiki page config
11 *
12 * This class consults the allow list
13 * in AutoModeratorWikiConfigLoader::ALLOW_LIST, and runs
14 * WikiPageConfig if requested config variable is there. Otherwise,
15 * it throws an exception.
16 *
17 * Fallback to GlobalVarConfig is implemented, so developer setup
18 * works without any config page, and also to not let wikis break
19 * AutoModerator setup by removing an arbitrary config variable.
20 */
21class AutoModeratorWikiConfigLoader implements Config, ICustomReadConstants {
22
23    private WikiPageConfig $wikiPageConfig;
24    private Config $globalVarConfig;
25
26    public const ALLOW_LIST = [
27        'AutoModeratorEnableRevisionCheck',
28        'AutoModeratorFalsePositivePageTitle',
29        'AutoModeratorUseEditFlagMinor',
30        'AutoModeratorRevertTalkPageMessageEnabled',
31        'AutoModeratorEnableBotFlag',
32        'AutoModeratorSkipUserRights',
33        'AutoModeratorCautionLevel',
34        'AutoModeratorEnableUserRevertsPerPage',
35        'AutoModeratorUserRevertsPerPage'
36    ];
37
38    /**
39     * Map of variable name => merge strategy. Defaults to replace.
40     * @see MergeStrategy
41     */
42    public const MERGE_STRATEGIES = [];
43
44    /**
45     * @param WikiPageConfig $wikiPageConfig
46     * @param Config $globalVarConfig
47     */
48    public function __construct(
49        WikiPageConfig $wikiPageConfig,
50        Config $globalVarConfig
51    ) {
52        $this->wikiPageConfig = $wikiPageConfig;
53        $this->globalVarConfig = $globalVarConfig;
54    }
55
56    /**
57     * @param string $name
58     * @return bool
59     */
60    private function variableIsAllowed( $name ) {
61        return in_array( $name, self::ALLOW_LIST );
62    }
63
64    /**
65     * Determine if on-wiki config is enabled or not
66     *
67     * If this returns false, all calls to get()/has() will be immediately
68     * forwarded to GlobalVarConfig, as if there was no on-wiki config.
69     *
70     * @return bool
71     */
72    public function isWikiConfigEnabled(): bool {
73        return (bool)$this->globalVarConfig->get( 'AutoModeratorEnableWikiConfig' );
74    }
75
76    /**
77     * @inheritDoc
78     */
79    public function get( $name ) {
80        return $this->getWithFlags( $name );
81    }
82
83    /**
84     * @param string $name
85     * @param int $flags bit field, see IDBAccessObject::READ_XXX
86     * @return mixed Config value
87     */
88    public function getWithFlags( string $name, int $flags = 0 ) {
89        if ( !$this->isWikiConfigEnabled() ) {
90            return $this->globalVarConfig->get( $name );
91        }
92
93        if ( !$this->variableIsAllowed( $name ) ) {
94            throw new ConfigException( 'Config key cannot be retrieved via AutoModeratorWikiConfigLoader' );
95        }
96
97        if ( $this->wikiPageConfig->hasWithFlags( $name, $flags ) ) {
98            $wikiValue = $this->wikiPageConfig->getWithFlags( $name, $flags );
99            $mergeStrategy = self::MERGE_STRATEGIES[$name] ?? null;
100            if ( !$mergeStrategy || !$this->globalVarConfig->has( $name ) ) {
101                return $wikiValue;
102            }
103            $globalValue = $this->globalVarConfig->get( $name );
104            return MergeStrategy::newFromName( $mergeStrategy )->merge( $globalValue, $wikiValue );
105        }
106
107        if ( $this->globalVarConfig->has( $name ) ) {
108            return $this->globalVarConfig->get( $name );
109        }
110
111        throw new ConfigException( 'Config key was not found in AutoModeratorWikiConfigLoader' );
112    }
113
114    /**
115     * @inheritDoc
116     */
117    public function has( $name ): bool {
118        return $this->hasWithFlags( $name );
119    }
120
121    /**
122     * @param string $name
123     * @param int $flags
124     * @return bool
125     */
126    public function hasWithFlags( string $name, int $flags = 0 ): bool {
127        if ( !$this->isWikiConfigEnabled() ) {
128            return $this->globalVarConfig->has( $name );
129        }
130
131        return $this->variableIsAllowed( $name ) && (
132            $this->wikiPageConfig->hasWithFlags( $name, $flags ) ||
133            $this->globalVarConfig->has( $name )
134        );
135    }
136}