Деджаваскриптизиция (2)
Сделал то, что намеревался: удалил с сайта все сторонние сервисы. Больше нет социальных кнопок, гугло-аналитики и, самое важное, комментариев Disqus. На страницах вообще нет аякса за тем исключением, когда встроен плеер Ютуба. Красота.
Отдельно расскажу про комментарии. Теперь они встроены в блог, являются его частью, а не лежат на серверах Disqus. Для этого я написал импорт из XML. Ясное дело, на Кложе, исходники на Гитхабе.
Если вкратце, код пробегает по XML, строит мапы и индексы по ID. Для каждого комментария он создает файл вроде _comments/2016-08-08-08-27-14.md
с содержимым:
---
id: 2826354744
is_spam: false
is_deleted: false
post: /interview/
date: 2016-08-08T08:27:14Z
author_fullname: 'Александр'
author_nickname: 'VinokurovAlexnader'
author_is_anon: false
---
<p>Вопрос "Есть кортеж из трех элементов. Назначить переменным a, b, c его значения".</p>
<p>У Вас ответ:<br>a, b, c = [1, 2, 3]</p>
<p>Но это список, а не кортеж. С кортежом будет вот так:<br>a, b, c = (1, 2, 3)</p>
Всего таких файлов 993. В шаблон заметки я добавил код для вывода комментариев:
{% assign comments = site.comments | where:'post', include.permalink %}
{% if comments.size == 0 %}
<center>Комментариев пока нет</center>
{% else %}
<center>Комментарии</center>
<div class="comments-block">
{% for comment in comments %}
<div class="comment-block">
<p class="comment-lead">
<small>
<em>{{ comment.author_fullname or comment.author_nickname }}, {{ comment.date | date_to_string: "ordinal", "RU" }}</em>
</small>
</p>
<div>{{ comment.content | markdownify }}</div>
</div>
{% endfor %}
</div>
{% endif %}
Получилось неоптимально, потому что на каждый пост происходит линейный поиск. В идеале нужно один раз построить словарь URL => список комментариев и затем брать оттуда. Но я не настолько хорошо знаю Jekyll и Ruby, чтобы это запилить.
Ради интереса проверьте страницы, где много комментариев, например про сервис IVI или про интервью. Лично мне результат нравится: чистенький HTML, минимум CSS, все лаконично. На текущий момент не учитывается структура, но технически это возможно: каждый комментарий знает ID родителя, и однажды их вывод можно улучшить.
Теперь главное: как сделать прием комментариев. Мне накидали советов, плюс я гуглил, и все сводится двум решениям: Гитхаб или self-hosted сервис.
Напомню, как работает Гитхаб: люди пишут комменты к какому-либо issue. Зная номер issue, легко выгрести комментарии GET-запросом, сгенерить HTML и вставить под заметкой. Выглядит красиво:
, но меня тревожат две вещи.
- Комментарии лежат в чужом сервисе, который может отвалиться из-за санкций или Роскомнадзора.
- Обязательна авторизация через Гитхаб — не у всех есть учетная запись.
Self-hosted-решения вроде Remark42 интересны, но вынуждают держать виртуалку, платить за нее и делать бекапы. Придется возиться.
Я придумал так. Пишем лямбду для Яндекс.Облака (на Кложе с компиляцией Граалем). Лямбда принимает POST-запросы с сайта. На сайте висит статичная форма с полем action=URL нашей лямбды. Отправить форму может любой желающий, даже тот, у кого нет учетки в Гитхабе, Твиттере, Инстаграме и так далее.
Получив запрос, лямбда создает pull request в репозитории блога. Для этого не нужен git: все возможности Гитхаба доступны в REST API. Pull request содержит новый файл с комментарием в папке _comments
. Мне приходит письмо. Если норм, я нажимаю Merge, блог собирается и выкатывается новая версия.
Одновременно получается модерация: если кто-то написал дичь, я отклоняю PR, и делу конец.
Открыв PR, лямбда перенаправляет пользователя обратно в блог со словами “спасибо, ваш комментарий скоро появится”.
Вот такую штуку я хочу запилить. А пока что комментации работают только в Телеграме.
Нашли ошибку? Выделите мышкой и нажмите Ctrl/⌘+Enter
Ivan Grishaev, 19th Sep 2022, link
Проверка новых комментариев! Ссылка