Открыть список
Как стать автором
Обновить

Комментарии 9

Вы бы хоть какой-нибудь пример типа бложека сделали, а то одинокий hello world и больше никаких намёков на то, на что же будет похож итоговый код.
В качестве учебного пособия есть гостевая книга: github.com/nyan-cat/easybook, ее логика такая: регистрации нет, автор сообщения может редактировать или удалять сообщения. Автор определяется по правилу: если IP тот же, и если сообщение не старше 10 минут (конечно же это просто для примера, в жизни так не делают). Или вы ее и назвали hello world-ом? Реальный сайт будет примерно так и выглядеть, только будет больше файликов в каждой папке. Объемы файликов будут такие же, или чуть больше. Разве что последние фичи, описанные в этом посте, там еще не используются. Easybook должна дать полное понимание того, как делается сайт на Easyweb. В репе лежит easybook.sql — его надо импортнуть в базу, создать MySQL-юзера, прописать его логин-пароль в datasource.xml, и все — сайт заработает. Если же примера Easybook вам недостаточно, то напишите, что именно вы хотели бы увидеть, и я буду дорабатывать этот пример.

P.S. Хабротипограф — фи. Тире нужно отбивать неразрывным пробелом, а не обычным.
делаю нечто похожее, так что небольшой обмен опытом)

1. для парсера нужно уметь указывать baseURI относительно которого будут вычисляться relativeURI. использовать везде абсолютные ссылки — не предлагать)

2. get — слишком абстрактный интерфейс, лучше его конкретизировать: getDOMNode, getSimpleXML и тп. у меня у каждого узла просто есть свойства DOMNode и DOMDocument.

3. www:paginate — опять же префикс слишком абстрактен, лучше использовать конктретный типа easyweb:paginate. и использовать его не только в имени функции, но и в имени режимов (easyweb:previous,easyweb:next,...). основная цель пространств имён — не указать предназначение, а избежать конфликтов и недопониманий. впрочем, там действительно нужна эта функция? сдаётся мне всё это реализуемо не слишком сложными шаблонами. к тому же, почему нельзя указать откуда брать данные? или предполагается для каждого блока на странице вручную прогонять по xslt преобразованию? не слишком практичное решение.

4. инвалидация по времени — зло. неужели так сложно сделать инвалидацию по событиям? да и вообще, что там кешировать? xslt преобразования и так реактивны. а если уж совсем жалко процессорного времени фронтенда, то можно вообще переложить его на плечи клиента. для примера сайт: hyoo.ru/?article=XStyle;author=Nin+Jin — статейку тоже почитайте, может заинтересует)

5. «В репе лежит easybook.sql — его надо импортнуть в базу, создать MySQL-юзера, прописать его логин-пароль в datasource.xml, и все — сайт заработает.» — фу как сложно) вы же наверняка используете какой-нибудь pdo, так что какая проблема по умолчанию автоматом создавать sqlite базу с нужной структурой?

6. почему нету checked_children, кидающего исключение в случае отсутствия детей, а также checked_alone_children проверяющего, что он такой один?) я это к чему — ошибка в данных не является настолько исключительной ситуацией, чтобы раскручивать стек. и все такие ошибки должны быть обработаны и зачастую могут быть заменены дефолтными значениями или другими источниками получения. а если нужна логика «либо всё верно и работаем, либо не верно и падаем», то лучше применить какую-нибудь схему валидации с более совершенными механизмами чем проверка «в элементе есть хотябы один узел»)
Ох, сколько всего. Отвечу на каждый пункт отдельно, чтобы было удобнее обсуждать.

