Preserve runtime passwords when revalidating launch files

This commit is contained in:
2026-10-08 11:31:26 -04:00
parent f8942c732a
commit 8863e8a882
4 changed files with 76 additions and 10 deletions
+5 -2
View File
@@ -683,6 +683,7 @@ async function processJob(job: Job, eligibility: (job: Job) => string | null) {
if (!current || !['queued','waiting','interrupted'].includes(current.state) || eligibility(job)) return;
let prepared: PreparedNativeLaunch | undefined;
let preparedKey: string | null = null;
let preparedPassword: string | undefined;
try {
if (job.action === 'create' || job.action === 'rebuild') {
if (count(['create','rebuild']) + otherPreparations(job.id) >= fleetSettings().createConcurrency) {
@@ -696,8 +697,9 @@ async function processJob(job: Job, eligibility: (job: Job) => string | null) {
const prior = recipeForDeployment(job.id)!.recipe as NativeRecipe;
deploymentStage(job.id, 'Preparing launch files for the host agent', { phase: 'prepare',
checkpoint: { key: 'startup-queue', label: 'Startup capacity available' } });
preparedPassword = config.rcon.password || randomBytes(32).toString('hex');
prepared = await prepareNativeLaunch({ game: prior.game, mapSlug: prior.mapSlug, native: prior.native,
instance, serverKey: preparedKey, rconPassword: config.rcon.password || randomBytes(32).toString('hex'),
instance, serverKey: preparedKey, rconPassword: preparedPassword,
rebuild: job.action === 'rebuild' && !migration, safetyOverride: overrideSafety });
if (job.action === 'rebuild' && !migration && !await checkOccupancy()) return;
}
@@ -728,8 +730,9 @@ async function processJob(job: Job, eligibility: (job: Job) => string | null) {
}
if (job.action === 'destroy' && count(['destroy']) >= fleetSettings().destroyConcurrency) { hold(job, 'Waiting for destruction capacity.'); return; }
if (prepared) {
// Compare the same runtime config bytes while rechecking current promoted files.
if (getServerKey(job.server) !== preparedKey || !sameLaunchFiles(prepared.recipe,
captureRecipePlan(prepared.recipe.game, prepared.recipe.mapSlug))) {
captureRecipePlan(prepared.recipe.game, prepared.recipe.mapSlug, preparedPassword))) {
hold(job, 'Launch files or credentials changed during preparation; preparing the current selection next pass.'); return;
}
assertReadyLibrary(instance!.host_id, instance!.library_id);