parser

Написать ответ на текущее сообщение

 

 
   команды управления поиском

PF: Шаблоны. Templet

Sumo 25.08.2007 10:26 / 26.08.2007 11:55

Как правило архитектура MVC (Model-View-Controller, Модель-Представление-Контролер) в веб разработке используется следующим образом: контролер получает запрос от веб сервера, ищет подходящий обработчик и передает ему управление. Обработчик получает данные от модели и с помошью "представления" формирует ответ, который возвращает контролеру. Контроллер возвращает ответ серверу. Такая схема несколько отличается от классической определения, но сути не меняет.

В контексте библиотеки PF контролером являются модули (pfModule/pfSiteModule/pfSiteManager и т.д.), для обеспечения функциональности представления используется шаблонный движок Templet (читается как Темплет :), а реализация модели пока остается за программистом (PF предоставляет только вспомогательные классы для работы с sql и пр.).

Опыт показывает, что оптимально использовать следующую логику при программировании обработчиков в контролере: из модели достаем данные, соответствующие запросу (переменные), которые передаются шаблонному движку, а он, в свою очередь, занимается формированием html'я, xml'я или чего-либо еще. Далее контролер может делать с результатами работы шаблонизатора что угодно, например, выполнить дополнительное xslt-преобразование или просто передать его серверу. Здесь важно, что программист (при использовании Templet'а) продолжает работать на основном языке и не тратит силы на отладку "сторонних" шаблонов - пусть этим знимаются другие специалисты :).

Теперь перейдем к примеру использования шаблонов. Предположим, что в нашем модуле для работы с блогом необходимо вывести три последние записи. Изменяем обработчик в blogModule:
@CLASS
blogModule

@USE
blog/blog.p
pf/web/pfSiteModule.p

@BASE
pfSiteModule

@create[aOptions]
  ^BASE:create[$aOptions]
# Инициализируем класс с моделью блога
  $blogModel[^blog::create[$.sql[$CSQL]]
# Задаем переменную с именем блога
  ^assignVar[title;Тестовый блог]
# Задаем функцию для формирования URL'а.
  ^assignVar[linkTo;$linkTo]
...

@onINDEX[aActionArgs][$lArticles]
# Получаем записи о 3 последних статьях
# Считаем, что метод возвращает нам таблицу date/title/body
  $lArticles[^blogModel.getArticles[3]] 
# Добавляем переменную в программное окружеин шаблонизатора
  ^assignVar[articles;$lArticles]
# Зовем шаблонизатор
  ^display[index.pt]
В папке /app/views/ создаем папку blog, а в ней файл index.pt с самим шаблоном:
  <h1>$title</h1>
  ^if($articles){
    ^articles.menu{
      <h2>$articles.title</h2>
      <p class="date">$articles.title</p>
      <p class="body">$articles.body</p>
    }
  }{
     <p>В блоге нет записей!</p>
   }
 
  <p class="actions"><a href="^linkTo[new]"></a></p>
Немного пояснений к коду. Методы assignVar и display являются "прокладкой" для методов assign и display класса pfTemplet, просто так удобнее програмировать, тем более, что метод еще и понимает вложенность модулей т.е. он будет искать шаблон index.pt не в корнейво папке для шаблонов (в нашем случае /app/views/), а в /app/views/blog/. Сам шаблон компилируется в отдельный объект класса pfTempletPattern, данные изолируются от глобального пространства имен, а сами переменые в шаблоне доступны как свойства только для чтения, что предотвращает их случайную перезапись.

В коде шаблонов можно определять свои операторы:
@main[]
  ...
  ^print_footer[]

@print_footer[]
 ...
Свойствой $CSQL - это ссылка на текущий объект класса pfSQL (создается автоматически контролером на основании переменной $SQL.connect-string или может быть инициализирован программистом самостоятельно). Контролер умеет не только создавать необходимые служебные классы (CSQL, AUTH, CACHE, TEMPLET), но и автоматически передает ссылки на них вложенным модулям. Таким образом облегчается работа по автоматической сборке модулей в единую систему.

В результате мы разделили "логику и представление", при этом получив вполне ясный код без "излишеств". Стоит добавить, что Templet умеет кешировать шаблоны, используя класс pfCache. Шаблоны можно хранить не только на диске, но и в любом другом доступном месте, например в БД.

Библиотека PF