Подписка на обновления через RSS
Карта распространения добавила RSS как открытый путь к обновлениям. RSS — XML-лента, которую читатель может подключить в подходящем приложении и получать новые записи без участия редакции в его аккаунте. В этом уроке составим локальный образец FEED-01 и правила включения материалов. Реальная лента ProfessorWeb не создаётся и не публикуется.
В lesson-21 архива серии находится полный учебный feed.xml. Все домены с окончанием .example, даты и состояния публикации вымышлены. Лента представляет отдельный сценарий ожидаемого выпуска, а не подтверждённую выдачу действующего сайта. Программы чтения и сетевые запросы не запускались.
Запись и идентификатор
Для RSS 2.0 задаются канал и записи материалов. У канала обязательны title, link и description. Для записи будем использовать заголовок, ссылку, краткое описание, дату и устойчивый guid. Значение guid помогает читателю различать записи; при isPermaLink="false" оно не обязано быть открываемым URL. Эти свойства формата описаны в спецификации RSS 2.0.
В нашей модели ID записи urn:professorweb-lab:PUB-01 остаётся прежним, когда редактор исправляет опечатку. Ссылка обозначает страницу материала, а описание — короткую самостоятельную аннотацию. Не используем номер сборки как ID статьи: очередная сборка тогда выглядела бы новым материалом. Устойчивость определяется редакционной сущностью, которую мы ввели в реестре содержания.
Канал назовём «Профессор Веб — учебная лента». Его адрес https://professorweb.example/ обозначает вымышленную площадку. Первая запись ведёт к условному материалу о сохранении пути, вторая — к разбору источника адреса. Это не новые маршруты настоящего ProfessorWeb. В исходной редакционной цепочке PUB-01 и PUB-04 остаются локальными карточками; сценарий ленты описывает, как они выглядели бы после согласованного выпуска.
Полный локальный образец
Ниже структура первой записи; полный файл с двумя записями находится в приложении. Фрагмент предназначен для чтения, не исполнения или загрузки.
<item>
<title>Адрес страницы и имя исходника</title>
<link>https://professorweb.example/articles/url-and-source.html</link>
<description>Почему перенос текста не должен случайно менять прежний путь.</description>
<guid isPermaLink="false">urn:professorweb-lab:PUB-01</guid>
<pubDate>Sun, 11 Oct 2026 09:00:00 GMT</pubDate>
</item>
Обратите внимание на три разных значения: заголовок можно редактировать, ссылку обычно сохраняют как постоянный адрес, идентификатор сохраняет саму запись. В нашей политике обычная правка не меняет ни ID, ни дату первоначального выпуска. При существенном обновлении редакция может пояснить его в описании, но не изображать старую статью новой без отдельного основания.
Даты RSS имеют специальный формат; выбранная запись содержит день недели, число, месяц, год и часовой пояс. Точная дата здесь учебная. При настоящем построении значение должно браться из подтверждённой даты публикации, а не из времени каждой сборки. Иначе читатель увидит ложное обновление всех материалов после обычной технической операции. Неизвестную дату нельзя заменять случайной текущей минутой.
Политика отбора
В реальном выпуске лента должна включать только доступные материалы. Черновик, закрытый предпросмотр и карточка без URL не являются готовыми записями. Для FEED-01 зададим отдельное условие published_in_model: оно разрешает только учебный сценарий двух вымышленных страниц. Поле не меняет draft статей нашего репозитория и не объявляет их опубликованными. Такое разделение предотвращает путаницу между моделью и действующим сайтом.
Описание записи полезнее пустого «читайте новую статью». Для PUB-01 оно раскрывает различие адреса и исходника. Полный текст можно оставить на сайте, если задача ленты — выбор материала. Это редакционное решение, а не запрет RSS на полное содержание. В лаборатории выбираем краткие аннотации, потому что они согласованы с пакетом распространения и не дублируют длинные уроки.
Особые символы требуют XML-экранирования. Если в аннотации появляется амперсанд, он не должен разрушать документ. В приложении строки не содержат HTML-разметку и обходятся простым текстом. При будущей реализации генератора текстовые значения нужно сериализовать корректно, а не собирать случайным соединением строк. В этой главе генератор отсутствует, поэтому мы не заявляем, что образец прошёл машинную проверку.
Политика также определяет размер окна. Для модели оставим десять последних доступных материалов, хотя файл содержит только две записи. Это не требование спецификации и не измеренная оптимальная длина. Ограничение помогает не превращать подписку на обновления в выгрузку всей многотысячной библиотеки. Старые страницы продолжают находиться через каталог и оглавления, даже когда исчезают из окна ленты.
Обновление и наблюдение
Когда появляется новый материал, его ID добавляется, а старые сохраняются в пределах окна. Если исправлена аннотация PUB-01, запись с тем же ID остаётся той же сущностью. Конкретное приложение читателя может обрабатывать обновления по-своему, поэтому редакция не должна обещать одинаковый интерфейс всем. Наша задача — предоставить устойчивые данные и понятную политику, а не управлять чужим устройством.
У ленты нужен заметный вход на сайте: понятная ссылка «RSS обновлений» и краткое объяснение назначения. Техническое XML-содержимое не заменяет такой текст. Но этот урок не меняет хедер или футер ProfessorWeb; он готовит приложение для будущей интеграции. Публичный URL реальной ленты остаётся неизвестным, а поле deployed — ложным.
Число скачиваний ленты не равно числу подписчиков. Приложение может запрашивать её повторно, а общий сервис — обслуживать нескольких читателей. В нашей лаборатории запросов вообще нет. Если редакция позднее решит измерять использование, нужно отдельно определить наблюдение и ограничения. RSS предоставляет открытый маршрут получения данных, но не готовую точную аналитику аудитории.
В after.json добавлены FEED-01, политика отбора и устойчивые ID. Полный файл в приложении содержит объявление XML, канал и две записи. Ожидаемый результат — возможность сопоставить материал реестра с записью ленты и объяснить, почему обычная правка не должна создавать новый ID. Никакой подписки в реальном приложении не оформлялось.
Измените сценарий: PUB-04 ещё не доступен в вымышленном выпуске. Исключите его из ленты, сохранив карточку в редакционном плане. Оставшаяся запись должна по-прежнему иметь тот же ID и дату. Так политика отбора связывает обновления с состоянием материала и не раскрывает неподготовленные страницы только ради заполнения списка.