Skip to content

Commit 87d3d0a

Browse files
Guilherme Blancoaitboudad
authored andcommitted
[Translator] Adding support for intl message formatter and decoupling default formatter.
1 parent bfa28d6 commit 87d3d0a

File tree

16 files changed

+383
-48
lines changed

16 files changed

+383
-48
lines changed

src/Symfony/Bridge/Twig/Tests/Extension/TranslationExtensionTest.php

Lines changed: 4 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -13,7 +13,6 @@
1313

1414
use Symfony\Bridge\Twig\Extension\TranslationExtension;
1515
use Symfony\Component\Translation\Translator;
16-
use Symfony\Component\Translation\MessageSelector;
1716
use Symfony\Component\Translation\Loader\ArrayLoader;
1817

1918
class TranslationExtensionTest extends \PHPUnit_Framework_TestCase
@@ -34,7 +33,7 @@ public function testTrans($template, $expected, array $variables = array())
3433
print $template."\n";
3534
$loader = new \Twig_Loader_Array(array('index' => $template));
3635
$twig = new \Twig_Environment($loader, array('debug' => true, 'cache' => false));
37-
$twig->addExtension(new TranslationExtension(new Translator('en', new MessageSelector())));
36+
$twig->addExtension(new TranslationExtension(new Translator('en')));
3837

3938
echo $twig->compile($twig->parse($twig->tokenize($twig->getLoader()->getSource('index'), 'index')))."\n\n";
4039
$this->assertEquals($expected, $this->getTemplate($template)->render($variables));
@@ -136,7 +135,7 @@ public function testDefaultTranslationDomain()
136135
',
137136
);
138137

139-
$translator = new Translator('en', new MessageSelector());
138+
$translator = new Translator('en');
140139
$translator->addLoader('array', new ArrayLoader());
141140
$translator->addResource('array', array('foo' => 'foo (messages)'), 'en');
142141
$translator->addResource('array', array('foo' => 'foo (custom)'), 'en', 'custom');
@@ -169,7 +168,7 @@ public function testDefaultTranslationDomainWithNamedArguments()
169168
',
170169
);
171170