1. В PHP-конфиге сайта указывается константа website_root — все пути внутри сайта (за исключением пары особых ситуаций) считаются относительно этого пути: github.com/nyan-cat/easybook/blob/master/php/config.php
2. Вопрос именования сущностей — это тема отдельного курса лекций, обосновать свою позицию в несколько предложений не так просто. Но я все же попробую :) Имена сущностей должны нести минимум информации, которой, в свою очередь, должно быть достаточно для того, чтобы понять, как этой сущностью пользоваться, и не более. Имена не должны сообщать «как это устроено», только — «как этим пользоваться». Например, в Boost-е аналогичная функция назвается native_handle, и у сокетов, и у файлов, и у тредов. Я надеюсь, вы доверяете коммьюнити буста в вопросе имен? native_handle не говорит, что именно вы получите. Об этом можно догадаться по имени агрегирующего класса, и убедиться наверняка из документации. Именно поэтому в C++ шаблоны, конкретизированные параметрами, берут в typedef. Пользователю нужно знать, как этим пользоваться, а не как оно устроено. В 90% ситуаций пользователю достаточно знать про контейнер лишь то, что это контейнер, и его можно проитерировать через range-based for-loop. То есть, сосредоточиться стоит на том, «для чего мне это», а не «как это устроено». Я вижу всего один случай, когда действительно нужно называть функции getDOMNode / getSimpleXML — это когда фасилити умеют выдавать сразу несколько встроенных типов ресурсов.
3. Пространства имен XML — это не просто способ разрешения коллизии имен. Подразумевается, что за пространством имен стоит какая-то библиотека, или часть очень большой библиотеки (как в случае EXSLT). Функция введена просто для удобства, т.к. отрисовка пагинатора — задача каждого второго сайта. Все XPath-расширения, предоставляемые движком: github.com/nyan-cat/easyweb/wiki/XPath-extensions
Что же касается самого имени пространства имен «www» — предполагается, что XSL- и XPath-расширения Easyweb реализуют всю необходимую сайтостроительную функциональность и должны покрыть 95% всех вебмастеропотребностей, поэтому мне кажется совершенно логичным выбрать имя, претендующее на дефолтность.
4. Это например по каким событиям? Можете привести пару примеров? Теперь что касается кеширования. Необходимость решения возникла как раз в реальном проекте. Суть такова: на каждой странице сайта есть ссылка «Выбрать город». По нажатию появляется окно со списком городов. Всего городов порядка ~1500, а их XSL-отверстывание выполняется с группировкой по первой букве названия. По ТЗ нужнто было чтобы этот блок был именно в HTML, а не подгружался аяксом, и был на каждой странице сайта. При этом Google Bot ходит на сайт ~50 раз в секунду. Речь именно про страницы сайта, а не про скрипты или там favicon. Такой интенсивности оказалось достаточно, чтобы достаточно сильно напрячь деда на предпоследней линейке Intel Xeon. Введение кеша снизило общую нагрузку в разы. Вот вам и пример из реальной жизни ;-)
5. Easyweb — это не CMS. В ней нет ничего по умолчанию: нет готовых баз, готовых шаблонов, или чего-то еще готового. Голый сайт на Easyweb — это голый сайт впринципе, в котором нет вообще ничего. Считайте так: Easyweb — это XSLT-верстка + специальная шина данных. То есть, вы устанавливаете сторонние хранилища данных (MySQL, PostgreSQL, Apache Solr, GeoIP, и т.д.), конфигурите их как хотите, дизайните их внутренние контейнеры данных (базы, таблицы, индексы, и т.д.) так, как хотите, без каких-либо ограничений, и уже после этого конфигурите Easyweb так, чтобы он умел брать нужные данные из нужных мест. Далее вам остается только верстать на XSL, а Easyweb уже сам разберется, куда пойти, и что откуда взять.
6. Рекомендую еще раз посмотреть на Boost. Функции по работе с некоторыми типами системных ресурсов (например — файлы или сокеты) представлены в двух экземплярах — одна в случае ошибки кидает исключение, другая — возвращает ошибку через параметр-ссылку. Поскольку в PHP нет перегрузки функций, я решил сделать префикс checked_. Смысл в том, что одной и той же функцией можно воспользоваться с разными ожиданиями. В одном случае логика программы может сразу же предполагать, что файла может и не быть. То есть — это не является ошибкой, а является одним из валидных кейсов. В таком случае пользовател пишет что-то вроде:
if($file = fs::read('...'))
{
    # ...
}

Но может быть ситуация, когда файл обязан быть, и его отсутствие означает невалидность каких-либо дальнейших действий. В таком случае пользователь пишет:
$file = fs::checked_read('...');
# ...

и получает гарантию, что «либо все, либо ничего».
checked_children не нужен, т.к. в случая отсутствия детей функция вернет пустой range, из-за которого foreach не сломается, а просто будет выполнено ноль итераций. checked_ функций не так много: это fs::checked_read, nodeset::checked_first и nodeset::checked_last. Кажется — все. Это просто редкие ситуации, когда одна и та же функция в разных ситуациях может вызываться с разными ожиданиями.
Только полноправные пользователи могут оставлять комментарии. Войдите, пожалуйста.