fix(job): handle SIGTERM and skip static IP for Linux guests

- Install SIGTERM handler that raises KeyboardInterrupt so act_runner
  workflow cancellations trigger the existing VM cleanup path
- Resolve guest_os before the ip_pool block and skip guestinfo IP
  injection for Linux (template doesn't read VMX guestinfo to configure
  network, causing SSH probe to fail against the wrong IP)

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
This commit is contained in:
2026-05-26 01:03:16 +02:00
parent 64f800019d
commit 6d205386dc
+15 -8
View File
@@ -22,6 +22,7 @@ import shutil
import subprocess import subprocess
import sys import sys
import tempfile import tempfile
import signal
import time import time
import uuid import uuid
from datetime import UTC, datetime from datetime import UTC, datetime
@@ -473,6 +474,12 @@ def job(
phase_timings: list[tuple[str, float]] = [] phase_timings: list[tuple[str, float]] = []
phase_start = _now() phase_start = _now()
# SIGTERM (sent by act_runner on workflow cancellation) must trigger cleanup.
def _sigterm(_sig: int, _frame: object) -> None:
raise KeyboardInterrupt()
signal.signal(signal.SIGTERM, _sigterm)
click.echo("=" * 60) click.echo("=" * 60)
click.echo(f"[job] Job : {job_id}") click.echo(f"[job] Job : {job_id}")
click.echo(f"[job] Repository : {repo_url}") click.echo(f"[job] Repository : {repo_url}")
@@ -508,7 +515,14 @@ def job(
) )
_apply_vmx_overrides(clone_vmx, guest_cpu, guest_memory_mb) _apply_vmx_overrides(clone_vmx, guest_cpu, guest_memory_mb)
if config.ip_pool is not None: # Resolve guest OS before IP-pool guard — Linux doesn't read guestinfo IP.
if guest_os.lower() == "auto":
guest_os = _read_guest_os_from_vmx(clone_vmx)
click.echo(f"[job] auto-detected guest OS: {guest_os}")
else:
guest_os = guest_os.lower()
if config.ip_pool is not None and guest_os != "linux":
slot_pool = IpSlotPool( slot_pool = IpSlotPool(
addresses=config.ip_pool.addresses, addresses=config.ip_pool.addresses,
netmask=config.ip_pool.netmask, netmask=config.ip_pool.netmask,
@@ -531,13 +545,6 @@ def job(
except BackendError as exc: except BackendError as exc:
raise click.ClickException(f"vmrun start failed: {exc}") from exc raise click.ClickException(f"vmrun start failed: {exc}") from exc
# Resolve guest OS now that the clone exists.
if guest_os.lower() == "auto":
guest_os = _read_guest_os_from_vmx(clone_vmx)
click.echo(f"[job] auto-detected guest OS: {guest_os}")
else:
guest_os = guest_os.lower()
deadline = _now() + ready_timeout deadline = _now() + ready_timeout
if not _wait_running(backend, handle, deadline, poll_interval): if not _wait_running(backend, handle, deadline, poll_interval):
raise click.ClickException("timeout waiting for VM to be running.") raise click.ClickException("timeout waiting for VM to be running.")