#php #pdf.js
#php #pdf.js
Вопрос:
Я создаю частный веб-сайт, чтобы поделиться некоторыми старыми семейными письмами со своими родственниками. Чтобы предотвратить обход писем, я использую функцию smartReadFile (показана ниже) для потоковой передачи писем в браузер. (Я дам семье пароль для входа на сайт.) Письма представляют собой PDF-файлы, созданные с помощью сканера.
Я нахожу, что некоторые буквы всегда отображаются просто отлично, некоторые отображаются с перерывами, а некоторые вообще не отображаются. Все они прекрасно открываются с помощью Acrobat reader. Когда письмо не отображается, я вижу это сообщение в консоли (Firefox) :
Invalid or corrupted PDF file. PDF.js v2.11.298 (build: d370a281c) Message: Invalid PDF structure.
Я тестировал как Firefox (94.0.2), так и Chrome (96.0.4664.45), и хотя в любой момент времени данная буква может вести себя по-разному в одном или другом, я вижу одну и ту же основную проблему в обоих. (Просто пошел и тоже протестировал с Edge. Та же проблема.)
На данный момент все это локально для моей машины разработки под управлением Windows 10 v. 21H1. Установленным веб-сервером является IIS.
Вот функция, которую я не писал. (Получил его от моего сына, который изначально получил его от кого-то другого.)
function smartReadFile($location, $filename, $mimeType = 'application/octet-stream') { if (!file_exists($location)) { header ("HTTP/1.1 404 Not Found"); return; } $size = filesize($location); $time = date('r', filemtime($location)); $fm = @fopen($location, 'rb'); if (!$fm) { header ("HTTP/1.1 505 Internal server error"); return; } $begin = 0; $end = $size - 1; if (isset($_SERVER['HTTP_RANGE'])) { if (preg_match('/bytes=h*(d )-(d*)[D.*]?/i', $_SERVER['HTTP_RANGE'], $matches)) { $begin = intval($matches[1]); if (!empty($matches[2])) { $end = intval($matches[2]); } } } if (isset($_SERVER['HTTP_RANGE'])) { header('HTTP/1.1 206 Partial Content'); } else { header('HTTP/1.1 200 OK'); } header("Content-Type: $mimeType"); header('Cache-Control: public, must-revalidate, max-age=0'); header('Pragma: no-cache'); header('Accept-Ranges: bytes'); header('Content-Length:' . (($end - $begin) 1)); if (isset($_SERVER['HTTP_RANGE'])) { header("Content-Range: bytes $begin-$end/$size"); } if($_REQUEST['SaveAs'] == "1"){ header('Content-Disposition: attachment; filename=' . $filename); }else{ header("Content-Disposition: inline; filename="$filename""); } header("Content-Transfer-Encoding: binary"); header("Last-Modified: $time"); $cur = $begin; fseek($fm, $begin, 0); while(!feof($fm) amp;amp; $cur lt;= $end amp;amp; (connection_status() == 0)) { print fread($fm, min(1024 * 16, ($end - $cur) 1)); $cur = 1024 * 16; } }
Мой инстинкт подсказывает, что речь идет о размере файла, таймауте или чем-то в этом роде, но я не знаю, как это исправить. Я попытался уменьшить размер фрагментов, которые я читаю и передаю (изменив множитель ближе к концу функции с 16 на 4 или 2), но безуспешно.
Комментарии:
1. Спасибо. Я этого не показывал, но вызов smartReadFile передает «приложение/PDF» как тип $mimeType. Хорошая идея проверить файлы с помощью другого считывателя. Я также подумывал о том, чтобы попытаться каким-то образом уменьшить их, потому что некоторые из них довольно большие.
2. Спасибо за совет по поводу PDF-файлов. Мое намерение состояло в том, чтобы обменять некоторое разрешение на размер (как я сделал много лет назад, когда использовал SnagIt, чтобы уменьшить размер сотен семейных фотографий, которые я сканировал с высоким разрешением). Однако я пришел к выводу, что проблема заключается в конфигурации моего локального веб-сервера, а не в файлах.
Ответ №1:
По совету моего сына я попробовал упрощенную версию на производственном веб-сервере (а не на моей локальной установке), и проблема исчезла. Поэтому я сведу это к некоторым настройкам в моей установке IIS, которые мне не нужно выяснять, и перейду к завершению этого проекта.