diff --git a/.gitignore b/.gitignore index 77132f8..6cd8af8 100644 --- a/.gitignore +++ b/.gitignore @@ -30,8 +30,13 @@ ASTERION_VR/ # Server-side secrets — never commit (config.example.php sert de template) server/api/config.php +# Le contenu de server/builds/ est ignoré (gros ZIPs / launcher.exe), mais on +# garde le code (.htaccess, gate.php, .gitkeep) sous version. server/builds/* !server/builds/.gitkeep +!server/builds/.htaccess +!server/builds/gate.php +!server/builds/launcher/.gitkeep # Plans .claude/ diff --git a/server/admin/launcher.php b/server/admin/launcher.php index a93e8b6..8c9a234 100644 --- a/server/admin/launcher.php +++ b/server/admin/launcher.php @@ -70,8 +70,10 @@ if ($_SERVER['REQUEST_METHOD'] === 'POST') { elseif ($action === 'sync_launcher') { require_once "$root/tools/SignManifest.php"; $signer = new \PSLauncher\Tools\SignManifest($root); - $result = $signer->run('launcher'); - $message = "Sortie du script (scope: launcher) :\n" . implode("\n", $result['log']); + $force = !empty($_POST['force']); + $result = $signer->run('launcher', $force); + $forceLabel = $force ? ' [FORCE: cache ignoré]' : ''; + $message = "Sortie du script (scope: launcher{$forceLabel}) :\n" . implode("\n", $result['log']); if (!$result['ok']) $messageType = 'error'; } } catch (Exception $e) { @@ -159,6 +161,9 @@ Layout::header('Launcher', 'launcher'); = Layout::csrfField() ?> + diff --git a/server/admin/versions.php b/server/admin/versions.php index 13abe4a..f31318b 100644 --- a/server/admin/versions.php +++ b/server/admin/versions.php @@ -136,11 +136,56 @@ if ($_SERVER['REQUEST_METHOD'] === 'POST') { require_once "$root/tools/SignManifest.php"; $signer = new \PSLauncher\Tools\SignManifest($root); $scope = $action === 'sync_versions' ? 'versions' : 'all'; - $result = $signer->run($scope); + $force = !empty($_POST['force']); + $result = $signer->run($scope, $force); $label = $scope === 'versions' ? 'versions Proserve' : 'manifest complet'; - $message = "Sortie du script (scope: {$label}) :\n" . implode("\n", $result['log']); + $forceLabel = $force ? ' [FORCE: cache ignoré]' : ' [cache utilisé pour les ZIPs inchangés]'; + $message = "Sortie du script (scope: {$label}{$forceLabel}) :\n" . implode("\n", $result['log']); if (!$result['ok']) $messageType = 'error'; } + elseif ($action === 'sync_one') { + $version = $_POST['version'] ?? ''; + if ($version === '') throw new Exception("Version manquante"); + require_once "$root/tools/SignManifest.php"; + $signer = new \PSLauncher\Tools\SignManifest($root); + $force = !empty($_POST['force']); + $result = $signer->run('versions', $force, $version); + $forceLabel = $force ? ' [FORCE]' : ''; + $message = "Hash de v{$version}{$forceLabel} :\n" . implode("\n", $result['log']); + if (!$result['ok']) $messageType = 'error'; + } + elseif ($action === 'set_skip_hash') { + $version = $_POST['version'] ?? ''; + $skipHash = !empty($_POST['skip']); + foreach ($manifest['versions'] as &$v) { + if ($v['version'] === $version) { + if ($skipHash) { + $v['download']['hashAlgorithm'] = 'none'; + $v['download']['sha256'] = ''; + } else { + unset($v['download']['hashAlgorithm']); + if (empty($v['download']['sha256'])) { + $v['download']['sha256'] = 'REPLACE_AFTER_BUILD'; + } + } + break; + } + } + unset($v); + saveManifest($manifestPath, $manifest); + + // Re-signature auto pour garder le manifest valide après le changement. + // En mode skip, on n'a rien à hasher : on appelle run() qui se contentera + // de détecter hashAlgorithm=none et re-signera. Pas de calcul lourd. + require_once "$root/tools/SignManifest.php"; + $signer = new \PSLauncher\Tools\SignManifest($root); + $resign = $signer->run('versions', false); + $message = ($skipHash + ? "Vérif SHA-256 désactivée pour v{$version} et manifest re-signé." + : "Vérif SHA-256 réactivée pour v{$version}. Clique « 🔁 Hash » sur cette ligne pour calculer le SHA-256.") + . "\n" . implode("\n", $resign['log']); + if (!$resign['ok']) $messageType = 'error'; + } } catch (Exception $e) { $message = $e->getMessage(); $messageType = 'error'; @@ -221,6 +266,9 @@ Layout::header('Versions', 'versions'); = Layout::csrfField() ?> + @@ -238,9 +286,10 @@ Layout::header('Versions', 'versions');
= substr($v['download']['sha256'], 0, 12) ?>…
à calculer
@@ -273,6 +324,47 @@ Layout::header('Versions', 'versions');
+
+ La vérif SHA-256 est désactivée pour cette release.
+ Le manifest sert hashAlgorithm: "none". La sécurité repose
+ uniquement sur la signature Ed25519 du manifest + HTTPS.
+
+ Désactive la vérif SHA-256 chez les clients pour cette release
+ (utile sur très gros builds où on accepte le compromis perf/sécurité).
+
+