Шаблоны: супервизор

Фанат

oncle terrible
Команда форума
Собственно, эти мои топики - это такая попытка думать вслух.
Сразу сформулировать не получается, поэтому выходит не очень внятно.

В общем, если подумать, то все мои страдания сводятся к такому обобщению:
Проблема шаблонизации имеет два уровня - примитивный и архитектурный.

С примитивным всё ясно - это собственно технология отображения единичного блока данных. Синтаксис разный в деталях, а по сути всё одно и то же. Вообще не стоит обсуждения.

А вот второй - для любителей на всё навесить ярлык - уже относится не столько к собственно шаблонизации, сколько к архитектуре приложения, к организации отображения, View.
И вот эта часть представляет собой проблему.
Которая заключается в том, что "Главный шаблон" сайта по сути представляет собой отдельный модуль, со своей логикой, своими данными и заморочками.
И попытка свести эту задачу тупо к шаблонизации порождает непонятки и кривизну в реализациях.

Из этой мысли я делаю такой вывод, что "супервизор" AKA "контроллер главного шаблона" однозначно нужен.
Попытки заменить контроллер главного шаблона такими вещами, как
- активным шаблоном
- наследованием
- созданием новых контроллеров/экшенов в существующих контроллерах.
- попытка управлять каждым блоком главного шаблона из каждого контроллера
- размножением главных шаблонов а-ля Духовность.
суть паллиатив и проблему не решают.

извините, что столь декларативно, и без примеров, но мне важно было сформулировать, а уточню детали чуть позже.
 

Фанат

oncle terrible
Команда форума
по сути, не шаблон у нас должен быть двухпроходным, а работа Вью.
которая и раскладывается на уровни, о которых я писал выше:
1. Тупо отрендерить шаблон переданным набором данных
2. Вызвать этот тупой рендерер для всех блоков на данной странице.

то есть, от схемы "шаблон с "местом для контента" надо уходить на схему "шаблон с десятком [условно равноправных] мест для контента".
Условно равноправных - потому что получение данных для "блока контента" обладает правом вето - если произошла ошибка, то вся концепция меняется - от отдаваемых НТТР заголовков до контента (попсовой 404-й).
а вот остальные блоки таким правом не обладают - наоборот, ошибки в них должны быть обработаны, и на их место поставлена заглушка (хотя лучше конечно просто вёрстка, которая не поедет из-за пустого блока).

В итоге, как решается проблема "каждому модулю - свой CSS"?
Да так же, как вывод новостей!
Контроллер по алгоритму, детали которого нам сейчас не важны, выбирает имена css файлов, которые потребуются на данной странице, запихивая их в массив.
В шаблоне же ссылки формируются из массива обычным циклом.
В итоге мы решили поставленную цель - развесистую ЛОГИКУ ВЫБОРА КСС ФАЙЛА вынесли в контроллер, в шаблоне оставив самое необходимое - только вывод!

Вполне допускаю, что написанное выше - баян. просьба дать ссылку на фреймворк, который это реализует.
 

Ragazzo

TDD interested
Фанат
Ссылку на что? на то как фреймворки подключают Css файлы через специальный класс работы с ними? ну вот ссылка. Я правда чуть мозг не сломал пока прочитал что ты написал, столько "своих" терминов. Я лично во view подключаю где мне надо, зачем пихать в контроллер мне немного не понятно, но каждый делает как хочет, да.
 

Фанат

oncle terrible
Команда форума
Соответственно, как у нас работает приложение в итоге?
роутер определяет нужный модуль, и пинает его.
контроллер собирает данные и дергает вью, передавая ему данные и имя файла шалабона.

Вью запускает шаблонизатор, который натравливает одно на другое возвращает отрендеренный шаблон в переменную.

Дальше Вью начинает выполнять работать таким мини-роутером - по списку дергать контроллеры всех блоков, расположенных на странице, получать от них данные и шаблон, ендерить и сохранять в переменную.
причём заключая такие вызовы в трай-кетч, и сохраняя пустую строку в случае фейла.
параллельно назначая всем переменным, полученным от шаблонизатора, статус "не искейпить".
Закончив этот мартышкин труд, он с чистой совестью натравливает шаблонизатор на Главный Шаблон.

Ну как, нормальный сценарий?
 

ksnk

