Если вы обнаружили, что исходный HTML отличается от того, что видите в браузере, действуйте по шагам.
Шаг 1. Определите источник проблемы
Проверьте, на каком этапе контент добавляется. Если он появляется только после выполнения JavaScript (например, через fetch-запросы), вам нужно внедрить серверный рендеринг (SSR) для вашего фреймворка (Next.js для React, Nuxt.js для Vue, Angular Universal для Angular). Если сайт статический, рассмотрите пререндеринг — генерацию статических HTML-файлов на этапе сборки.
Шаг 2. Внедрите SSR или пререндеринг
- Для React-приложений: используйте Next.js или ReactDOMServer.hydrate().
- Для Vue-приложений: переходите на Nuxt.js в режиме универсального приложения.
- Для статических сайтов: настройте генерацию HTML на сервере через headless CMS или статический генератор (Gatsby, Eleventy).
Убедитесь, что title, description, canonical и hreflang прописаны в исходном HTML, а не добавляются через JS. Используйте инструмент для проверки — если в полученном коде нет <title>Нужный заголовок</title>, а в браузере он есть, значит мета-теги динамические. Исправьте это, перенеся логику на сервер.
Шаг 4. Проверьте ссылки и структуру
Все внутренние ссылки должны присутствовать в исходном HTML. Если ссылки генерируются через JS (например, router.push()), краулер их не увидит. Замените их на реальные <a href="..."> или добавьте noscript-версию навигации.
Шаг 5. Настройте lazy-loading с умом
Изображения и видео, загружаемые через lazy-load, должны иметь атрибут src или srcset в исходном коде (или хотя бы placeholder с data-src). Для краулера лучше явно указывать src и использовать loading="lazy" — это безопасно.