feature #26152 [Intl] Add polyfill for Locale::canonicalize() (nicolas-grekas)

This PR was merged into the 4.1-dev branch.

Discussion
----------

[Intl] Add polyfill for Locale::canonicalize()

| Q             | A
| ------------- | ---
| Branch?       | master
| Bug fix?      | yes
| New feature?  | yes
| BC breaks?    | no
| Deprecations? | no
| Tests pass?   | yes
| Fixed tickets | -
| License       | MIT
| Doc PR        | -

Required after #26069

Commits
-------

972a330 [Intl] Add polyfill for Locale::canonicalize()
This commit is contained in:
Nicolas Grekas 2018-02-12 17:35:36 +01:00
commit 06ab73bc38
4 changed files with 49 additions and 5 deletions

View File

@ -16,8 +16,8 @@ use Symfony\Component\Intl\Exception\MethodNotImplementedException;
/** /**
* Replacement for PHP's native {@link \Locale} class. * Replacement for PHP's native {@link \Locale} class.
* *
* The only method supported in this class is {@link getDefault}. This method * The only methods supported in this class are `getDefault` and `canonicalize`.
* will always return "en". All other methods will throw an exception when used. * All other methods will throw an exception when used.
* *
* @author Eriksen Costa <eriksen.costa@infranology.com.br> * @author Eriksen Costa <eriksen.costa@infranology.com.br>
* @author Bernhard Schussek <bschussek@gmail.com> * @author Bernhard Schussek <bschussek@gmail.com>
@ -57,6 +57,39 @@ class Locale
throw new MethodNotImplementedException(__METHOD__); throw new MethodNotImplementedException(__METHOD__);
} }
/**
* Returns a canonicalized locale string.
*
* This polyfill doesn't implement the full-spec algorithm. It only
* canonicalizes locale strings handled by the `LocaleBundle` class.
*
* @param string $locale
*
* @return string
*/
public static function canonicalize($locale)
{
$locale = (string) $locale;
if ('' === $locale || '.' === $locale[0]) {
return self::getDefault();
}
if (!preg_match('/^([a-z]{2})[-_]([a-z]{2})(?:([a-z]{2})(?:[-_]([a-z]{2}))?)?(?:\..*)?$/i', $locale, $m)) {
return $locale;
}
if (!empty($m[4])) {
return strtolower($m[1]).'_'.ucfirst(strtolower($m[2].$m[3])).'_'.strtoupper($m[4]);
}
if (!empty($m[3])) {
return strtolower($m[1]).'_'.ucfirst(strtolower($m[2].$m[3]));
}
return strtolower($m[1]).'_'.strtoupper($m[2]);
}
/** /**
* Not supported. Returns a correctly ordered and delimited locale code. * Not supported. Returns a correctly ordered and delimited locale code.
* *

View File

@ -21,6 +21,17 @@ class LocaleTest extends AbstractLocaleTest
$this->call('acceptFromHttp', 'pt-br,en-us;q=0.7,en;q=0.5'); $this->call('acceptFromHttp', 'pt-br,en-us;q=0.7,en;q=0.5');
} }
public function testCanonicalize()
{
$this->assertSame('en', $this->call('canonicalize', ''));
$this->assertSame('en', $this->call('canonicalize', '.utf8'));
$this->assertSame('fr_FR', $this->call('canonicalize', 'FR-fr'));
$this->assertSame('fr_FR', $this->call('canonicalize', 'FR-fr.utf8'));
$this->assertSame('uz_Latn', $this->call('canonicalize', 'UZ-lATN'));
$this->assertSame('uz_Cyrl_UZ', $this->call('canonicalize', 'UZ-cYRL-uz'));
$this->assertSame('123', $this->call('canonicalize', 123));
}
/** /**
* @expectedException \Symfony\Component\Intl\Exception\MethodNotImplementedException * @expectedException \Symfony\Component\Intl\Exception\MethodNotImplementedException
*/ */

View File

@ -12,7 +12,6 @@
namespace Symfony\Component\Validator\Constraints; namespace Symfony\Component\Validator\Constraints;
use Symfony\Component\Intl\Intl; use Symfony\Component\Intl\Intl;
use Symfony\Component\Intl\Locale as IntlLocale;
use Symfony\Component\Validator\Constraint; use Symfony\Component\Validator\Constraint;
use Symfony\Component\Validator\ConstraintValidator; use Symfony\Component\Validator\ConstraintValidator;
use Symfony\Component\Validator\Exception\UnexpectedTypeException; use Symfony\Component\Validator\Exception\UnexpectedTypeException;
@ -43,7 +42,7 @@ class LocaleValidator extends ConstraintValidator
$value = (string) $value; $value = (string) $value;
if ($constraint->canonicalize) { if ($constraint->canonicalize) {
$value = IntlLocale::canonicalize($value); $value = \Locale::canonicalize($value);
} }
$localeBundle = Intl::getLocaleBundle(); $localeBundle = Intl::getLocaleBundle();
$locales = $localeBundle->getLocaleNames(); $locales = $localeBundle->getLocaleNames();

View File

@ -24,7 +24,7 @@
"symfony/http-foundation": "~4.1", "symfony/http-foundation": "~4.1",
"symfony/http-kernel": "~3.4|~4.0", "symfony/http-kernel": "~3.4|~4.0",
"symfony/var-dumper": "~3.4|~4.0", "symfony/var-dumper": "~3.4|~4.0",
"symfony/intl": "~3.4|~4.0", "symfony/intl": "~4.1",
"symfony/yaml": "~3.4|~4.0", "symfony/yaml": "~3.4|~4.0",
"symfony/config": "~3.4|~4.0", "symfony/config": "~3.4|~4.0",
"symfony/dependency-injection": "~3.4|~4.0", "symfony/dependency-injection": "~3.4|~4.0",
@ -39,6 +39,7 @@
"phpunit/phpunit": "<4.8.35|<5.4.3,>=5.0", "phpunit/phpunit": "<4.8.35|<5.4.3,>=5.0",
"symfony/dependency-injection": "<3.4", "symfony/dependency-injection": "<3.4",
"symfony/http-kernel": "<3.4", "symfony/http-kernel": "<3.4",
"symfony/intl": "<4.1",
"symfony/yaml": "<3.4" "symfony/yaml": "<3.4"
}, },
"suggest": { "suggest": {