merged 2.0 branch
This commit is contained in:
commit
3a4d1a6a22
@ -69,6 +69,7 @@ class TestSessionListener
|
||||
|
||||
if ($session = $event->getRequest()->getSession()) {
|
||||
$session->save();
|
||||
$session->close();
|
||||
|
||||
$params = session_get_cookie_params();
|
||||
|
||||
|
@ -32,7 +32,7 @@
|
||||
</trans-unit>
|
||||
<trans-unit id="8">
|
||||
<source>One or more of the given values is invalid</source>
|
||||
<target>One or more of the given values is invalid</target>
|
||||
<target>Ett eller fler av de valda värdena är ogiltigt</target>
|
||||
</trans-unit>
|
||||
<trans-unit id="9">
|
||||
<source>The fields {{ fields }} were not expected</source>
|
||||
|
@ -157,18 +157,19 @@ class DateType extends AbstractType
|
||||
public function getDefaultOptions(array $options)
|
||||
{
|
||||
return array(
|
||||
'years' => range(date('Y') - 5, date('Y') + 5),
|
||||
'months' => range(1, 12),
|
||||
'days' => range(1, 31),
|
||||
'widget' => 'choice',
|
||||
'input' => 'datetime',
|
||||
'format' => \IntlDateFormatter::MEDIUM,
|
||||
'data_timezone' => null,
|
||||
'user_timezone' => null,
|
||||
'empty_value' => null,
|
||||
'years' => range(date('Y') - 5, date('Y') + 5),
|
||||
'months' => range(1, 12),
|
||||
'days' => range(1, 31),
|
||||
'widget' => 'choice',
|
||||
'input' => 'datetime',
|
||||
'format' => \IntlDateFormatter::MEDIUM,
|
||||
'data_timezone' => null,
|
||||
'user_timezone' => null,
|
||||
'empty_value' => null,
|
||||
// Don't modify \DateTime classes by reference, we treat
|
||||
// them like immutable value objects
|
||||
'by_reference' => false,
|
||||
'by_reference' => false,
|
||||
'error_bubbling' => false,
|
||||
);
|
||||
}
|
||||
|
||||
|
@ -123,18 +123,19 @@ class TimeType extends AbstractType
|
||||
public function getDefaultOptions(array $options)
|
||||
{
|
||||
return array(
|
||||
'hours' => range(0, 23),
|
||||
'minutes' => range(0, 59),
|
||||
'seconds' => range(0, 59),
|
||||
'widget' => 'choice',
|
||||
'input' => 'datetime',
|
||||
'with_seconds' => false,
|
||||
'data_timezone' => null,
|
||||
'user_timezone' => null,
|
||||
'empty_value' => null,
|
||||
'hours' => range(0, 23),
|
||||
'minutes' => range(0, 59),
|
||||
'seconds' => range(0, 59),
|
||||
'widget' => 'choice',
|
||||
'input' => 'datetime',
|
||||
'with_seconds' => false,
|
||||
'data_timezone' => null,
|
||||
'user_timezone' => null,
|
||||
'empty_value' => null,
|
||||
// Don't modify \DateTime classes by reference, we treat
|
||||
// them like immutable value objects
|
||||
'by_reference' => false,
|
||||
'by_reference' => false,
|
||||
'error_bubbling' => false,
|
||||
);
|
||||
}
|
||||
|
||||
|
@ -11,8 +11,6 @@
|
||||
|
||||
namespace Symfony\Component\HttpFoundation;
|
||||
|
||||
use Symfony\Component\HttpFoundation\SessionStorage\NativeSessionStorage;
|
||||
|
||||
/**
|
||||
* Request represents an HTTP request.
|
||||
*
|
||||
@ -298,15 +296,15 @@ class Request
|
||||
$dup->server = new ServerBag($server);
|
||||
$dup->headers = new HeaderBag($dup->server->getHeaders());
|
||||
}
|
||||
$this->languages = null;
|
||||
$this->charsets = null;
|
||||
$this->acceptableContentTypes = null;
|
||||
$this->pathInfo = null;
|
||||
$this->requestUri = null;
|
||||
$this->baseUrl = null;
|
||||
$this->basePath = null;
|
||||
$this->method = null;
|
||||
$this->format = null;
|
||||
$dup->languages = null;
|
||||
$dup->charsets = null;
|
||||
$dup->acceptableContentTypes = null;
|
||||
$dup->pathInfo = null;
|
||||
$dup->requestUri = null;
|
||||
$dup->baseUrl = null;
|
||||
$dup->basePath = null;
|
||||
$dup->method = null;
|
||||
$dup->format = null;
|
||||
|
||||
return $dup;
|
||||
}
|
||||
|
@ -29,7 +29,7 @@ class Session implements \Serializable
|
||||
protected $oldFlashes;
|
||||
protected $locale;
|
||||
protected $defaultLocale;
|
||||
protected $saved;
|
||||
protected $closed;
|
||||
|
||||
/**
|
||||
* Constructor.
|
||||
@ -47,7 +47,7 @@ class Session implements \Serializable
|
||||
$this->attributes = array();
|
||||
$this->setPhpDefaultLocale($this->defaultLocale);
|
||||
$this->started = false;
|
||||
$this->saved = false;
|
||||
$this->closed = false;
|
||||
}
|
||||
|
||||
/**
|
||||
@ -194,7 +194,7 @@ class Session implements \Serializable
|
||||
public function invalidate()
|
||||
{
|
||||
$this->clear();
|
||||
$this->storage->regenerate();
|
||||
$this->storage->regenerate(true);
|
||||
}
|
||||
|
||||
/**
|
||||
@ -358,12 +358,22 @@ class Session implements \Serializable
|
||||
'flashes' => $this->flashes,
|
||||
'locale' => $this->locale,
|
||||
));
|
||||
$this->saved = true;
|
||||
}
|
||||
|
||||
/**
|
||||
* This method should be called when you don't want the session to be saved
|
||||
* when the Session object is garbaged collected (useful for instance when
|
||||
* you want to simulate the interaction of several users/sessions in a single
|
||||
* PHP process).
|
||||
*/
|
||||
public function close()
|
||||
{
|
||||
$this->closed = true;
|
||||
}
|
||||
|
||||
public function __destruct()
|
||||
{
|
||||
if (true === $this->started && !$this->saved) {
|
||||
if (true === $this->started && !$this->closed) {
|
||||
$this->save();
|
||||
}
|
||||
}
|
||||
|
@ -25,6 +25,7 @@ class MessageCatalogue implements MessageCatalogueInterface
|
||||
private $messages = array();
|
||||
private $locale;
|
||||
private $resources;
|
||||
private $fallbackCatalogue;
|
||||
|
||||
/**
|
||||
* Constructor.
|
||||
@ -91,6 +92,22 @@ class MessageCatalogue implements MessageCatalogueInterface
|
||||
* @api
|
||||
*/
|
||||
public function has($id, $domain = 'messages')
|
||||
{
|
||||
if (isset($this->messages[$domain][$id])) {
|
||||
return true;
|
||||
}
|
||||
|
||||
if (null !== $this->fallbackCatalogue) {
|
||||
return $this->fallbackCatalogue->has($id, $domain);
|
||||
}
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
/**
|
||||
* {@inheritdoc}
|
||||
*/
|
||||
public function defines($id, $domain = 'messages')
|
||||
{
|
||||
return isset($this->messages[$domain][$id]);
|
||||
}
|
||||
@ -102,7 +119,15 @@ class MessageCatalogue implements MessageCatalogueInterface
|
||||
*/
|
||||
public function get($id, $domain = 'messages')
|
||||
{
|
||||
return isset($this->messages[$domain][$id]) ? $this->messages[$domain][$id] : $id;
|
||||
if (isset($this->messages[$domain][$id])) {
|
||||
return $this->messages[$domain][$id];
|
||||
}
|
||||
|
||||
if (null !== $this->fallbackCatalogue) {
|
||||
return $this->fallbackCatalogue->get($id, $domain);
|
||||
}
|
||||
|
||||
return $id;
|
||||
}
|
||||
|
||||
/**
|
||||
@ -158,13 +183,7 @@ class MessageCatalogue implements MessageCatalogueInterface
|
||||
*/
|
||||
public function addFallbackCatalogue(MessageCatalogueInterface $catalogue)
|
||||
{
|
||||
foreach ($catalogue->getDomains() as $domain) {
|
||||
foreach ($catalogue->all($domain) as $id => $translation) {
|
||||
if (false === $this->has($id, $domain)) {
|
||||
$this->set($id, $translation, $domain);
|
||||
}
|
||||
}
|
||||
}
|
||||
$this->fallbackCatalogue = $catalogue;
|
||||
|
||||
foreach ($catalogue->getResources() as $resource) {
|
||||
$this->addResource($resource);
|
||||
|
@ -76,6 +76,18 @@ interface MessageCatalogueInterface
|
||||
*/
|
||||
function has($id, $domain = 'messages');
|
||||
|
||||
/**
|
||||
* Checks if a message has a translation (it does not take into account the fallback mechanism).
|
||||
*
|
||||
* @param string $id The message id
|
||||
* @param string $domain The domain name
|
||||
*
|
||||
* @return Boolean true if the message has a translation, false otherwise
|
||||
*
|
||||
* @api
|
||||
*/
|
||||
function defines($id, $domain = 'messages');
|
||||
|
||||
/**
|
||||
* Gets a message translation.
|
||||
*
|
||||
|
@ -54,9 +54,9 @@ class MessageSelector
|
||||
foreach ($parts as $part) {
|
||||
$part = trim($part);
|
||||
|
||||
if (preg_match('/^(?P<interval>'.Interval::getIntervalRegexp().')\s+(?P<message>.+?)$/x', $part, $matches)) {
|
||||
if (preg_match('/^(?P<interval>'.Interval::getIntervalRegexp().')\s*(?P<message>.*?)$/x', $part, $matches)) {
|
||||
$explicitRules[$matches['interval']] = $matches['message'];
|
||||
} elseif (preg_match('/^\w+\: +(.+)$/', $part, $matches)) {
|
||||
} elseif (preg_match('/^\w+\:\s*(.*?)$/', $part, $matches)) {
|
||||
$standardRules[] = $matches[1];
|
||||
} else {
|
||||
$standardRules[] = $part;
|
||||
|
@ -142,6 +142,11 @@ class Translator implements TranslatorInterface
|
||||
$this->loadCatalogue($locale);
|
||||
}
|
||||
|
||||
if (!$this->catalogues[$locale]->defines((string) $id, $domain)) {
|
||||
// we will use the fallback
|
||||
$locale = $this->computeFallbackLocale($locale);
|
||||
}
|
||||
|
||||
return strtr($this->selector->choose($this->catalogues[$locale]->get((string) $id, $domain), (int) $number, $locale), $parameters);
|
||||
}
|
||||
|
||||
@ -163,13 +168,7 @@ class Translator implements TranslatorInterface
|
||||
|
||||
private function optimizeCatalogue($locale)
|
||||
{
|
||||
if (strlen($locale) > 3) {
|
||||
$fallback = substr($locale, 0, -strlen(strrchr($locale, '_')));
|
||||
} else {
|
||||
$fallback = $this->fallbackLocale;
|
||||
}
|
||||
|
||||
if (!$fallback) {
|
||||
if (!$fallback = $this->computeFallbackLocale($locale)) {
|
||||
return;
|
||||
}
|
||||
|
||||
@ -179,4 +178,13 @@ class Translator implements TranslatorInterface
|
||||
|
||||
$this->catalogues[$locale]->addFallbackCatalogue($this->catalogues[$fallback]);
|
||||
}
|
||||
|
||||
private function computeFallbackLocale($locale)
|
||||
{
|
||||
if (strlen($locale) > 3) {
|
||||
return substr($locale, 0, -strlen(strrchr($locale, '_')));
|
||||
} else {
|
||||
return $this->fallbackLocale;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -1120,6 +1120,17 @@ abstract class AbstractLayoutTest extends \PHPUnit_Framework_TestCase
|
||||
);
|
||||
}
|
||||
|
||||
public function testDateErrorBubbling()
|
||||
{
|
||||
$child = $this->factory->createNamed('date', 'date');
|
||||
$form = $this->factory->createNamed('form', 'form')->add($child);
|
||||
$child->addError(new FormError('Error!'));
|
||||
$view = $form->createView();
|
||||
|
||||
$this->assertEmpty($this->renderErrors($view));
|
||||
$this->assertNotEmpty($this->renderErrors($view['date']));
|
||||
}
|
||||
|
||||
public function testBirthDay()
|
||||
{
|
||||
$form = $this->factory->createNamed('birthday', 'na&me', '2000-02-03', array(
|
||||
@ -1646,6 +1657,17 @@ abstract class AbstractLayoutTest extends \PHPUnit_Framework_TestCase
|
||||
);
|
||||
}
|
||||
|
||||
public function testTimeErrorBubbling()
|
||||
{
|
||||
$child = $this->factory->createNamed('time', 'time');
|
||||
$form = $this->factory->createNamed('form', 'form')->add($child);
|
||||
$child->addError(new FormError('Error!'));
|
||||
$view = $form->createView();
|
||||
|
||||
$this->assertEmpty($this->renderErrors($view));
|
||||
$this->assertNotEmpty($this->renderErrors($view['time']));
|
||||
}
|
||||
|
||||
public function testTimezone()
|
||||
{
|
||||
$form = $this->factory->createNamed('timezone', 'na&me', 'Europe/Vienna', array(
|
||||
|
@ -200,6 +200,38 @@ class SessionTest extends \PHPUnit_Framework_TestCase
|
||||
$this->assertSame(array(), $this->session->getFlashes());
|
||||
$this->assertSame(array(), $this->session->all());
|
||||
}
|
||||
|
||||
public function testSavedOnDestruct()
|
||||
{
|
||||
$this->session->set('foo', 'bar');
|
||||
|
||||
$this->session->__destruct();
|
||||
|
||||
$expected = array(
|
||||
'attributes'=>array('foo'=>'bar'),
|
||||
'flashes'=>array(),
|
||||
'locale'=>'en'
|
||||
);
|
||||
$saved = $this->storage->read('_symfony2');
|
||||
$this->assertSame($expected, $saved);
|
||||
}
|
||||
|
||||
public function testSavedOnDestructAfterManualSave()
|
||||
{
|
||||
$this->session->set('foo', 'nothing');
|
||||
$this->session->save();
|
||||
$this->session->set('foo', 'bar');
|
||||
|
||||
$this->session->__destruct();
|
||||
|
||||
$expected = array(
|
||||
'attributes'=>array('foo'=>'bar'),
|
||||
'flashes'=>array(),
|
||||
'locale'=>'en'
|
||||
);
|
||||
$saved = $this->storage->read('_symfony2');
|
||||
$this->assertSame($expected, $saved);
|
||||
}
|
||||
|
||||
public function testStorageRegenerate()
|
||||
{
|
||||
|
@ -39,8 +39,14 @@ class MessageSelectorTest extends \PHPUnit_Framework_TestCase
|
||||
{
|
||||
return array(
|
||||
array('There is no apples', '{0} There is no apples|{1} There is one apple|]1,Inf] There is %count% apples', 0),
|
||||
array('There is no apples', '{0} There is no apples|{1} There is one apple|]1,Inf] There is %count% apples', 0),
|
||||
array('There is no apples', '{0}There is no apples|{1} There is one apple|]1,Inf] There is %count% apples', 0),
|
||||
|
||||
array('There is one apple', '{0} There is no apples|{1} There is one apple|]1,Inf] There is %count% apples', 1),
|
||||
|
||||
array('There is %count% apples', '{0} There is no apples|{1} There is one apple|]1,Inf] There is %count% apples', 10),
|
||||
array('There is %count% apples', '{0} There is no apples|{1} There is one apple|]1,Inf]There is %count% apples', 10),
|
||||
array('There is %count% apples', '{0} There is no apples|{1} There is one apple|]1,Inf] There is %count% apples', 10),
|
||||
|
||||
array('There is %count% apples', 'There is one apple|There is %count% apples', 0),
|
||||
array('There is one apple', 'There is one apple|There is %count% apples', 1),
|
||||
@ -53,6 +59,9 @@ class MessageSelectorTest extends \PHPUnit_Framework_TestCase
|
||||
array('There is no apples', '{0} There is no apples|one: There is one apple|more: There is %count% apples', 0),
|
||||
array('There is one apple', '{0} There is no apples|one: There is one apple|more: There is %count% apples', 1),
|
||||
array('There is %count% apples', '{0} There is no apples|one: There is one apple|more: There is %count% apples', 10),
|
||||
|
||||
array('', '{0}|{1} There is one apple|]1,Inf] There is %count% apples', 0),
|
||||
array('', '{0} There is no apples|{1}|]1,Inf] There is %count% apples', 1),
|
||||
);
|
||||
}
|
||||
}
|
||||
|
@ -163,6 +163,16 @@ class TranslatorTest extends \PHPUnit_Framework_TestCase
|
||||
array('Il y a 0 pomme', new String('{0} There is no apples|{1} There is one apple|]1,Inf] There is %count% apples'), '[0,1] Il y a %count% pomme|]1,Inf] Il y a %count% pommes', 0, array('%count%' => 0), 'fr', ''),
|
||||
);
|
||||
}
|
||||
|
||||
public function testTransChoiceFallback()
|
||||
{
|
||||
$translator = new Translator('ru', new MessageSelector());
|
||||
$translator->setFallbackLocale('en');
|
||||
$translator->addLoader('array', new ArrayLoader());
|
||||
$translator->addResource('array', array('some_message2' => 'one thing|%count% things'), 'en');
|
||||
|
||||
$this->assertEquals('10 things', $translator->transChoice('some_message2', 10, array('%count%' => 10)));
|
||||
}
|
||||
}
|
||||
|
||||
class String
|
||||
|
Reference in New Issue
Block a user