M — for model

Очень-очень редко, но бывает нужно использовать в каком-нибудь методе контроллера несколько несвязанных между собой моделей. Еще раз, ключевые слова: «редко-редко» и «несвязанных».

Можно такие модели перечислить в переменной класса $uses — тогда, они, правда, будут загружаться для любого метода контроллера.

В версии 1.1 фреймворка была функция loadModel(), которая теперь отменена.

Есть еще метод requestAction(), но он объявлен «плохим». И правда, это, по сути, еще один запрос к приложению по полной программе, с диспетчеризацией, роутингом, стартом и инициализацией всех сопутствующих классов. В общем, путь неоптимальный и пользоваться им можно лишь от полной безысходности.

Можно воспользоваться методом App::import() — это хороший метод для многих классов. Но загруженная модель будет неполной. Т.е. это будет просто загруженный класс модели, без всех предварительных инициализаций самой модели и т.п. Этим методом лучше пользоваться для подгрузки своих классов или библиотек сторонних разработчиков.

В общем, я лично чаще всего в Cake 1.2 использовал именно App::import(), мирясь с некоторыми ограничениями. Но, оказывается есть еще один метод, позволяющий полностью загрузить модель, со всем ее «обвесом»

teknoid в своем блоге описал пример создания dashboard, ну примерно как в wordpress 2.7 :-) . Мне полезность самой dashboard как-то сомнительна, но не в ней дело. А дело в том, что это тот редкий случай, когда в одном отдельно взятом методе нужно вызывать методы нескольких совершенно неотносящихся друг к другу моделей. teknoid приводит пример с вызовами методов для извлечения самых активных пользователей, самых посещаемых страниц, свежих новостей и т.д.

Для этого он использует ускользнувший от моего внимания :-) метод ClassRegistry::init(). Вот как выглядит написанный им метод контроллер Dashboard:

Этот метод позволяет загрузить только нужные модели, и только тогда, когда они нужны. Это, на мой взгляд, гораздо интереснее перечисления моделей в переменной $uses и принудительной их загрузки вне зависимости от необходимости их использования.

В общем, на мой взгляд, очень полезная вещь. Надо запомнить, может пригодится. Thanks to teknoid :-)

Автор

Сергей Родовниченко

Родился, учился, работал и все такое. Занимаюсь поддержкой сайтов на Shop-Script, Joomla, Wordpress, Prestashop. А также на самописных движках на базе CakePHP.

4 thoughts on “M — for model”

  1. Попробовал, несколько вариантов в свое время. Так и не понял, к сожалению, как правильно загрузить компонент динамически в контроллер. Например, у меня много компонентов, между ними есть связи в виде наследования и делегирования, пришлось также создать подкомпоненты и поместить их в подпапку папки components. Как Вы и говорили, хочется загружать не все, а именно тот — который нужен, а кокой нужен — определяется через некоторый адапторКомпонент.
    Странно, но мне ни App::import, ни ClassRegistry::init почему-то это не позволили сделать. require_once в середине кода — очень не хотелось, но оно единственное помогло. Да, подумывал вынести все в вендеры, но этот функционал ближе к контроллерам, чем к чему либо еше и используется только в них.

  2. Попробовал, несколько вариантов в свое время. Так и не понял, к сожалению, как правильно загрузить компонент динамически в контроллер. Например, у меня много компонентов, между ними есть связи в виде наследования и делегирования, пришлось также создать подкомпоненты и поместить их в подпапку папки components. Как Вы и говорили, хочется загружать не все, а именно тот — который нужен, а кокой нужен — определяется через некоторый адапторКомпонент.
    Странно, но мне ни App::import, ни ClassRegistry::init почему-то это не позволили сделать. require_once в середине кода — очень не хотелось, но оно единственное помогло. Да, подумывал вынести все в вендеры, но этот функционал ближе к контроллерам, чем к чему либо еше и используется только в них.

Добавить комментарий

Ваш e-mail не будет опубликован. Обязательные поля помечены *