Code Coverage
 
Lines
Functions and Methods
Classes and Traits
Total
0.00% covered (danger)
0.00%
0 / 39
0.00% covered (danger)
0.00%
0 / 2
CRAP
0.00% covered (danger)
0.00%
0 / 1
GeneratePhpCharToUpperMappings
0.00% covered (danger)
0.00%
0 / 36
0.00% covered (danger)
0.00%
0 / 2
90
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
 execute
0.00% covered (danger)
0.00%
0 / 34
0.00% covered (danger)
0.00%
0 / 1
72
1<?php
2
3/**
4 * Update list of upper case differences between JS and PHP
5 *
6 * This program is free software; you can redistribute it and/or modify
7 * it under the terms of the GNU General Public License as published by
8 * the Free Software Foundation; either version 2 of the License, or
9 * (at your option) any later version.
10 *
11 * This program is distributed in the hope that it will be useful,
12 * but WITHOUT ANY WARRANTY; without even the implied warranty of
13 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14 * GNU General Public License for more details.
15 *
16 * You should have received a copy of the GNU General Public License along
17 * with this program; if not, write to the Free Software Foundation, Inc.,
18 * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
19 * http://www.gnu.org/copyleft/gpl.html
20 *
21 * @file
22 * @ingroup Maintenance
23 */
24
25use MediaWiki\Shell\Shell;
26
27require_once __DIR__ . '/../Maintenance.php';
28
29/**
30 * Update list of upper case differences between JS and PHP
31 *
32 * @ingroup Maintenance
33 * @since 1.33
34 */
35class GeneratePhpCharToUpperMappings extends Maintenance {
36
37    public function __construct() {
38        parent::__construct();
39        $this->addDescription( 'Update list of upper case differences between JS and PHP.' );
40    }
41
42    public function execute() {
43        global $IP;
44
45        $data = [];
46
47        $result = Shell::command(
48                [ 'node', $IP . '/maintenance/mediawiki.Title/generateJsToUpperCaseList.js' ]
49            )
50            // Node allocates lots of memory
51            ->limits( [ 'memory' => 1024 * 1024 ] )
52            ->execute();
53
54        if ( $result->getExitCode() !== 0 ) {
55            $this->output( $result->getStderr() );
56            return;
57        }
58
59        $jsUpperChars = json_decode( $result->getStdout() );
60        '@phan-var string[] $jsUpperChars';
61
62        $contentLanguage = $this->getServiceContainer()->getContentLanguage();
63        for ( $i = 0; $i <= 0x10ffff; $i++ ) {
64            if ( $i >= 0xd800 && $i <= 0xdfff ) {
65                // Skip surrogate pairs
66                continue;
67            }
68            $char = \UtfNormal\Utils::codepointToUtf8( $i );
69            $phpUpper = $contentLanguage->ucfirst( $char );
70            $jsUpper = $jsUpperChars[$i];
71            if ( $jsUpper !== $phpUpper ) {
72                if ( $char === $phpUpper ) {
73                    // Optimisation: Use 0 to signal "leave character unchanged".
74                    // Reduces the transfer size by ~50%. Reduces browser memory cost as well.
75                    $data[$char] = 0;
76                } else {
77                    $data[$char] = $phpUpper;
78                }
79            }
80        }
81
82        $mappingJson = str_replace( '    ', "\t",
83            json_encode( $data, JSON_PRETTY_PRINT | JSON_UNESCAPED_UNICODE )
84        ) . "\n";
85        $outputPath = '/resources/src/mediawiki.Title/phpCharToUpper.json';
86        $file = fopen( $IP . $outputPath, 'w' );
87        if ( !$file ) {
88            $this->fatalError( "Unable to write file \"$IP$outputPath\"" );
89        }
90        fwrite( $file, $mappingJson );
91
92        $this->output( count( $data ) . " differences found.\n" );
93        $this->output( "Written to $outputPath\n" );
94    }
95}
96
97$maintClass = GeneratePhpCharToUpperMappings::class;
98require_once RUN_MAINTENANCE_IF_MAIN;