172-
$translator = new Translator('en', new MessageSelector());
171+
$translator = new Translator('en');
173172
$translator->addLoader('array', new ArrayLoader());
174173
$translator->addResource('array', array('foo' => 'foo (messages)'), 'en');
175174
$translator->addResource('array', array('foo' => 'foo (custom)'), 'en', 'custom');
@@ -184,7 +183,7 @@ public function testDefaultTranslationDomainWithNamedArguments()
184183
protected function getTemplate($template, $translator = null)
185184
{
186185
if (null === $translator) {
187-
$translator = new Translator('en', new MessageSelector());
186+
$translator = new Translator('en');
188187
}
189188

190189
if (is_array($template)) {

src/Symfony/Bundle/FrameworkBundle/DependencyInjection/Configuration.php

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -583,6 +583,7 @@ private function addTranslatorSection(ArrayNodeDefinition $rootNode)
583583
->defaultValue(array('en'))
584584
->end()
585585
->booleanNode('logging')->defaultValue($this->debug)->end()
586+
->scalarNode('formatter')->defaultValue('translator.formatter.default')->end()
586587
->arrayNode('paths')
587588
->prototype('scalar')->end()
588589
->end()

src/Symfony/Bundle/FrameworkBundle/DependencyInjection/FrameworkExtension.php

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -660,6 +660,7 @@ private function registerTranslatorConfiguration(array $config, ContainerBuilder
660660

661661
// Use the "real" translator instead of the identity default
662662
$container->setAlias('translator', 'translator.default');
663+
$container->setAlias('translator.formatter', $config['formatter']);
663664
$translator = $container->findDefinition('translator.default');
664665
$translator->addMethodCall('setFallbackLocales', array($config['fallbacks']));
665666

src/Symfony/Bundle/FrameworkBundle/Resources/config/schema/symfony-1.0.xsd

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -188,6 +188,7 @@
188188
<xsd:attribute name="enabled" type="xsd:boolean" />
189189
<xsd:attribute name="fallback" type="xsd:string" />
190190
<xsd:attribute name="logging" type="xsd:boolean" />
191+
<xsd:attribute name="formatter" type="xsd:string" />
191192
</xsd:complexType>
192193

193194
<xsd:complexType name="validation">

src/Symfony/Bundle/FrameworkBundle/Resources/config/translation.xml

Lines changed: 8 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -38,7 +38,7 @@
3838
<services>
3939
<service id="translator.default" class="%translator.class%">
4040
<argument type="service" id="service_container" />
41-
<argument type="service" id="translator.selector" />
41+
<argument type="service" id="translator.formatter" />
4242
<argument type="collection" /> <!-- translation loaders -->
4343
<argument type="collection">
4444
<argument key="cache_dir">%kernel.cache_dir%/translations</argument>
@@ -54,6 +54,13 @@
5454
</service>
5555

5656
<service id="translator" class="%translator.identity.class%">
57+
<argument type="service" id="translator.formatter" />
58+
</service>
59+
60+
<service id="translator.formatter" alias="translator.formatter.default" />
61+
<service id="translator.formatter.intl" class="Symfony\Component\Translation\Formatter\IntlMessageFormatter" public="false" />
62+
63+
<service id="translator.formatter.default" class="Symfony\Component\Translation\Formatter\DefaultMessageFormatter" public="false">
5764
<argument type="service" id="translator.selector" />
5865
</service>
5966

src/Symfony/Bundle/FrameworkBundle/Tests/DependencyInjection/ConfigurationTest.php

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -142,6 +142,7 @@ protected static function getBundleDefaultConfig()
142142
),
143143
'translator' => array(
144144
'enabled' => false,
145+
'formatter' => 'translator.formatter.default',
145146
'fallbacks' => array('en'),
146147
'logging' => true,
147148
'paths' => array(),

src/Symfony/Bundle/FrameworkBundle/Tests/Translation/TranslatorTest.php

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -14,7 +14,7 @@
1414
use Symfony\Bundle\FrameworkBundle\Translation\Translator;
1515
use Symfony\Component\Translation\MessageCatalogue;
1616
use Symfony\Component\Filesystem\Filesystem;
17-
use Symfony\Component\Translation\MessageSelector;
17+
use Symfony\Component\Translation\Formatter\DefaultMessageFormatter;
1818

1919
class TranslatorTest extends \PHPUnit_Framework_TestCase
2020
{
@@ -157,7 +157,7 @@ public function testGetDefaultLocale()
157157
->will($this->returnValue('en'))
158158
;
159159

160-
$translator = new Translator($container, new MessageSelector());
160+
$translator = new Translator($container, new DefaultMessageFormatter());
161161

162162
$this->assertSame('en', $translator->getLocale());
163163
}
@@ -290,7 +290,7 @@ private function createTranslator($loader, $options, $translatorClass = '\Symfon
290290
{
291291
return new $translatorClass(
292292
$this->getContainer($loader),
293-
new MessageSelector(),
293+
new DefaultMessageFormatter(),
294294
array($loaderFomat => array($loaderFomat)),
295295
$options
296296
);

src/Symfony/Bundle/FrameworkBundle/Translation/Translator.php

Lines changed: 6 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -46,14 +46,14 @@ class Translator extends BaseTranslator implements WarmableInterface
4646
* * debug: Whether to enable debugging or not (false by default)
4747
* * resource_files: List of translation resources available grouped by locale.
4848
*
49-
* @param ContainerInterface $container A ContainerInterface instance
50-
* @param MessageSelector $selector The message selector for pluralization
51-
* @param array $loaderIds An array of loader Ids
52-
* @param array $options An array of options
49+
* @param ContainerInterface $container A ContainerInterface instance
50+
* @param MessageFormatterInterface|MessageSelector $formatter The message formatter
51+
* @param array $loaderIds An array of loader Ids
52+
* @param array $options An array of options
5353
*
5454
* @throws \InvalidArgumentException
5555
*/
56-
public function __construct(ContainerInterface $container, MessageSelector $selector, $loaderIds = array(), array $options = array())
56+
public function __construct(ContainerInterface $container, $formatter, $loaderIds = array(), array $options = array())
5757
{
5858
$this->container = $container;
5959
$this->loaderIds = $loaderIds;
@@ -69,7 +69,7 @@ public function __construct(ContainerInterface $container, MessageSelector $sele
6969
$this->loadResources();
7070
}
7171

72-
parent::__construct($container->getParameter('kernel.default_locale'), $selector, $this->options['cache_dir'], $this->options['debug']);
72+
parent::__construct($container->getParameter('kernel.default_locale'), $formatter, $this->options['cache_dir'], $this->options['debug']);
7373
}
7474

7575
/**
Lines changed: 45 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,45 @@
1+
<?php
2+
3+
/*
4+
* This file is part of the Symfony package.
5+
*
6+
* (c) Fabien Potencier <fabien@symfony.com>
7+
*
8+
* For the full copyright and license information, please view the LICENSE
9+
* file that was distributed with this source code.
10+
*/
11+
12+
namespace Symfony\Component\Translation\Formatter;
13+
14+
use Symfony\Component\Translation\MessageSelector;
15+
16+
/**
17+
* @author Guilherme Blanco <guilhermeblanco@hotmail.com>
18+
*/
19+
class DefaultMessageFormatter implements MessageFormatterInterface
20+
{
21+
/**
22+
* @var MessageSelector
23+
*/
24+
protected $selector;
25+
26+
/**
27+
* @param MessageSelector $selector Message selector to choose pluralization messages.
28+
*/
29+
public function __construct(MessageSelector $selector = null)
30+
{
31+
$this->selector = $selector ?: new MessageSelector();
32+
}
33+
34+
/**
35+
* {@inheritdoc}
36+
*/
37+
public function format($locale, $id, $number = null, array $arguments = array())
38+
{
39+
$pattern = ($number !== null)
40+
? $this->selector->choose($id, (int) $number, $locale)
41+
: $id;
42+
43+
return strtr($pattern, $arguments);
44+
}
45+
}
Lines changed: 54 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,54 @@
1+
<?php
2+
3+
/*
4+
* This file is part of the Symfony package.
5+
*
6+
* (c) Fabien Potencier <fabien@symfony.com>
7+
*
8+
* For the full copyright and license information, please view the LICENSE
9+
* file that was distributed with this source code.
10+
*/
11+
12+
namespace Symfony\Component\Translation\Formatter;
13+
14+
/**
15+
* @author Guilherme Blanco <guilhermeblanco@hotmail.com>
16+
*/
17+
class IntlMessageFormatter implements MessageFormatterInterface
18+
{
19+
/**
20+
* {@inheritdoc}
21+
*/
22+
public function format($locale, $id, $number = null, array $arguments = array())
23+
{
24+
if ($number !== null) {
25+
array_unshift($arguments, $number);
26+
}
27+
28+
$formatter = new \MessageFormatter($locale, $id);
29+
30+
if (null === $formatter) {
31+
throw new \InvalidArgumentException(
32+
sprintf(
33+
'Invalid message format. Reason: %s (error #%d)',
34+
intl_get_error_message(),
35+
intl_get_error_code()
36+
)
37+
);
38+
}
39+
40+
$message = $formatter->format($arguments);
41+
42+
if ($formatter->getErrorCode() !== U_ZERO_ERROR) {
43+
throw new \InvalidArgumentException(
44+
sprintf(
45+
'Unable to format message. Reason: %s (error #%s)',
46+
$formatter->getErrorMessage(),
47+
$formatter->getErrorCode()
48+
)
49+
);
50+
}
51+
52+
return $message;
53+
}
54+
}

0 commit comments

Comments
 (0)