прохожий
по сути, не шаблон у нас должен быть двухпроходным, а работа Вью.
по сути, если пользоваться twig'ом - шаблонизатором с развесистой логикой внутри, то view и будет шаблоном. Во всяком случае, я именно так себе это представляю ;)

В каком случае комбинирование css для каждой страницы будет выгоднее, чем один большой css в кеше броузера? Один большой css будет собираться один раз при монтаже-модификации сайта.
 

Ragazzo

TDD interested
Фанат
Ты не ЦМС ли пишешь случайно? :D
по списку дергать контроллеры всех блоков
это что именно?форвардинг как в HMVC? или просто рендеринг view других контроллеров? Немного не понял, зачем заключать в try()catch() разве если view не нашлось это не ошибка?не проще ли бросить будет Exception и отобразить стандартно информацию об ошибке, чем показывать пользователю недособранный template?
 

Фанат

oncle terrible
Команда форума
Фанат
Ссылку на что? на то как фреймворки подключают Css файлы через специальный класс работы с ними?
КСС - это частный случай.
Я, как раз, не хочу выделять работу с ксс-файлами в какой-то отдельный модуль. а хочу работать с ними, как с любыми другими данными.
Я лично во view подключаю где мне надо, зачем пихать в контроллер мне немного не понятно, но каждый делает как хочет, да.
поясни, плиз, если нетрудно?
 

ksnk

прохожий
imho, требуется свой собственный транслятор с языка шаблонов, в котором было бы возможно отмечать некоторые операторы как "активный с 404", "активный со сменой шаблона" , "ежели сломается - вот такоая затычка"...
 

Фанат

oncle terrible
Команда форума
Фанат
Немного не понял, зачем заключать в try()catch() разве если view не нашлось это не ошибка?не проще ли бросить будет Exception и отобразить стандартно информацию об ошибке, чем показывать пользователю недособранный template?
Это очень важный вопрос.
Я исхожу из положения, что главная страница сайта не состоит из "рыбы сайта и блока контента".
Что на самом деле, на любом мало-мальски взрослом сайте каждая страница содержит десяток разных блоков, каждый из которых имеет свой контроллер.
Но при этом "блок контента" сохраняет статус критически важного - если при его формировании вылезла ошибка - мы полностью переигрываем вывод.
Но вот для остальных блоков - это неправильно! Если, скажем, на хабре заглючил "прямой кефир" - это не повод кидать 404! Логично? Если основной контент отобразится нормально, но не будет бляшки справа - большинство пользователей и не заметят.
Именно поэтому я хочу пропускать ошибки в дополнительных модулях, тупо выводя заглушки на их месте
 

Фанат

oncle terrible
Команда форума
ksnk
по сути, если пользоваться twig'ом - шаблонизатором с развесистой логикой внутри,
imho, требуется свой собственный транслятор с языка шаблонов,
ЗАЧЕМ? :)
Вот об этом я ж и говорю! Перечисленные действия - это чистая бизнес-логика! Какой блок на странице показать. Шаблон не должен этим заниматься. Шаблонизатор должен быть туп - тупо рендерить переданные ему данные в переданный ему шаблон. Всё. Работа с блоками - бизнес-логика, и в шаблоне ей не место.
Я как раз это всё пишу, чтобы забрать у шаблона несвойственные ему функции, облегчить его, сделать архитектуру логичной, разложив всё по полочкам.
 

Фанат

oncle terrible
Команда форума
Ты не ЦМС ли пишешь случайно?
я думаю о переписывании Вью в самопальном фреймворке, в котором есть прекрасные идеи по шаблонизации(и не только), но шаблон начинает рендериться (в буфер, разумеется) до того, как будут получены все данные.
 

fixxxer

К.О.
Партнер клуба
Фанат
А можешь привести конкретный пример - как сделано, какие видишь проблемы?

Работа с блоками - бизнес-логика, и в шаблоне ей не место.
Ну вот у меня шаблоны и не решают, какие блоки показать. Блок либо есть в шаблоне, либо нет, данные все переданы заранее. К наследованию и прочим конструкциям это ортогонально :)
 

Фанат

oncle terrible
Команда форума
Фанат
А можешь привести конкретный пример - как сделано, какие видишь проблемы?
Ну вот взять хотя бы тот же самый дополнительный ксс. (для любителей придираться к частностям - пусть будет замена тайтла).

