
Исходная задача сообщает о пропавшем логотипе в PDF с конфигурацией товара. Она не называет используемую библиотеку и не устанавливает причину. Ниже разобран учебный порядок диагностики. В примере используется условный графический знак; реальный логотип, домен клиента и содержимое коммерческого документа не нужны.
Начать с фактического PDF
Сохраните документ, который показывает проблему, в разрешённом рабочем месте и сравните его с исходной веб-страницей. Убедитесь, что речь идёт об одном шаблоне и одной версии конфигурации. Иногда браузер показывает актуальную страницу, а фоновый обработчик использует старый HTML или ранее созданный файл. В таком случае работа с путём картинки в новом шаблоне не изменит отправляемое вложение.
Проверьте, исчез только логотип или все изображения. Посмотрите, сохранилось ли место, есть ли подпись, пустая область или сдвиг соседнего текста. Эти наблюдения помогают разделить недоступный ресурс, ошибку формата и правило печатного оформления. Не называйте конкретную причину по одному белому прямоугольнику: одинаковый результат может получиться на разных этапах.
Откройте файл в поддерживаемом просмотрщике и проверьте несколько страниц. Если изображение появляется лишь на первой либо пропадает при переносе, исследуйте правила размещения и разбиения страницы. Снимок одного первого экрана не показывает весь документ. Для публичной иллюстрации достаточно учебного PDF без контактов, цен и спецификации клиента.
Найти источник изображения в шаблоне
Определите, как логотип вставляется: элемент img, CSS-фон, встроенный SVG или изображение внутри другого шаблона. У каждого способа собственные требования. Например, печатные настройки могут иначе обрабатывать фон, а поддержка сложного SVG зависит от генератора. Нельзя переносить успешный браузерный результат на любой PDF-движок без проверки его документации.
Просмотрите итоговый HTML, который получает рендерер, а не только исходный файл шаблона. Во время сборки адрес мог измениться, переменная остаться пустой или условие убрать блок. Если итоговый HTML уже не содержит правильного источника, диагностика сети не нужна до исправления этого этапа. Сохраняйте учебный минимальный пример, исключая персональные данные из промежуточного документа.
Проверьте, нет ли второго логотипа для печати. Экранный и печатный варианты могут выбирать разные ресурсы. Иногда первый успешно отображается на сайте, а второй ссылается на несуществующий файл. Переключение стилей в браузере помогает заметить различие, но окончательную проверку выполняют используемым PDF-генератором, поскольку его возможности могут отличаться.
| Источник | Что проверить |
|---|---|
| Относительный img src | Базовый URL или путь рендерера |
| Абсолютный HTTPS-адрес | Доступность из среды генерации |
| CSS-фон | Печатные настройки и поддержка |
| SVG | Поддержка конкретных конструкций движком |
| Локальный файл | Разрешения и допустимые пути чтения |
Разрешить относительный адрес в правильном контексте
Относительный путь получает смысл только вместе с базовым адресом или каталогом. MDN описывает это на примере конструктора URL: результат зависит от переданной базы. В браузере база обычно связана с открытой страницей, а фоновая генерация может получать строку HTML без такого контекста. Тогда один и тот же src указывает в другое место или не разрешается вовсе.
Учебный шаблон с путём assets/mark.svg может работать на странице каталога, но не при обработке HTML из временного каталога. Не исправляйте это слепым добавлением текущего домена запроса. Фоновая задача может не иметь запроса, а сайт обслуживать несколько витрин. Источник базового адреса должен быть доверенным и принадлежать нужному сайту документа.
Выберите поддерживаемый способ: явная база, разрешённый абсолютный адрес, встроенный ресурс или локальный путь по правилам движка. У каждого варианта есть ограничения доставки и безопасности. Не выдавайте один из них за универсальный. Важно, чтобы выбранный способ работал в реальной среде генерации и не зависел от случайного рабочего каталога процесса.
Проверить доступ из среды генератора
Доступность картинки в личном браузере не означает её доступность серверному процессу. Браузер может иметь авторизацию, сетевой маршрут и доверенные сертификаты, которых нет у фонового обработчика. Проверьте запрос из разрешённой среды с теми же ограничениями. Не передавайте в рендерер личную сессию администратора ради появления одного изображения.
Если ресурс требует входа, решите, действительно ли логотип должен быть защищён таким способом. Для публичного фирменного знака обычно можно выбрать отдельный разрешённый источник, но решение зависит от проекта. Нельзя открывать целый закрытый каталог документов, чтобы сделать доступным один файл. Ограничение должно соответствовать назначению ресурса и правам процесса.
Проверьте DNS, HTTPS и сетевую политику среды. Не отключайте проверку сертификатов как постоянный способ устранения ошибки. Если генератор не доверяет цепочке или обращается к недоступному имени, исправляйте подтверждённую причину. В статье достаточно описать наблюдения; реальные внутренние адреса и настройки сети клиента не публикуются.
Уточнить поддержку формата
PNG, JPEG и SVG имеют разные свойства, а конкретный PDF-движок может поддерживать их не одинаково. Проверьте документацию установленной версии и минимальный пример с тем же файлом. Успешное открытие SVG в современном браузере не доказывает поддержку шрифтов, масок, фильтров или внешних ссылок внутри него в другом рендерере.
Для проверки подготовьте простой учебный знак в нескольких разрешённых форматах. Если один вариант работает, а другой нет, это сужает причину, но не оправдывает ухудшение качества без оценки. Растровая версия должна иметь достаточный размер для печати, прозрачность и корректный цвет. Не растягивайте маленькую миниатюру только ради факта появления картинки.
Если SVG содержит внешние ресурсы, они образуют дополнительную цепочку загрузки. Один доступный файл может ссылаться на недоступный шрифт или другое изображение. Старайтесь использовать самостоятельный проверенный ресурс, когда это соответствует требованиям. Не заменяйте фирменный знак самодельным похожим изображением и не называйте такую замену исправлением реального логотипа.
Сверить экранные и печатные стили
PDF может формироваться в печатном режиме, который применяет другие CSS-правила. В документации Playwright, например, указано использование print media для page.pdf по умолчанию. Это иллюстрирует зависимость среды, но не означает, что исходный проект использует именно Playwright. Для своего генератора проверьте фактический режим и правила шаблона.
Поищите print-правила, скрывающие шапку, изображения или фон. Логотип мог быть частью навигационного блока, который целиком исключается из печати. В таком случае сетевой запрос проходит, но элемент не рисуется. Исправление состоит в корректной структуре печатного документа, а не в замене адреса файла или расширении прав доступа.
Проверьте размеры, переполнение и положение. Изображение может оказаться за пределами печатной области, перекрыться блоком или получить нулевую высоту после применения правил. Учебный тест с заметной временной границей контейнера помогает установить геометрию. После диагностики служебное оформление удаляют, а окончательный файл проверяют заново.
Дождаться ресурсов штатным способом
Если движок использует браузерный рендеринг, документ может печататься до завершения нужной загрузки. Не добавляйте произвольную длинную паузу как единственное решение. Определите, какое состояние подтверждает готовность изображений и шрифтов в используемой библиотеке. Способ ожидания должен соответствовать её API и не превращаться в бесконечное ожидание внешнего сервиса.
Установите ограничение времени и понятный результат ошибки. Если обязательный логотип недоступен, проект должен решить, допустим ли документ без него или генерация должна остановиться с диагностикой. Нельзя молча отправить неполный документ как полностью проверенный. При этом декоративный ресурс и существенный элемент документа могут иметь разные правила отказа.
Проверьте медленную загрузку и недоступность на учебной копии. Быстрая локальная сеть скрывает гонку готовности. Отдельно убедитесь, что повторная попытка не отправляет письмо дважды. Генерация файла и доставка уведомления относятся к разным действиям: исправление ожидания ресурса не должно создавать повторную бизнес-отправку.
Не привязывать документ к случайному домену
В группе сайтов логотип и базовый адрес должны выбираться по явному контексту документа. Если шаблон использует первый домен установки, PDF одной витрины может получить знак другой. Даже если изображение стало видно, это ещё не правильный результат. Проверьте принадлежность ресурса, язык и контактные сведения вместе с самой доступностью.
Фоновая задача должна хранить достаточно контекста, чтобы повторить генерацию позже. Текущий браузерный URL в этот момент уже не существует. Передавайте разрешённый ключ сайта и выбирайте конфигурацию на сервере. Не позволяйте входным данным произвольно задавать внутренний путь или внешний адрес ресурса без проверки, иначе генератор получит ненужные возможности доступа.
При изменении основного домена убедитесь, что старые документы и новые генерации ведут себя по согласованным правилам. Абсолютная ссылка в шаблоне может остаться прежней, а сеть позже перестанет её обслуживать. Для сопровождаемости полезно отделить идентичность ресурса от способа доставки. Конкретная реализация зависит от выбранной библиотеки и системы хранения.
Проверить кэш и отправляемое вложение
После исправления создайте новый файл штатным способом и проверьте его содержимое. Старый PDF может храниться под тем же именем, а почтовая задача брать его из кэша. Сверьте время, контрольную сумму или безопасный идентификатор версии локально. Сам факт обновлённого предпросмотра в админке не доказывает, что адресату отправляется тот же файл.
Для учебной отправки используйте разрешённый тестовый канал и синтетические данные. Откройте полученное вложение, проверьте логотип, конфигурацию, число страниц и читаемость. Если нет доступа к почтовому каналу, отметьте эту часть как непроверенную и сохраните готовый локальный PDF. Не отправляйте сообщения реальным клиентам ради получения скриншота.
Проверьте повторную генерацию после изменения конфигурации. Документ не должен сохранять старые модули или случайно возвращать прежний логотип. Область кэширования должна учитывать существенные входные данные. Удаление всех файлов генерации без понимания ключа может временно помочь, но не гарантирует корректность следующего документа.
Собрать минимальный набор проверок
| Условие | Что наблюдать |
|---|---|
| Браузерная страница | Источник и принадлежность логотипа |
| Генерация без личной сессии | Ресурс доступен разрешённым способом |
| Печатный режим | Элемент не скрыт и имеет размеры |
| Медленный ресурс | Ограниченное ожидание и понятный отказ |
| Два сайта | Каждый получает свой знак |
| Почтовое вложение | Совпадает с проверенным новым файлом |
Для регрессии используйте минимальный документ с логотипом и короткой таблицей, затем полноценный учебный шаблон. Первый быстро проверяет доступность и формат, второй выявляет геометрию и печатные ограничения. Не заменяйте финальную приёмку минимальным примером: он не содержит условий, в которых изображение могло скрываться в настоящем документе.
В рабочей заметке оставьте подтверждённую причину, способ доставки ресурса, режим рендеринга и проверенный путь до вложения. Секреты, реальные контакты и закрытые файлы в публичный пакет не входят. Если причина не установлена, сохраните результаты проверок по слоям, а не одну предполагаемую формулировку «не работал путь».
Задача завершена, когда правильный ресурс виден в новом документе, соответствует нужному сайту и сохраняется в фактическом вложении. Появление любой картинки в локальном предпросмотре недостаточно. Проверка всей цепочки помогает не перепутать исправление шаблона с обновлением кэша или случайным успехом в среде, отличающейся от рабочей генерации.
Связанный разбор: Разработка интернет-магазина с конфигуратором товара.
Документация и источники
- MDN: URL constructor: Разрешение относительного адреса относительно базового URL
- Playwright: Page.pdf: Пример зависимости PDF-вывода от печатного режима; не утверждение о генераторе исходного проекта