Make WordPress Core

Changeset 57513


Ignore:
Timestamp:
02/01/2024 11:43:21 AM (15 months ago)
Author:
swissspidy
Message:

I18N: Improve singular lookup of pluralized strings.

Ensures that string lookup in MO files only uses the singular string.

This matches expected behavior with gettext files and improves compatibility for cases where for example both __( 'Product' ) and _n( 'Product', 'Products’, num ) are used in a project, where both will use the same translation for the singular version. Maintains backward compatibility and feature parity with the pomo library and the PHP translation file format.

Replaces [57386], which was reverted in [57505], with a more accurate and performant solution.

See #59656.

Location:
trunk
Files:
6 edited

Legend:

Unmodified
Added
Removed
  • trunk/src/wp-includes/l10n/class-wp-translation-file-mo.php

    r57337 r57513  
    162162                }
    163163            } else {
    164                 $this->entries[ (string) $original ] = $translation;
     164                /*
     165                 * In MO files, the key normally contains both singular and plural versions.
     166                 * However, this just adds the singular string for lookup,
     167                 * which caters for cases where both __( 'Product' ) and _n( 'Product', 'Products' )
     168                 * are used and the translation is expected to be the same for both.
     169                 */
     170                $parts = explode( "\0", (string) $original );
     171
     172                $this->entries[ $parts[0] ] = $translation;
    165173            }
    166174        }
  • trunk/src/wp-includes/l10n/class-wp-translation-file-php.php

    r57337 r57513  
    2929
    3030        if ( isset( $result['messages'] ) && is_array( $result['messages'] ) ) {
    31             foreach ( $result['messages'] as $singular => $translations ) {
    32                 if ( is_array( $translations ) ) {
    33                     $this->entries[ $singular ] = implode( "\0", $translations );
    34                 } elseif ( is_string( $translations ) ) {
    35                     $this->entries[ $singular ] = $translations;
    36                 }
     31            foreach ( $result['messages'] as $original => $translation ) {
     32                $this->entries[ (string) $original ] = $translation;
    3733            }
    3834            unset( $result['messages'] );
  • trunk/src/wp-includes/l10n/class-wp-translations.php

    r57344 r57513  
    9696        }
    9797
    98         // Look for plural original.
    99         $parts           = explode( "\0", $original );
    100         $entry->singular = $parts[0];
    101         if ( isset( $parts[1] ) ) {
    102             $entry->is_plural = true;
    103             $entry->plural    = $parts[1];
    104         }
     98        $entry->singular     = $original;
     99        $entry->translations = explode( "\0", $translations );
     100        $entry->is_plural    = count( $entry->translations ) > 1;
    105101
    106         $entry->translations = explode( "\0", $translations );
    107102        return $entry;
    108103    }
  • trunk/tests/phpunit/data/l10n/example-simple.php

    r57386 r57513  
    33    'messages' =>
    44        [
    5             'original' => ['translation'],
    6             'contextoriginal with context' => ['translation with context'],
    7             'plural0' . "\0" . 'plural1' => ['translation0', 'translation1'],
    8             'contextplural0 with context' . "\0" . 'plural1 with context' => ['translation0 with context', 'translation1 with context'],
    9             'Product' . "\0" . 'Products' => 'Produkt' . "\0" . 'Produkte',
     5            'original' => 'translation',
     6            'contextoriginal with context' => 'translation with context',
     7            'plural0' => 'translation0'  . "\0" . 'translation1',
     8            'contextplural0 with context' => 'translation0 with context' . "\0" . 'translation1 with context',
     9            'Product' => 'Produkt' . "\0" . 'Produkte',
    1010        ],
    1111];
  • trunk/tests/phpunit/tests/l10n/wpTranslations.php

    r57344 r57513  
    7272                new Translation_Entry(
    7373                    array(
     74                        'is_plural'    => true,
    7475                        'singular'     => 'one dragon',
    75                         'plural'       => '%d dragons',
    7676                        'translations' => array(
    7777                            'oney dragoney',
     
    120120                        'is_plural'    => true,
    121121                        'singular'     => 'one dragon',
    122                         'plural'       => '%d dragons',
    123122                        'context'      => 'dragonland',
    124123                        'translations' => array(
  • trunk/tests/phpunit/tests/l10n/wpTranslationsConvert.php

    r57505 r57513  
    200200        $this->assertSame( 'translation0 with context', $controller->translate_plural( array( 'plural0 with context', 'plural1 with context' ), 1, 'context', 'unittest' ) );
    201201        $this->assertSame( 'translation1 with context', $controller->translate_plural( array( 'plural0 with context', 'plural1 with context' ), 2, 'context', 'unittest' ) );
     202
     203        $this->assertSame( 'Produkt', $controller->translate( 'Product', '', 'unittest' ) );
     204        $this->assertSame( 'Produkt', $controller->translate_plural( array( 'Product', 'Products' ), 1, '', 'unittest' ) );
     205        $this->assertSame( 'Produkte', $controller->translate_plural( array( 'Product', 'Products' ), 2, '', 'unittest' ) );
    202206    }
    203207
Note: See TracChangeset for help on using the changeset viewer.