我遇到了以下问题:我想获取特定区域设置的doctrine实体,而不会破坏我的Symfony应用程序的默认行为。
以下是我的一个实体的示例:
use Doctrine\ORM\Mapping as ORM;
use Gedmo\Mapping\Annotation as Gedmo;
/**
* @ORM\Entity(repositoryClass="ProductRepository")
* @ORM\Table(name="product")
* @ORM\InheritanceType("SINGLE_TABLE")
* @ORM\DiscriminatorColumn(name="discr", type="string")
*/
class Product
{
/**
* @var integer $id
* @ORM\Column(name="id", type="integer")
* @ORM\Id
* @ORM\GeneratedValue(strategy="AUTO")
*/
protected $id;
/**
* @var string
* @ORM\Column(name="name", type="string")
* @Gedmo\Translatable
*/
protected $name;
// ...
}
相关学说知识库的一部分:
class ProductRepository extends \Doctrine\ORM\EntityRepository
{
public function findOneProductInLocale($id, $locale)
{
$qb = $this->createQueryBuilder('p')
->select('p')
->where('p.id = :id')
->setMaxResults(1)
->setParameter('id', $id);
;
$query = $qb->getQuery();
$query->setHint(
\Doctrine\ORM\Query::HINT_CUSTOM_OUTPUT_WALKER,
'Gedmo\\Translatable\\Query\\TreeWalker\\TranslationWalker'
);
// force Gedmo Translatable to not use current locale
$query->setHint(
\Gedmo\Translatable\TranslatableListener::HINT_TRANSLATABLE_LOCALE,
$locale
);
$query->setHint(
\Gedmo\Translatable\TranslatableListener::HINT_FALLBACK,
1
);
return $query->getOneOrNullResult();
}
}
和我的部分脚本:
// default Locale: en
// request Locale: de
$repo = $em->getRepository('Acme\\Entity\\Product');
$product1 = $repo->findOneById($id);
echo $product1->getName(); // return 'Name (DE)'
$product_de = $repo->findOneProductInLocale($id, 'de');
echo $product_de->getName(); // return 'Name (DE)';
$product_en = $repo->findOneProductInLocale($id, 'en');
echo $product_en->getName(); // return 'Name (EN)'
echo $product1->getName(); // return 'Name (EN)' instead of 'Name (DE)' !! <-- What is wrong?
// even if I refetch a product
$product2 = $repo->findOneById($id);
echo $product2->getName(); // return 'Name (EN)' without taking anymore in account the current locale
有人为什么这不能按预期工作?
在我ProductRepository::findOneProductInLocale()
的实施中出了什么问题?
欢迎任何帮助或提示。
答案 0 :(得分:0)
刷新实体应该恢复当前的语言环境:
$em->refresh($product1);
答案 1 :(得分:0)
问题是,您的$product1
,$product_de
,$product_en
和$product2
都是一样的。如果您var_dump
他们,则他们具有相同的object #id
。他们引用相同的Product Entity
。如果您在一个中更改任何内容,则会在所有内容中进行更改。要让它们与众不同,您必须clone
。
$product_de = clone $repo->findOneProductInLocale($id, 'de');
$product_en = clone $repo->findOneProductInLocale($id, 'en');
答案 2 :(得分:0)
我知道我的回答有点晚了,但是我遇到了同样的问题并找到了解决方案。我希望它将对其他一些开发人员有所帮助。
您的findOneProductInLocale
(如果可以)。
它像设计一样-当您使用findOneProductInLocale
时,查询将在给定的语言环境中进行搜索,但最终实体将始终在当前语言环境中加载,则无法更改。
通过findOneProductInLocale
找到实体,并加载到当前语言环境后,您可以使用{ {1}} Gedmo的方法并刷新实体,如@umadesign
setTranslatableLocale
(可选)您可能需要将// Reload the entity in different languages.
$entity->setTranslatableLocale($locale);
$em->refresh($entity);
方法和伴随属性setTranslatableLocale
添加到可翻译实体
$local
您可以在Gedmo documentation under "Basic usage examples" subsection中找到完整的说明。