Для дефолтного случая, когда тайтл задается "блоком основного контента" задача решается элементарно - контроллер устанавливает переменную, передаёт во вью, шаблонизатор рендерит её в конечный хтмл. Всё в шоколаде.

Теперь рассмотрим случай, когда тайтл у нас меняет один из второстепенных блоков. К примеру - викторина с призами. В тайтле пишем 100500 денег приз.
Активный шаблон начинает исполнять сам себя. Рендерит тайтл, доходит до блока с викториной... эээ, а дальше как? извраты, которые предлагали в соседнем топике - регами кромсать итоговый хтмл?!

Двухпроходный шаблонизатор будет смотреться лучше, но тут проблема, которую поставил NeD в соседнем топике - мы не контролируем порядок выполнения. Не говоря уже о мало-мальски сложной логике вывода блоков (ту же викторину в виде виджета не надо выводить на основной странице викторины), а вместо него показать топ10 товаров.
Вопрос - КТО будет решать, какой виджет показывать? контроллер викторины? а как?

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

При этом если подходить к формированию главного шаблона точно так же, как к формированию шаблона страницы, задача превращается в тривиальную - любая логика, влияющая на состав и порядок отображаемых на странице данных, сначала пишется в контроллере, и только после того, как она отработает, начинается рендеринг.

Собственно, идея, которую я хочу протолкнуть - главный шаблон по сути не отличается от любого другого шаблона. И подход к нему должен быть такой же. Нафига изобретать козе баян в виде двухпроходности или активности - непонятно.
 

fixxxer

К.О.
Партнер клуба
А откуда взялась идея, что он может отличаться? У меня никогда не отличалось, ни с инклюдами, ни с наследованием.

Когда я говорил про layout template и page template, я ни в коем случае не имел в виду, что page template парсится отдельно - это, действительно, какой-то изврат; я имел ввиду простой include $page_template в layout template.
 

fixxxer

К.О.
Партнер клуба
Теперь рассмотрим случай, когда тайтл у нас меняет один из второстепенных блоков. К примеру - викторина с призами. В тайтле пишем 100500 денег приз.
Активный шаблон начинает исполнять сам себя. Рендерит тайтл, доходит до блока с викториной... эээ, а дальше как? извраты, которые предлагали в соседнем топике - регами кромсать итоговый хтмл?!
Кажется, (если я правильно понял), как раз для таких случаев в twig недавно появился тэг embed: http://twig.sensiolabs.org/doc/tags/embed.html
 

Фанат

oncle terrible
Команда форума
Кажется, (если я правильно понял), как раз для таких случаев в twig недавно появился тэг embed: http://twig.sensiolabs.org/doc/tags/embed.html
Ты уже постил его, кстати, и он так и висит у меня открытый в браузере непрочитанным, эх.

Но у меня, все-таки, два возражения.
Первое - принципиальное. Я принципиально не хочу решать задачи безнес-логики шаблонизатором.
А по моему мнению, то, какие блоки показывать на странице - это именно бизнес-логика.

и практическое - заэмбедить ведь можно только шаблон. Но ведь надо откуда-то ещё достать данные для него?

Неужели вещи, которые я говорю - настолько непривычны народу?
Учитывая постулат о том, что любой мало-мальский сайт просто обвешан виджетами, у меня только одно предположение - все тупо делают виджеты старой доброй лапшой, заморачиваясь на шаблоны только если для "основного контента"?
Ну, или решая большинство задач активным шаблоном/ ещё чем-то + для отдельных случаев грязные хаки.

А я хочу придумать систему - серебряную пулю, покрывающую любые случаи по определению, в штатном режиме. :)
придумал же я её для SQL! :)
 

ksnk

прохожий
fixxxer Нет, это не про то. Это - гибкий include подшаблона. Если это подшаблон пожелает менять заголовок - он обломится.
Хотя - забавно и полезно...
 

AmdY

Пью пиво
Команда форума
не нужно решать эту проблему. если есть блок с подобной бизнес логикой, то обсчитывай его в контроллере до вывода шаблона. я в своё время пытался решать эту проблему за счёт двух проходов, но получается говно какое-то.
 

ksnk

прохожий
Конечным результатом было бы получить список всех "активных шаблонов", по которому нужно собрать их данные перед рендерингом основного. Проблема именно в получении этого списка. А учитывая, что активные шаблоны могут вставляться или игнорироваться в соответствии с логикой главного, то простым списком совсем не просто будет обойтись ;)
 
Сверху