我認爲你做這件事的方式非常好。
您可以添加/重寫一些獲取i18n數據的方法,例如getTitle($ locale)(或者get * Whatever *),它會添加一些邏輯,在topic_i18n集合中找到合適的值。
// in your Topic class
public function getTitle()
{
return $this
->getTopicI18nCollection()
->findByLocale($this->getLocale()) // actually findByLocale does not exist, you will have to find another way, like iterating over all collection
->getTitle()
;
}
與__toString或他人的自動化問題是與現場切換,或如何定義默認語言環境默認使用。
這可以使用doctrine postLoad事件偵聽器解決,該偵聽器將當前語言環境設置爲由EntityManager(http://www.doctrine-project.org/docs/orm/2.1/en/reference/events.html#lifecycle-events)獲取的任何實體,例如使用請求或會話信息。
使用Symfony2中,它可能是這樣的:
# app/config/config.yml
services:
postload.listener:
class: Translatable\LocaleInitializer
arguments: [@session]
tags:
- { name: doctrine.event_listener, event: postLoad }
// src/Translatable/LocaleInitalizer.php
class LocaleInitializer
{
public function __construct(Session $session)
{
$this->session = $session;
}
public function postLoad(LifecycleEventArgs $args)
{
$entity = $args->getEntity();
if ($entity implements TranslatableInterface) { // or whatever check
$entity->setLocale($this->session->getLocale());
}
}
}
最後,你不有得到一個主題對象來創建一個新的topic_i18n對象,你可以簡單地插入的i18n對象independantly 。 (但你將不得不刷新以前提取的集合)。
非常感謝,您的解釋就是我一直在尋找的!你能解釋爲什麼findByLocale()不會存在嗎?是由於語言環境是一個私有變量而不是@ORM \列?另一個問題是,爲了能夠同時管理兩個實體,我應該創建一個服務層/管理器,或者只需將所需的字段/變量添加到Topic實體,並將偵聽器註冊爲prepersist事件,然後從實體中獲取變量,實例化一個Entity_i18n對象並將它們設置爲它?我的意思是我希望能夠運行$ t = new Topic(); $ t-> setLocale('es'); $ t-> setContent(foo);並堅持下去 – user846226 2012-02-03 08:10:35