MediaWiki master
RemoteIcuCollation.php
Go to the documentation of this file.
1<?php
2
4use Shellbox\RPC\RpcClient;
5
12 private RpcClient $rpcClient;
13 private string $locale;
14
15 public function __construct( ShellboxClientFactory $shellboxClientFactory, string $locale ) {
16 $this->rpcClient = $shellboxClientFactory->getRpcClient(
17 [ 'service' => 'icu-collation' ] );
18 $this->locale = $locale;
19 }
20
21 public function getSortKey( $string ) {
22 return $this->getSortKeys( [ $string ] )[0];
23 }
24
31 private static function encode( $strings ) {
32 $ret = '';
33 foreach ( $strings as $s ) {
34 $ret .= sprintf( "%08x", strlen( $s ) ) . $s;
35 }
36 return $ret;
37 }
38
45 private static function decode( $blob ) {
46 $p = 0;
47 $ret = [];
48 while ( $p < strlen( $blob ) ) {
49 $len = intval( substr( $blob, $p, 8 ), 16 );
50 $p += 8;
51 $ret[] = substr( $blob, $p, $len );
52 $p += $len;
53 }
54 return $ret;
55 }
56
57 public function getSortKeys( $strings ) {
58 if ( !count( $strings ) ) {
59 return [];
60 }
61 $blob = $this->rpcClient->call(
62 'icu-collation',
63 self::class . '::' . 'doGetSortKeys',
64 [
65 $this->locale,
66 self::encode( array_values( $strings ) )
67 ],
68 [
69 'classes' => [ parent::class, self::class ],
70 'binary' => true
71 ]
72 );
73 return array_combine(
74 array_keys( $strings ),
75 self::decode( $blob )
76 );
77 }
78
79 public function getFirstLetter( $string ) {
80 // @phan-suppress-previous-line PhanPluginNeverReturnMethod
81 throw new RuntimeException( __METHOD__ . ': not implemented' );
82 }
83
91 public static function doGetSortKeys( $locale, $blob ) {
92 $mainCollator = Collator::create( $locale );
93 if ( !$mainCollator ) {
94 throw new RuntimeException( "Invalid ICU locale specified for collation: $locale" );
95 }
96
97 // If the special suffix for numeric collation is present, turn on numeric collation.
98 if ( str_ends_with( $locale, '-u-kn' ) ) {
99 $mainCollator->setAttribute( Collator::NUMERIC_COLLATION, Collator::ON );
100 }
101 $ret = [];
102 foreach ( self::decode( $blob ) as $string ) {
103 $ret[] = $mainCollator->getSortKey( $string );
104 }
105 return self::encode( $ret );
106 }
107}
This is a service which provides a configured client to access a remote Shellbox installation.
getRpcClient(array $options=[])
Get a Shellbox RPC client with specified options.
An ICU collation that uses a remote server to compute sort keys.
static doGetSortKeys( $locale, $blob)
The remote entry point.
__construct(ShellboxClientFactory $shellboxClientFactory, string $locale)
getSortKey( $string)
Given a string, convert it to a (hopefully short) key that can be used for efficient sorting.
getSortKeys( $strings)
Get multiple sort keys.
getFirstLetter( $string)
Given a string, return the logical "first letter" to be used for grouping on category pages and so on...