denyAccessUnlessGranted('ROLE_ADMIN'); if (!$this->isCsrfTokenValid('system', $request->request->getString('_csrf_token'))) { return $this->back('Deine Sitzung ist abgelaufen. Bitte melde dich erneut an.'); } @set_time_limit(0); try { $file = $this->packages->export($request->request->getBoolean('benutzer')); } catch (InvalidPage $e) { return $this->back($e->getMessage()); } $response = new BinaryFileResponse($file, headers: ['Content-Type' => 'application/zip', 'X-Content-Type-Options' => 'nosniff', 'Cache-Control' => 'no-store']); $response->setContentDisposition(ResponseHeaderBag::DISPOSITION_ATTACHMENT, basename($file)); // Ein Export ist zum Mitnehmen da, nicht zum Liegenlassen: er enthält alle Inhalte. $response->deleteFileAfterSend(); return $response; } #[Route('/%kant.admin_path%/system/paket/import', name: 'admin_package_import', methods: ['POST'])] public function import(Request $request): Response { $this->denyAccessUnlessGranted('ROLE_ADMIN'); if (!$this->isCsrfTokenValid('system', $request->request->getString('_csrf_token'))) { return $this->back('Deine Sitzung ist abgelaufen. Bitte melde dich erneut an.'); } if (!$request->request->getBoolean('bestaetigt')) { return $this->back('Bitte bestätige, dass die Inhalte dieser Website ersetzt werden.'); } $upload = $request->files->get('paket'); $waiting = basename($request->request->getString('wartend')); $temporary = null; if ($upload instanceof UploadedFile) { if (!$upload->isValid()) { return $this->back(\in_array($upload->getError(), [\UPLOAD_ERR_INI_SIZE, \UPLOAD_ERR_FORM_SIZE], true) ? 'Das Paket ist größer, als das Hosting für einen Upload erlaubt. Bitte per FTP nach var/pakete/ legen – dann erscheint es hier zur Auswahl.' : 'Das Hochladen ist gescheitert. Bitte erneut versuchen oder das Paket per FTP nach var/pakete/ legen.'); } $temporary = $this->packages->directory().'/hochgeladen-'.bin2hex(random_bytes(6)).'.zip'; @mkdir($this->packages->directory(), 0o775, true); $upload->move(\dirname($temporary), basename($temporary)); $file = $temporary; } elseif ('' !== $waiting && str_ends_with($waiting, '.zip') && is_file($this->packages->directory().'/'.$waiting)) { $file = $this->packages->directory().'/'.$waiting; } else { return $this->back('Bitte ein Paket hochladen oder eines aus var/pakete/ wählen.'); } @set_time_limit(0); try { $result = $this->packages->import($file, $request->request->getBoolean('benutzer')); } finally { if (null !== $temporary) { @unlink($temporary); } } // Das Ergebnis direkt, nicht über eine Weiterleitung: wurden die Konten ersetzt, gilt die // Anmeldung ab der nächsten Anfrage nicht mehr. // Schriften liegen nicht im Paket, sondern auf dem Server dieser Website (public/assets/fonts). // Fehlt eine, die die neue Gestaltung verlangt, sagt die Ergebnisseite, wo man sie holt. $missing = $result['ok'] ? $this->fonts->missing($this->theme->load()) : []; return $this->render('admin/package-result.html.twig', ['result' => $result, 'fontsMissing' => $missing]); } private function back(string $message): Response { $this->addFlash('error', $message); return $this->redirectToRoute('admin_system'); } }