fix(ci-fallout): repoint the in-container docker test, two windows-only tests and the desktop exe-integrity patches to the defining modules; name bot_relay turn timeout/attempts as constants so the Desktop mirror test reads them instead of counting subprocess.run sites
This commit is contained in:
@@ -31,14 +31,15 @@ describe('bot_relay.deliver budget mirrors', () => {
|
||||
})
|
||||
|
||||
it('mirrors the backend per-attempt turn timeout', () => {
|
||||
const attemptTimeouts = [...relayHandler.matchAll(/timeout=(\d+)/g)].map(m => Number(m[1]))
|
||||
// The backend names both numbers explicitly (methods_bot_relay.py) so the mirror is a
|
||||
// constant-to-constant check, not a count of textual subprocess.run(...) call sites.
|
||||
const attemptTimeout = relayHandler.match(/^TURN_ATTEMPT_TIMEOUT_SECONDS\s*=\s*(\d+)/m)
|
||||
const maxAttempts = relayHandler.match(/^TURN_MAX_ATTEMPTS\s*=\s*(\d+)/m)
|
||||
|
||||
expect(attemptTimeouts.length, 'expected the attempt and its policy-gated retry').toBeGreaterThanOrEqual(2)
|
||||
// Every attempt shares one bound; if they ever diverge, the mirror below is
|
||||
// no longer a faithful ceiling and this must be revisited deliberately.
|
||||
expect(new Set(attemptTimeouts).size, `attempt timeouts diverged: ${attemptTimeouts}`).toBe(1)
|
||||
expect(tsConstant('RELAY_TURN_ATTEMPT_MS')).toBe(attemptTimeouts[0] * 1000)
|
||||
expect(tsConstant('RELAY_TURN_MAX_ATTEMPTS')).toBe(attemptTimeouts.length)
|
||||
expect(attemptTimeout, 'TURN_ATTEMPT_TIMEOUT_SECONDS must exist in methods_bot_relay.py').toBeTruthy()
|
||||
expect(maxAttempts, 'TURN_MAX_ATTEMPTS must exist in methods_bot_relay.py').toBeTruthy()
|
||||
expect(tsConstant('RELAY_TURN_ATTEMPT_MS')).toBe(Number(attemptTimeout![1]) * 1000)
|
||||
expect(tsConstant('RELAY_TURN_MAX_ATTEMPTS')).toBe(Number(maxAttempts![1]))
|
||||
})
|
||||
|
||||
it('keeps the client deadline strictly greater than the backend ceiling', () => {
|
||||
|
||||
@@ -58,7 +58,7 @@ def test_prebuilt_bundle_present_and_no_runtime_install(built_image: str) -> Non
|
||||
py = (
|
||||
"import json\n"
|
||||
"from pathlib import Path\n"
|
||||
"from hermes_cli.main import _tui_need_npm_install, _find_bundled_tui, _make_tui_argv\n"
|
||||
"from hermes_cli.main_tui_launch import _tui_need_npm_install, _find_bundled_tui, _make_tui_argv\n"
|
||||
"ui = Path('/opt/hermes/ui-tui')\n"
|
||||
"argv, cwd = _make_tui_argv(ui, tui_dev=False)\n"
|
||||
"out = {\n"
|
||||
|
||||
@@ -310,16 +310,16 @@ def test_build_only_fails_when_pack_produces_corrupt_exe(tmp_path, monkeypatch,
|
||||
make_pe(staging / "win-unpacked" / "Hermes.exe", PE_AMD64, truncate_to=0x300)
|
||||
return subprocess.CompletedProcess(list(cmd), 0)
|
||||
|
||||
with patch("hermes_cli.main.shutil.which", return_value="/usr/bin/npm"), \
|
||||
patch("hermes_cli.main._resolve_node_runtime_npm", return_value="npm.cmd"), \
|
||||
patch("hermes_cli.main._run_npm_install_deterministic", return_value=install_ok), \
|
||||
patch("hermes_cli.main._desktop_build_needed", return_value=True), \
|
||||
with patch("hermes_cli.main_desktop.shutil.which", return_value="/usr/bin/npm"), \
|
||||
patch("hermes_cli.main_install_repair._resolve_node_runtime_npm", return_value="npm.cmd"), \
|
||||
patch("hermes_cli.main_web_build._run_npm_install_deterministic", return_value=install_ok), \
|
||||
patch("hermes_cli.main_desktop._desktop_build_needed", return_value=True), \
|
||||
patch("hermes_cli.main_desktop._stop_desktop_processes_locking_build", return_value=[]), \
|
||||
patch("hermes_cli.main_desktop._purge_electron_build_cache", return_value=[]), \
|
||||
patch("hermes_cli.main_desktop._desktop_stamp_path", return_value=tmp_path / "stamp.json"), \
|
||||
patch("hermes_cli.main_desktop._write_desktop_build_stamp") as mock_stamp, \
|
||||
patch("hermes_cli.main_desktop._windows_native_machine", return_value="AMD64"), \
|
||||
patch("hermes_cli.main.subprocess.run", side_effect=pack_into_staging), \
|
||||
patch("hermes_cli.main_desktop.subprocess.run", side_effect=pack_into_staging), \
|
||||
pytest.raises(SystemExit) as exc:
|
||||
cli_main.cmd_gui(_ns())
|
||||
|
||||
|
||||
@@ -764,7 +764,7 @@ class TestGitBashPathNormalization:
|
||||
``windows_only``: the function's whole job is producing native
|
||||
Windows paths, which is only meaningful where ``os.sep`` is ``\\``.
|
||||
"""
|
||||
import cli as cli_mod
|
||||
from hermes_cli import worktree_ops as cli_mod
|
||||
assert cli_mod._normalize_git_bash_path("/c/Users/foo") == r"C:\Users\foo"
|
||||
assert cli_mod._normalize_git_bash_path("/C/Users/foo") == r"C:\Users\foo"
|
||||
assert cli_mod._normalize_git_bash_path("/cygdrive/d/data") == r"D:\data"
|
||||
|
||||
@@ -22,11 +22,18 @@ def _relay_root() -> Path:
|
||||
return home.parent.parent if home.parent.name == "profiles" else home
|
||||
|
||||
|
||||
# Per-attempt turn timeout and attempt ceiling for bot_relay.deliver. The Desktop client mirrors
|
||||
# both (apps/desktop/src/plugins/hermes-bots/relay.ts: RELAY_TURN_ATTEMPT_MS / RELAY_TURN_MAX_ATTEMPTS)
|
||||
# and its relay-deliver-budget test reads these two lines, so a change here must be deliberate (#93911).
|
||||
TURN_ATTEMPT_TIMEOUT_SECONDS = 600
|
||||
TURN_MAX_ATTEMPTS = 2 # first attempt + the policy-gated re-run
|
||||
|
||||
|
||||
def _run_delivery(profile: str, tmp: str) -> subprocess.CompletedProcess:
|
||||
from tools.bot_relay import local_delivery_command
|
||||
return subprocess.run(
|
||||
local_delivery_command(profile, tmp), capture_output=True, text=True, encoding="utf-8",
|
||||
errors="replace", timeout=600)
|
||||
errors="replace", timeout=TURN_ATTEMPT_TIMEOUT_SECONDS)
|
||||
|
||||
|
||||
@method("bot_relay.roster.sync")
|
||||
|
||||
Reference in New Issue
Block a user