Yandex Metrika
sanches.free

Упаковка каталога в ZIP через ZipArchive сохраняя относительные пути без обхода вне корня

Разбор задачи

Открываем архив режим CREATE перебираем файлы RecursiveIteratorIterator и добавляем с префиксом без абсолютных путей.

<?php
declare(strict_types=1);

function packTreeToZip(string $srcDir, string $zipDest): bool {
    if (!class_exists(ZipArchive::class)) { return false; }

    $pack = new ZipArchive();
    if ($pack->open($zipDest, ZipArchive::CREATE | ZipArchive::OVERWRITE) !== true) {
      return false;
    }

    $iterator = new RecursiveIteratorIterator(
      new RecursiveDirectoryIterator($srcDir, FilesystemIterator::SKIP_DOTS),
    );

    foreach ($iterator as $node) {
      /** @var SplFileInfo $node */
      $local = substr($node->getRealPath(), strlen(realpath($srcDir)) + 1);
      $pack->addFile($node->getRealPath(), str_replace('\', '/', $local));
    }

    return $pack->close();
}
?>

В веб-сценариях ограничьте выполнение авторизацией и отдавайте файл через временный symlink с TTL очисткой во tmp чтобы не засорять upload.

Замечания перед выкладкой

Вносите правки только через среду с бэкапом и понятным diff. Если сниппет идёт в шаблон на Битрикс, проверьте конфликт с уже подключённым jQuery/UI и включите «отложенный» запуск там, где длинный главный файл может обрезать DOMContentLoaded.

Не хотите копаться сами?

Починю за 1-3 дня. Без предоплаты — оплата по результату.

15+ лет опыта с 1С-Битрикс · Без предоплаты · 7 дней гарантии