Merge "Tablesorter: Use localeCompare"
authorjenkins-bot <jenkins-bot@gerrit.wikimedia.org>
Fri, 28 Jun 2019 02:54:17 +0000 (02:54 +0000)
committerGerrit Code Review <gerrit@wikimedia.org>
Fri, 28 Jun 2019 02:54:17 +0000 (02:54 +0000)
resources/src/jquery.tablesorter/jquery.tablesorter.js
tests/qunit/suites/resources/jquery/jquery.tablesorter.parsers.test.js
tests/qunit/suites/resources/jquery/jquery.tablesorter.test.js

index c1b83fd..0c28b8e 100644 (file)
        }
 
        function sortText( a, b ) {
-               return ( ( a < b ) ? -1 : ( ( a > b ) ? 1 : 0 ) );
+               return ts.collator.compare( a, b );
        }
 
-       function sortTextDesc( a, b ) {
-               return ( ( b < a ) ? -1 : ( ( b > a ) ? 1 : 0 ) );
+       function sortNumeric( a, b ) {
+               return ( ( a < b ) ? -1 : ( ( a > b ) ? 1 : 0 ) );
        }
 
        function multisort( table, sortList, cache ) {
                var i,
-                       sortFn = [];
+                       sortFn = [],
+                       parsers = $( table ).data( 'tablesorter' ).config.parsers;
 
                for ( i = 0; i < sortList.length; i++ ) {
-                       sortFn[ i ] = ( sortList[ i ][ 1 ] ) ? sortTextDesc : sortText;
+                       // Android doesn't support Intl.Collator
+                       if ( window.Intl && Intl.Collator && parsers[ sortList[ i ][ 0 ] ].type === 'text' ) {
+                               sortFn[ i ] = sortText;
+                       } else {
+                               sortFn[ i ] = sortNumeric;
+                       }
                }
                cache.normalized.sort( function ( array1, array2 ) {
                        var i, col, ret;
                        for ( i = 0; i < sortList.length; i++ ) {
                                col = sortList[ i ][ 0 ];
-                               ret = sortFn[ i ].call( this, array1[ col ], array2[ col ] );
+                               if ( sortList[ i ][ 1 ] ) {
+                                       // descending
+                                       ret = sortFn[ i ].call( this, array2[ col ], array1[ col ] );
+                               } else {
+                                       // ascending
+                                       ret = sortFn[ i ].call( this, array1[ col ], array2[ col ] );
+                               }
                                if ( ret !== 0 ) {
                                        return ret;
                                }
                }
        }
 
-       function buildCollationTable() {
+       function buildCollation() {
                var key, keys = [];
                ts.collationTable = mw.config.get( 'tableSorterCollation' );
                ts.collationRegex = null;
                                ts.collationRegex = new RegExp( keys.join( '|' ), 'ig' );
                        }
                }
+               if ( window.Intl && Intl.Collator ) {
+                       ts.collator = new Intl.Collator( [
+                               mw.config.get( 'wgPageContentLanguage' ),
+                               mw.config.get( 'wgUserLanguage' )
+                       ], {
+                               numeric: true
+                       } );
+               }
        }
 
        function cacheRegexs() {
                                        // may customize tableSorterCollation but load after $.ready(), other
                                        // scripts may call .tablesorter() before they have done the
                                        // tableSorterCollation customizations.
-                                       buildCollationTable();
+                                       buildCollation();
 
                                        // Legacy fix of .sortbottoms
                                        // Wrap them inside a tfoot (because that's what they actually want to be)
                        buildTransformTable();
                        buildDateTable();
                        cacheRegexs();
-                       buildCollationTable();
+                       buildCollation();
 
                        return getParserById( id );
                },
                },
                format: function ( s ) {
                        var tsc;
-                       s = s.toLowerCase().trim();
+                       s = s.trim();
                        if ( ts.collationRegex ) {
                                tsc = ts.collationTable;
                                s = s.replace( ts.collationRegex, function ( match ) {
-                                       var r = tsc[ match ] ? tsc[ match ] : tsc[ match.toUpperCase() ];
-                                       return r.toLowerCase();
+                                       var r,
+                                               upper = match.toUpperCase(),
+                                               lower = match.toLowerCase();
+                                       if ( upper === match && !lower === match ) {
+                                               r = tsc[ lower ] ? tsc[ lower ] : tsc[ upper ];
+                                               r = r.toUpperCase();
+                                       } else {
+                                               r = tsc[ match.toLowerCase() ];
+                                       }
+                                       return r;
                                } );
                        }
                        return s;
index 4731b32..506b25b 100644 (file)
@@ -74,9 +74,9 @@
        }
 
        text = [
-               [ 'Mars', true, 'mars', 'Simple text' ],
-               [ 'Mẘas', true, 'mẘas', 'Non ascii character' ],
-               [ 'A sentence', true, 'a sentence', 'A sentence with space chars' ]
+               [ 'Mars', true, 'Mars', 'Simple text' ],
+               [ 'Mẘas', true, 'Mẘas', 'Non ascii character' ],
+               [ 'A sentence', true, 'A sentence', 'A sentence with space chars' ]
        ];
        parserTest( 'Textual keys', 'text', text );
 
index bd6ee16..f5de3ae 100644 (file)
                        [ 'Günther' ],
                        [ 'Peter' ],
                        [ 'Björn' ],
+                       [ 'ä' ],
+                       [ 'z' ],
                        [ 'Bjorn' ],
+                       [ 'BjÖrn' ],
+                       [ 'apfel' ],
                        [ 'Apfel' ],
                        [ 'Äpfel' ],
                        [ 'Strasse' ],
                        [ 'Sträßschen' ]
                ],
-               umlautWordsSorted = [
+               umlautWordsSortedEn = [
+                       [ 'ä' ],
                        [ 'Äpfel' ],
+                       [ 'apfel' ],
                        [ 'Apfel' ],
                        [ 'Björn' ],
+                       [ 'BjÖrn' ],
                        [ 'Bjorn' ],
                        [ 'Günther' ],
                        [ 'Peter' ],
                        [ 'Sträßschen' ],
-                       [ 'Strasse' ]
+                       [ 'Strasse' ],
+                       [ 'z' ]
+               ],
+               umlautWordsSortedSv = [
+                       [ 'apfel' ],
+                       [ 'Apfel' ],
+                       [ 'Bjorn' ],
+                       [ 'Björn' ],
+                       [ 'BjÖrn' ],
+                       [ 'Günther' ],
+                       [ 'Peter' ],
+                       [ 'Strasse' ],
+                       [ 'Sträßschen' ],
+                       [ 'z' ],
+                       [ 'ä' ], // ä sorts after z in Swedish
+                       [ 'Äpfel' ]
                ],
 
                // Data set "digraph"
                'Accented Characters with custom collation',
                [ 'Name' ],
                umlautWords,
-               umlautWordsSorted,
+               umlautWordsSortedEn,
                function ( $table ) {
                        mw.config.set( 'tableSorterCollation', {
                                ä: 'ae',
                }
        );
 
+       tableTest(
+               'Accented Characters Swedish locale',
+               [ 'Name' ],
+               umlautWords,
+               umlautWordsSortedSv,
+               function ( $table ) {
+                       mw.config.set( 'wgPageContentLanguage', 'sv' );
+
+                       $table.tablesorter();
+                       $table.find( '.headerSort:eq(0)' ).trigger( 'click' );
+               }
+       );
+
        tableTest(
                'Digraphs with custom collation',
                [ 'City' ],