Doctrine 1.2 автоматически присоединяется к i18n? - PullRequest
7 голосов
/ 25 марта 2011


Я хотел бы расширить поведение i18n, чтобы оно автоматически включалось в таблицу перевода при любом запросе (DQL, Relations, getTable).
Кроме того, он должен определить параметр языка по умолчанию, поэтому, когда я выполняю запрос без установленного языка, он возвращается к языку по умолчанию.
Примечание. Я ищу обобщенное поведение, которое применимо ко всем объектам модели i18n, а не к записи и переопределению для каждого из классов.

Вот пример:
таблица product -> id, category_id, цена ...
таблица product_translation -> id, lang, имя, описание ...

С текущим решением, когда я делаю что-то вроде этого: Doctrine_Core::getTable('Product')->findAll(), он получает все продукты, не присоединяясь к переводам.
Таким образом, в контроллере я должен пройти через все записи и повторно применить переведенные значения, с $product->name = $product->Translation['en']->name

Я бы хотел что-то вроде этого:

  • Doctrine_Core::getTable('Product')->findAll() он должен получить объединенные значения для lang = 'en'
  • Doctrine_Core::getTable('Product)->findAll('en') то же, что и выше
  • Он также должен работать с отношениями, поэтому, например, если у меня есть класс User, у которого много продуктов $user->Products, он должен возвращать коллекцию с включенными переводами.
  • Также что-то вроде $user->Products('en') должно возвращать коллекцию для других (не по умолчанию) языков
  • Магические функции тоже подойдут (если возможно) ... что-то вроде Doctrine_Core::getTable('Product')->getByCategoryAndLang(1,'en')

Может кто-нибудь помочь? Я смотрю на шаблоны и поведение, я думаю, что это путь, но понятия не имею, как реализовать это

РЕДАКТИРОВАТЬ: Я вижу, что это не очень интересно, поэтому позвольте мне попробовать с более простым вопросом. Как вы обычно получаете i18n поля через отношения. Например, как я могу позвонить $user->Products и получить продукты с загруженными переводами?

1 Ответ

1 голос
/ 04 мая 2011

Я думаю, что вам не нужно расширять стандартное поведение Doctrine, если вы не хотите, чтобы это было полностью автоматически. Но все же Вы можете попытаться сделать это так, как мы делаем - мы используем DAO (объект доступа к данным), который возвращает нам конкретную сущность Doctrine (представление таблицы Doctrine):

\DAO::get('Some\Namespace\Classname')

где Classname обозначает таблицу, описанную моделью класса PHP. Наш класс DAO создает экземпляр Classname, который инкапсулируется в proxy (см. Шаблоны проектирования).

Помимо модели класса таблицы, мы создаем еще один класс для этой таблицы, который стоит над моделью таблицы и манипулирует этой моделью. Внутри этого класса мы пишем методы типа getProducts($args), getProduct($id), getProductsByCategory($catId) и т. Д.

Я думаю, что это то, что Вы ищете ...

В методе getProducts($args) Затем вы можете реализовать ->leftJoin() в DQL, который присоединится к таблице переводов с помощью заданного $lang идентификатора в параметре $args. Простой пример (не тестировался):

class Products extends \DAO {
    public function save($item) {
        $item->save();
    }

    public function getProducts($args = array()) {
        $order = array('p.id');

        $result = \Doctrine_Query::create()
            ->from('Some\Namespace\Product p')
            ->where('1 = 1');

        if(!empty($args['lang'])) {
            $result = $result->leftJoin('Some\Namespace\ProductTranslation pt ON pt.product_id = p.id AND pt.language = ?', $args['lang']);
        }

        $result = $result->orderBy($order);

        $result = $result->execute();

        return $result;
    }
}

Затем по телефону

$products = DAO::get('Some\Namespace\Product')->getProducts(array('lang' => 1));

Вы получаете все продукты с загруженными английскими переводами ...

Он не настолько автоматизирован, и вам нужно написать собственный класс DAO для каждой модели, но это хороший подход, поскольку у вас есть другой класс определения данных (модель) и класс манипулирования данными (контроллер), которые необходимы для объекта MVC / MVP ориентированная архитектура приложения ...

...