Code Coverage
 
Lines
Functions and Methods
Classes and Traits
Total
80.00% covered (warning)
80.00%
20 / 25
42.86% covered (danger)
42.86%
3 / 7
CRAP
0.00% covered (danger)
0.00%
0 / 1
AutoModeratorWikiConfigLoader
80.00% covered (warning)
80.00%
20 / 25
42.86% covered (danger)
42.86%
3 / 7
18.05
0.00% covered (danger)
0.00%
0 / 1
 __construct
0.00% covered (danger)
0.00%
0 / 1
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    public const ALLOW_LIST = [
24        'AutoModeratorEnableRevisionCheck',
25        'AutoModeratorFalsePositivePageTitle',
26        'AutoModeratorUseEditFlagMinor',
27        'AutoModeratorRevertTalkPageMessageEnabled',
28        'AutoModeratorRevertTalkPageMessageRegisteredUsersOnly',
29        'AutoModeratorEnableBotFlag',
30        'AutoModeratorSkipUserRights',
31        'AutoModeratorCautionLevel',
32        'AutoModeratorEnableUserRevertsPerPage',
33        'AutoModeratorUserRevertsPerPage',
34        'AutoModeratorHelpPageLink',
35        'AutoModeratorMultilingualConfigEnableRevisionCheck',
36        'AutoModeratorMultilingualConfigFalsePositivePageTitle',
37        'AutoModeratorMultilingualConfigUseEditFlagMinor',
38        'AutoModeratorMultilingualConfigRevertTalkPageMessageEnabled',
39        'AutoModeratorMultilingualConfigRevertTalkPageMessageRegisteredUsersOnly',
40        'AutoModeratorMultilingualConfigEnableBotFlag',
41        'AutoModeratorMultilingualConfigSkipUserRights',
42        'AutoModeratorMultilingualConfigCautionLevel',
43        'AutoModeratorMultilingualConfigEnableUserRevertsPerPage',
44        'AutoModeratorMultilingualConfigUserRevertsPerPage',
45        'AutoModeratorMultilingualConfigHelpPageLink',
46        'AutoModeratorMultilingualConfigEnableLanguageAgnostic',
47        'AutoModeratorMultilingualConfigEnableMultilingual',
48        'AutoModeratorMultilingualConfigMultilingualThreshold'
49    ];
50
51    /**
52     * Map of variable name => merge strategy. Defaults to replace.
53     * @see MergeStrategy
54     */
55    public const MERGE_STRATEGIES = [];
56
57    public function __construct(
58        private readonly WikiPageConfig $wikiPageConfig,
59        private readonly Config $globalVarConfig,
60    ) {
61    }
62
63    /**
64     * @param string $name
65     * @return bool
66     */
67    private function variableIsAllowed( $name ) {
68        return in_array( $name, self::ALLOW_LIST );
69    }
70
71    /**
72     * Determine if on-wiki config is enabled or not
73     *
74     * If this returns false, all calls to get()/has() will be immediately
75     * forwarded to GlobalVarConfig, as if there was no on-wiki config.
76     *
77     * @return bool
78     */
79    public function isWikiConfigEnabled(): bool {
80        return (bool)$this->globalVarConfig->get( 'AutoModeratorEnableWikiConfig' );
81    }
82
83    /**
84     * @inheritDoc
85     */
86    public function get( $name ) {
87        return $this->getWithFlags( $name );
88    }
89
90    /**
91     * @param string $name
92     * @param int $flags bit field, see IDBAccessObject::READ_XXX
93     * @return mixed Config value
94     */
95    public function getWithFlags( string $name, int $flags = 0 ) {
96        if ( !$this->isWikiConfigEnabled() ) {
97            return $this->globalVarConfig->get( $name );
98        }
99
100        if ( !$this->variableIsAllowed( $name ) ) {
101            throw new ConfigException( 'Config key cannot be retrieved via AutoModeratorWikiConfigLoader' );
102        }
103
104        if ( $this->wikiPageConfig->hasWithFlags( $name, $flags ) ) {
105            $wikiValue = $this->wikiPageConfig->getWithFlags( $name, $flags );
106            $mergeStrategy = self::MERGE_STRATEGIES[$name] ?? null;
107            if ( !$mergeStrategy || !$this->globalVarConfig->has( $name ) ) {
108                return $wikiValue;
109            }
110            $globalValue = $this->globalVarConfig->get( $name );
111            return MergeStrategy::newFromName( $mergeStrategy )->merge( $globalValue, $wikiValue );
112        }
113
114        if ( $this->globalVarConfig->has( $name ) ) {
115            return $this->globalVarConfig->get( $name );
116        }
117
118        throw new ConfigException( 'Config key was not found in AutoModeratorWikiConfigLoader' );
119    }
120
121    /**
122     * @inheritDoc
123     */
124    public function has( $name ): bool {
125        return $this->hasWithFlags( $name );
126    }
127
128    /**
129     * @param string $name
130     * @param int $flags
131     * @return bool
132     */
133    public function hasWithFlags( string $name, int $flags = 0 ): bool {
134        if ( !$this->isWikiConfigEnabled() ) {
135            return $this->globalVarConfig->has( $name );
136        }
137
138        return $this->variableIsAllowed( $name ) && (
139            $this->wikiPageConfig->hasWithFlags( $name, $flags ) ||
140            $this->globalVarConfig->has( $name )
141        );
142    }
143}