mod: про проект и планы...

This commit is contained in:
2026-05-15 13:59:07 +03:00
parent 468d8e8fc4
commit ec82d4d36f
2 changed files with 44 additions and 91 deletions

110
README.md
View File

@@ -1,26 +1,47 @@
# Оконный агрегатор «Окнардия» # Оконный агрегатор «Окнардия»
### Переделка под Python 3.12 и Django 5.2 **Окнардия** — веб-сервис для сравнения цен на установку оконных конструкций в типовых многоквартирных домах России.
#### Планы, задачи, маркеры и идеи на будущее: * **Пользователь, желающий заменить окна**, вводит адрес дома → система распознаёт серию строения → выдаёт типовые размеры оконных проёмов → показывает предложения от поставщиков на установку (замену) окон, с ценами, характеристиками компонентов и условиями.
Алгоритмические рейтинги защищают потенциального покупателя от возможных накруток отзывов и позволяют сравнивать предложения по объективным характеристикам.
Для **производителей и поставщиков окон** платформа — это канал прямого доступа к целевой аудитории в конкретном районе города.
Они размещают свои предложения (компоненты, наборы, цены) и конкурируют на равных условиях. Масштабируемый каталог позволяет охватить
множество адресов типовой застройки, а система алгоритмического рейтинга (нет отзывов клиентов, а значит накрутка отзывов невозможна) ранжирует предложения исключительно по характеристикам и условиям предложений.
**Стек**: Python 3.12+ · Django 5.2+ · SQLite/MariaDB · Bootstrap 3.3 · jQuery · Yandex Maps API
---
### Переделка под Python 3.12 и Django 5.2.13 (апрель-май 2026)
Сделано:
* Переход проекта под Python 3.12 и Django 5.2.13, удаление устаревших зависимостей, унификация функций и хелперов.
* Перехода на SQLite (возможно, после нагрузочного тестирования переход обратно на mariaDB или PostgreSQL). * Перехода на SQLite (возможно, после нагрузочного тестирования переход обратно на mariaDB или PostgreSQL).
* Переделать все raw SQL-запросы на ORM для лучшей поддержки разных СУБД в будущем. * Переделаны все raw SQL-запросы на ORM для лучшей поддержки разных СУБД в будущем.
* Актуальная SEO- и LLM-оптимизация: добавить разметку schema.org, улучшить мета-теги, оптимизировать URL-структуру и канонические ссылки. * Все сервисные функции из `service/` вынесены в management-команды.
* Длялегаси-страниц (шаблоны и вьюхи) поэтапно проверять (если нужно убирать) старые SEO-хвосты вроде `last_update` / `PUB_DAT` / `Date4Meta` / `Last4Meta`: если дата не несёт смысловой нагрузки, лучше оставлять базовые `{% now %}` из `base.html`, а не тащить лишний контекст во вьюху. * Переработаны все шаблоны с целью SEO- и LLM-оптимизацим: более корректные meta-теги, разметка schema.org
* Шаблоны `report/report_last_user_visit.html` и `report/report_log_user_visit.html` сделать подгружаемыми через AJAX или (использовать HTMX, напрмемер) и убрать вызовы `get_last_user_visit_list` (переделать чтобьы формировалось на стороне клиента из куки. через `JSON-LD`, оптимизирована структура "хлебных крошек" и изменение роутинга.
* Все действия из сервисной `/service/` вынести в management-команды. * Облегчение шаблона `base.html`: блок логин-логаут подгружается через AJAX только по клику, модуль авторизации
* Перейти на `poetry` для управления зависимостями и виртуальным окружением. вынесен в отдельный JS-файл (`/static/js/auth.js`), счетчики посещений перенесены в подгружаемый JS.
* Перейти на Django 6.* * Шаблоны `report/report_last_user_visit.html` больше не требуют серверного рендеринга, а формируются
* Улучшение в блогах (добавить SEO-поля, Codemirror 6, Типограф etpgrfо, слаги через BS4 и pytils). на стороне клиента из кук.
* Добавлены SEO-поля блогов.
### Планы, задачи, маркеры на будущее:
* Оптимизация кеширования pre-render шаблонов: настроить cronjob для ежедневной/еженедельной очистки `seria_info/prepared/`.
* Улучшение администрирования в блогах (Codemirror 6, Типографф).
* Упаковать всё в контейнеры: бакенд Django + Gunicorn + WhiteNoise... * Упаковать всё в контейнеры: бакенд Django + Gunicorn + WhiteNoise...
* CI/CD через gitea + Watchtower для автоматического деплоя при пуше тега `v*.*.*` в репозиторий. * CI/CD через gitea + Watchtower для автоматического деплоя при пуше тега `v*.*.*` в репозиторий.
* Фронтенд: перейти на новый Bootstrap 5, добавить интерактивные элементы через HTMX + Alpine, сделать адаптивность для мобильных устройств. Убрать jQuery и старые плагины, заменить на современные аналоги. * Фронтенд: перейти на новый Bootstrap 5, добавить интерактивные элементы через HTMX + Alpine, сделать адаптивность для мобильных устройств. Убрать jQuery и старые плагины, заменить на современные аналоги.
* Оптимизация для мобильных устройств: адаптивный дизайн, оптимизация изображений, улучшение производительности.
* Переход проекта под Python 3.14 и Django 6.x.
* Нагрузочное тестирование (рпи необходимости переход с SQLite на PostgreSQL в продакшене).
# См. также: # См. также:
* [`MANAGEMENT_RUNBOOK.md`](MANAGEMENT_RUNBOOK.md) единый runbook по management-командам и batch-операциям, сниппеты. * [`MANAGEMENT_RUNBOOK.md`](MANAGEMENT_RUNBOOK.md) единый runbook по management-командам и batch-операциям, сниппеты.
* [`ROADMAP.md`](ROADMAP.md) дорожная карта переделки (весна 2026) с описанием выполненных шагов (ключевые коммиты).
* [`AGENTS.md`](AGENTS.md) контекст проекта для AI-ассистентов (архитектура, конвенции, рабочие сценарии). * [`AGENTS.md`](AGENTS.md) контекст проекта для AI-ассистентов (архитектура, конвенции, рабочие сценарии).
* [`SETUP.md`](SETUP.md) пошаговая настройка окружения, запуск проекта и базовые команды разработки. * [`SETUP.md`](SETUP.md) пошаговая настройка окружения, запуск проекта и базовые команды разработки.
@@ -40,63 +61,18 @@
Эти картинки создаются автоматически. Можно не удалять. Даже если какая-то схема открывания или размер проёма станет Эти картинки создаются автоматически. Можно не удалять. Даже если какая-то схема открывания или размер проёма станет
неактуальным, лишняя картинка просто будет лежать в папке (вдруг такой проём появится снова). неактуальным, лишняя картинка просто будет лежать в папке (вдруг такой проём появится снова).
#### Кеширование шаблонов #### Кеширование pre-render шаблонов серий домов
В папке `oknardia/oknardia/templates/seria_info/prepared` создаются пре-рендер шаблоны с информацией о сериях домов. В папке `oknardia/templates/seria_info/prepared/` создаются пре-рендер HTML-шаблоны с информацией о сериях домов.
Эти шаблоны надо периодически удалять. Они нужны для скорости. Но если меняются данные по серии, размерам окон, появляются Эти шаблоны создаются при первом обращении к странице серии и хранятся для ускорения последующих запросов.
новые коммерческие предложения -- их надо удалять и тогда построятся новые. Вообще на быстрых серверах скорость может **Важно**: их надо периодически удалять, особенно если меняются:
не быть проблемой, так что возможно стоит просто настроить через crone ежедневное или еженедельное удаление этих * данные по сериям и размерам окон
пре-рендер шаблонов. При обращении к соответсвующий страницам эти шаблоны будут пересозданы автоматически. * коммерческие предложения и цены
* рейтинги компонентов
**Рекомендация**: настроить cronjob на ежедневное или еженедельное удаление этих файлов. При обращении к соответствующим
страницам эти шаблоны будут пересозданы автоматически. На быстрых серверах можно вообще отключить кеширование, если оно
не критично для производительности.
### Некоторые заметки относительно разработки (DEV) на macOS:
Т.к. MariaDB "сидит" в контейнере Dockers могут возникнуть трудности при установке коннектора к базам данных MySQL/MariaDB. Примерно такие:
```txt
Collecting mysqlclient
Using cached mysqlclient-2.1.1.tar.gz (88 kB)
Preparing metadata (setup.py) ... error
error: subprocess-exited-with-error
× python setup.py egg_info did not run successfully.
│ exit code: 1
╰─> [16 lines of output]
/bin/sh: mysql_config: command not found
/bin/sh: mariadb_config: command not found
/bin/sh: mysql_config: command not found
Traceback (most recent call last):
File "<string>", line 2, in <module>
File "<pip-setuptools-caller>", line 34, in <module>
File "/private/var/folders/jh/gbhf3vk11svg9w4mvhntlb7c0000gn/T/pip-install-nu5ar2g2/mysqlclient_a07e3d9dbe514c7793dc71f1183dda19/setup.py", line 15, in <module>
metadata, options = get_config()
File "/private/var/folders/jh/gbhf3vk11svg9w4mvhntlb7c0000gn/T/pip-install-nu5ar2g2/mysqlclient_a07e3d9dbe514c7793dc71f1183dda19/setup_posix.py", line 70, in get_config
libs = mysql_config("libs")
File "/private/var/folders/jh/gbhf3vk11svg9w4mvhntlb7c0000gn/T/pip-install-nu5ar2g2/mysqlclient_a07e3d9dbe514c7793dc71f1183dda19/setup_posix.py", line 31, in mysql_config
raise OSError("{} not found".format(_mysql_config_path))
OSError: mysql_config not found
mysql_config --version
mariadb_config --version
mysql_config --libs
[end of output]
note: This error originates from a subprocess, and is likely not a problem with pip.
error: metadata-generation-failed
× Encountered error while generating package metadata.
╰─> See above for output.
note: This is an issue with the package mentioned above, not pip.
hint: See above for details.
```
Починить проблему можно воспользовавшись ([рецептом со StackOverflow](https://stackoverflow.com/a/44268445/1504067)):
```shell
brew install mariadb-connector-c
# sudo ln -s /usr/local/opt/mariadb-connector-c/bin/mariadb_config /usr/local/bin/mysql_config
pip install mysqlclient
# rm /usr/local/bin/mysql_config
brew unlink mariadb-connector-c
```

View File

@@ -1,23 +0,0 @@
# Дорожная карта переделки 2026 для проекта Oknardia
# Готово:
* Изменена база данных используемая в проекте (SQLite вместо MariaDB).
* Окружение проекта теперь настраивается через `poetry` вместо `pip` и `requirements.txt`.
* Проект получает настройки и секреты через переменные окружения (`.env`) вместо `my_secret*.py`.
* Рефакторинг создания `sitemap.xml`: raw ⟶ ORM, создание через Django-команду `generate_sitemaps` в медиа-файлы.
* Рефакторинг URL `/catalog/profil/`: raw SQL ⟶ ORM, убран `last_update`, измененs SEO `description` и `keywords`.
* Распилен `oknardia/web/catalog.py` на тематические модули (`catalog_companies.py`, `catalog_profiles.py`, `catalog_series.py`, `catalog_openings.py`) с вынесением общей логики в `catalog_utils.py`; маршруты обновлены без изменения внешних URL. Улучшены SEO-атрибуты, и добавлена разметка shema.org.
* Рефакторинг `catalog_profile_model` (`/catalog/profile/...`): raw SQL ⟶ ORM, упрощена логика, вынесены helper-функции, сокращено дублирование расчёта цветов рейтинга, нормализована подготовка `LIST_OTHER`/`MERCHANTS`/`PROFILES`/`PROFILE_DETAIL`, сохранена совместимость шаблонов. Улучшены SEO-атрибуты, и добавлена разметка shema.org.
* Рефакторинг `catalog_profile_manufacture` (`/catalog/profile/<id>-<manufacturer>`): упрощена валидация URL, убран дублирующий код маппинга для `PROFILES` и `MERCHANTS` через общие хелперы, стандартизирован хвост контекста (`LAST_VISIT`, `LOG_VISIT`, `ticks`) через `_append_visit_context`. Улучшены SEO-атрибуты, и добавлена разметка shema.org.
* Рефакторинг `catalog_seria` (`/catalog/seria/`): raw SQL ⟶ ORM для списка корневых серий, подготовка данных упрощена, хвост контекста с визитами и `ticks` вынесен в общий helper внутри `catalog_series.py`. Улучшены SEO-атрибуты, и добавлена разметка shema.org.
* Рефакторинг `catalog_seria_info` и связанных функций в `catalog_series.py`: raw SQL ⟶ ORM (`catalog_seria_info`, `seria_nav`, `seria_info_year`, `seria_info_geo_code`), снижена нагрузка на БД за счёт предвыборки и переиспользования агрегатов (`quantities_by_pair`, `offers_by_window`), добавлены безопасные fallback-значения для пустых выборок, включена потоковая обработка `iterator(chunk_size=500)` для гео-данных, обновлены комментарии и docstring под фактическую логику (таблица окон, pre-render light/heavy шаблонов, гео+статистика серии). Улучшены SEO-атрибуты, и добавлена разметка shema.org.
* Добавлена management-команда `regenerate_seria_prerender` для оффлайн-пересборки pre-render шаблонов `catalog_seria_info` (все или выбранные root-серии), с режимами `--dry-run` и `--force`; серверный reload (Gunicon? uWSGI или что там еще будет) должен быть вынесен из кода приложения в оркестрацию (cron/systemd/deploy step).
* Рефакторинг `standard_opening`: raw SQL -> ORM, упрощена дедублекация, убраны лишние запросы и переменные контекста, добавлены комментарии, SEO-описание и keywords, стандартизирован хвост контекста с визитами и `ticks` через общий helper внутри `catalog_openings.py`. Улучшены SEO-атрибуты и добавлена разметка shema.org.
* Рефакторинг `catalog_company` и `catalog_company_detail` (`/catalog/company`): raw SQL → ORM для получения списка компаний и их наборов, вынесены вспомогательные функции (`_get_company_statistics`, `_get_company_sets_detail`, `_format_company_for_template`, `_format_set_for_template`, `_clean_text_field`, `_lowercase_first_char`), упрощена логика форматирования данных, добавлены подробные комментарии и docstring для каждой функции, использованы `select_related` и `annotate` для оптимизации запросов, добавлена защита от `Http404` при неправильных slugs. Улучшены SEO-атрибуты, и добавлена разметка shema.org.
* Рефакторирнг главной страницы каталога (`/catalog/`): Улучшены SEO-атрибуты, и добавлена разметка shema.org.
* Рефакторинг страницы цен одного окна: введён новый канонический SEO-роут внутри `/catalog/standard_opening/`, старый URL сохранён как legacy и переведён на постоянный 301-редирект; в `prices.py` для ветки одного окна raw SQL заменён на ORM; в шаблонах `price_offers_for_one_window.html` и `price_offers_for_one_window_frame.html` улучшены SEO-атрибуты и добавлена JSON-LD разметка `schema.org` (`BreadcrumbList`, `Product`, `ItemList`, `Offer`) с размером окна, ценами и ключевыми характеристиками предложений; добавлены тесты `web.test_prices`.
* Рефакторинг страницы ценовых предложений: в `prices.py` для ветки ценовых предложений raw SQL заменён на ORM, добавлены комментарии и docstring, оптимизированы запросы с помощью `select_related` и `annotate`, добавлена обработка случая с отсутствующими предложениями; в шаблоне `price_offers.html` улучшены SEO-атрибуты и добавлена JSON-LD разметка `schema.org` (`BreadcrumbList`, `Product`, `ItemList`, `Offer`) с размером окна, ценами и ключевыми характеристиками предложений; добавлены тесты `web.test_prices`. Добавлены хлебные крошки в шаблон.
* Замена рутинга для ценовых предложений: старый URL `(?P<build_id>/<apart_id>)/<build_slug>` заменен на `/price/seriaID<sriea_id>--<seria_slug>/appartID<apart_id>/addressID<build_idD>--<build_slug>` что, прредположительно поможет SEO т.к. соответвует новым хлебным крошкам. Сделал редирект со старого URL на новый внутри `prices.py` и обновил ссылки в шаблонах, где были прямые ссылки на старый URL.
*
*