Code Coverage
 
Lines
Functions and Methods
Classes and Traits
Total
94.12% covered (success)
94.12%
16 / 17
66.67% covered (warning)
66.67%
2 / 3
CRAP
0.00% covered (danger)
0.00%
0 / 1
ArticleTopicFiltersRegistry
94.12% covered (success)
94.12%
16 / 17
66.67% covered (warning)
66.67%
2 / 3
8.01
0.00% covered (danger)
0.00%
0 / 1
 getTopicList
100.00% covered (success)
100.00%
4 / 4
100.00% covered (success)
100.00%
1 / 1
2
 getGroupedTopics
0.00% covered (danger)
0.00%
0 / 1
0.00% covered (danger)
0.00%
0 / 1
2
 getTopicMessages
100.00% covered (success)
100.00%
12 / 12
100.00% covered (success)
100.00%
1 / 1
5
1<?php
2
3declare( strict_types = 1 );
4
5namespace MediaWiki\Extension\WikimediaMessages;
6
7use InvalidArgumentException;
8
9/**
10 * This class provides a list of topic filters for articles that can be presented directly to users. Each filter defined
11 * here is mapped to one or more topics in the Articletopic taxonomy (https://www.mediawiki.org/wiki/ORES/Articletopic)
12 * used by LiftWing (https://api.wikimedia.org/wiki/Lift_Wing_API/Reference/Get_articletopic_outlink_prediction).
13 * Topic filters are grouped by category, and both the topics and the categories are localisable.
14 * Originally written for the ContentTranslation extension in includes/ArticleTopicsDefinition.php.
15 */
16class ArticleTopicFiltersRegistry {
17    private const FILTERS = [
18        [
19            'groupId' => 'geography',
20            'msgKey' => 'wikimedia-articletopics-group-geography',
21            'topics' => [
22                [
23                    'topicId' => 'africa',
24                    'msgKey' => 'wikimedia-articletopics-topic-africa',
25                    'articleTopics' => [
26                        'africa',
27                        'central-africa',
28                        'eastern-africa',
29                        'northern-africa',
30                        'southern-africa',
31                        'western-africa',
32                    ],
33                ],
34                [
35                    'topicId' => 'asia',
36                    'msgKey' => 'wikimedia-articletopics-topic-asia',
37                    'articleTopics' => [
38                        'asia',
39                        'central-asia',
40                        'east-asia',
41                        'north-asia',
42                        'south-asia',
43                        'southeast-asia',
44                        'west-asia',
45                    ],
46                ],
47                [
48                    'topicId' => 'central-america',
49                    'msgKey' => 'wikimedia-articletopics-topic-central-america',
50                    'articleTopics' => [ 'central-america' ],
51                ],
52                [
53                    'topicId' => 'north-america',
54                    'msgKey' => 'wikimedia-articletopics-topic-north-america',
55                    'articleTopics' => [ 'north-america' ],
56                ],
57                [
58                    'topicId' => 'south-america',
59                    'msgKey' => 'wikimedia-articletopics-topic-south-america',
60                    'articleTopics' => [ 'south-america' ],
61                ],
62                [
63                    'topicId' => 'europe',
64                    'msgKey' => 'wikimedia-articletopics-topic-europe',
65                    'articleTopics' => [
66                        'europe',
67                        'eastern-europe',
68                        'northern-europe',
69                        'southern-europe',
70                        'western-europe',
71                    ],
72                ],
73                [
74                    'topicId' => 'oceania',
75                    'msgKey' => 'wikimedia-articletopics-topic-oceania',
76                    'articleTopics' => [ 'oceania' ],
77                ],
78            ],
79        ],
80        [
81            'groupId' => 'culture',
82            'msgKey' => 'wikimedia-articletopics-group-culture',
83            'topics' => [
84                [
85                    'topicId' => 'architecture',
86                    'msgKey' => 'wikimedia-articletopics-topic-architecture',
87                    'articleTopics' => [ 'architecture' ],
88                ],
89                [
90                    'topicId' => 'art',
91                    'msgKey' => 'wikimedia-articletopics-topic-art',
92                    'articleTopics' => [ 'visual-arts' ],
93                ],
94                [
95                    'topicId' => 'comics-and-anime',
96                    'msgKey' => 'wikimedia-articletopics-topic-comics-and-anime',
97                    'articleTopics' => [ 'comics-and-anime' ],
98                ],
99                [
100                    'topicId' => 'entertainment',
101                    'msgKey' => 'wikimedia-articletopics-topic-entertainment',
102                    'articleTopics' => [
103                        'entertainment',
104                        'radio',
105                    ],
106                ],
107                [
108                    'topicId' => 'fashion',
109                    'msgKey' => 'wikimedia-articletopics-topic-fashion',
110                    'articleTopics' => [ 'fashion' ],
111                ],
112                [
113                    'topicId' => 'literature',
114                    'msgKey' => 'wikimedia-articletopics-topic-literature',
115                    'articleTopics' => [ 'books' ],
116                ],
117                [
118                    'topicId' => 'music',
119                    'msgKey' => 'wikimedia-articletopics-topic-music',
120                    'articleTopics' => [ 'music' ],
121                ],
122                [
123                    'topicId' => 'performing-arts',
124                    'msgKey' => 'wikimedia-articletopics-topic-performing-arts',
125                    'articleTopics' => [ 'performing-arts' ],
126                ],
127                [
128                    'topicId' => 'sports',
129                    'msgKey' => 'wikimedia-articletopics-topic-sports',
130                    'articleTopics' => [ 'sports' ],
131                ],
132                [
133                    'topicId' => 'tv-and-film',
134                    'msgKey' => 'wikimedia-articletopics-topic-tv-and-film',
135                    'articleTopics' => [ 'films', 'television' ],
136                ],
137                [
138                    'topicId' => 'video-games',
139                    'msgKey' => 'wikimedia-articletopics-topic-video-games',
140                    'articleTopics' => [ 'video-games' ],
141                ],
142            ],
143        ],
144        [
145            'groupId' => 'history-and-society',
146            'msgKey' => 'wikimedia-articletopics-group-history-and-society',
147            'topics' => [
148                [
149                    'topicId' => 'biography',
150                    'msgKey' => 'wikimedia-articletopics-topic-biography',
151                    'articleTopics' => [ 'biography' ],
152                ],
153                [
154                    'topicId' => 'business-and-economics',
155                    'msgKey' => 'wikimedia-articletopics-topic-business-and-economics',
156                    'articleTopics' => [ 'business-and-economics' ],
157                ],
158                [
159                    'topicId' => 'education',
160                    'msgKey' => 'wikimedia-articletopics-topic-education',
161                    'articleTopics' => [ 'education' ],
162                ],
163                [
164                    'topicId' => 'food-and-drink',
165                    'msgKey' => 'wikimedia-articletopics-topic-food-and-drink',
166                    'articleTopics' => [ 'food-and-drink' ],
167                ],
168                [
169                    'topicId' => 'history',
170                    'msgKey' => 'wikimedia-articletopics-topic-history',
171                    'articleTopics' => [ 'history' ],
172                ],
173                [
174                    'topicId' => 'military-and-warfare',
175                    'msgKey' => 'wikimedia-articletopics-topic-military-and-warfare',
176                    'articleTopics' => [ 'military-and-warfare' ],
177                ],
178                [
179                    'topicId' => 'philosophy-and-religion',
180                    'msgKey' => 'wikimedia-articletopics-topic-philosophy-and-religion',
181                    'articleTopics' => [ 'philosophy-and-religion' ],
182                ],
183                [
184                    'topicId' => 'politics-and-government',
185                    'msgKey' => 'wikimedia-articletopics-topic-politics-and-government',
186                    'articleTopics' => [ 'politics-and-government' ],
187                ],
188                [
189                    'topicId' => 'society',
190                    'msgKey' => 'wikimedia-articletopics-topic-society',
191                    'articleTopics' => [ 'society' ],
192                ],
193                [
194                    'topicId' => 'transportation',
195                    'msgKey' => 'wikimedia-articletopics-topic-transportation',
196                    'articleTopics' => [ 'transportation' ],
197                ],
198                [
199                    'topicId' => 'women',
200                    'msgKey' => 'wikimedia-articletopics-topic-women',
201                    'articleTopics' => [ 'women' ],
202                ],
203            ],
204        ],
205        [
206            'groupId' => 'science-technology-and-math',
207            'msgKey' => 'wikimedia-articletopics-group-science-technology-and-math',
208            'topics' => [
209                [
210                    'topicId' => 'biology',
211                    'msgKey' => 'wikimedia-articletopics-topic-biology',
212                    'articleTopics' => [ 'biology' ],
213                ],
214                [
215                    'topicId' => 'chemistry',
216                    'msgKey' => 'wikimedia-articletopics-topic-chemistry',
217                    'articleTopics' => [ 'chemistry' ],
218                ],
219                [
220                    'topicId' => 'computers-and-internet',
221                    'msgKey' => 'wikimedia-articletopics-topic-computers-and-internet',
222                    'articleTopics' => [
223                        'internet-culture',
224                        'computing',
225                        'software',
226                    ],
227                ],
228                [
229                    'topicId' => 'earth-and-environment',
230                    'msgKey' => 'wikimedia-articletopics-topic-earth-and-environment',
231                    'articleTopics' => [
232                        'geographical',
233                        'earth-and-environment',
234                    ],
235                ],
236                [
237                    'topicId' => 'engineering',
238                    'msgKey' => 'wikimedia-articletopics-topic-engineering',
239                    'articleTopics' => [ 'engineering' ],
240                ],
241                [
242                    'topicId' => 'general-science',
243                    'msgKey' => 'wikimedia-articletopics-topic-general-science',
244                    'articleTopics' => [ 'stem' ],
245                ],
246                [
247                    'topicId' => 'mathematics',
248                    'msgKey' => 'wikimedia-articletopics-topic-mathematics',
249                    'articleTopics' => [ 'mathematics' ],
250                ],
251                [
252                    'topicId' => 'medicine-and-health',
253                    'msgKey' => 'wikimedia-articletopics-topic-medicine-and-health',
254                    'articleTopics' => [ 'medicine-and-health' ],
255                ],
256                [
257                    'topicId' => 'physics',
258                    'msgKey' => 'wikimedia-articletopics-topic-physics',
259                    'articleTopics' => [
260                        'physics',
261                        'space',
262                    ],
263                ],
264                [
265                    'topicId' => 'technology',
266                    'msgKey' => 'wikimedia-articletopics-topic-technology',
267                    'articleTopics' => [ 'technology' ],
268                ],
269            ],
270        ],
271    ];
272
273    /**
274     * Returns a plain list of topic IDs, for validation and the like.
275     * @return list<string>
276     */
277    public static function getTopicList(): array {
278        $topics = [];
279        foreach ( self::FILTERS as $group ) {
280            $topics = array_merge( $topics, array_column( $group['topics'], 'topicId' ) );
281        }
282        return $topics;
283    }
284
285    /**
286     * Get the article topics definition, organized into groups with their associated articletopics and label messages.
287     *
288     * @return array[]
289     * @phan-return list<array{groupId:string,msgKey:string,topics:list<array{topicId:string,msgKey:string,articleTopics:list<string>}>}>
290     */
291    public static function getGroupedTopics(): array {
292        return self::FILTERS;
293    }
294
295    /**
296     * Returns message keys for the given topic IDs. The caller is responsible for validating that all the given
297     * topics exist.
298     *
299     * @param string[] $topicIDs
300     * @return array<string,string>
301     */
302    public static function getTopicMessages( array $topicIDs ): array {
303        $flatTopics = array_merge( ...array_column( self::FILTERS, 'topics' ) );
304        $topicCount = count( $flatTopics );
305        $ret = [];
306        $toFind = array_fill_keys( $topicIDs, true );
307        for ( $i = 0; $i < $topicCount && $toFind !== []; $i++ ) {
308            $curTopic = $flatTopics[$i]['topicId'];
309            if ( isset( $toFind[$curTopic] ) ) {
310                $ret[$curTopic] = $flatTopics[$i]['msgKey'];
311                unset( $toFind[$curTopic] );
312            }
313        }
314        if ( $toFind ) {
315            throw new InvalidArgumentException( "Unrecognized topics: " . implode( ', ', array_keys( $toFind ) ) );
316        }
317        return $ret;
318    }
319}