feat: configurable HANZO_AUTO_BACKGROUND_TIMEOUT env var (default: 30s)

This commit is contained in:
2026-01-05 06:41:08 -08:00
parent 41955bf7cd
commit 86cb5e0eb5
4 changed files with 21 additions and 8 deletions
+1 -1
View File
@@ -4,7 +4,7 @@ build-backend = "setuptools.build_meta"
[project]
name = "hanzo-mcp"
version = "0.10.33"
version = "0.10.34"
description = "The Zen of Hanzo MCP: One server to rule them all. The ultimate MCP that orchestrates all others."
readme = "README.md"
requires-python = ">=3.12"
@@ -26,7 +26,8 @@ Use 'cmd' for:
- Mixed DAG: cmd(["mkdir dist", {"parallel": ["cp a dist/", "cp b dist/"]}, "zip out"])
- Tool invocations: cmd([{"tool": "search", "input": {"pattern": "TODO"}}])
Auto-backgrounding: Commands exceeding 45s automatically background.
Auto-backgrounding: Commands exceeding timeout automatically background.
Configure via: export HANZO_AUTO_BACKGROUND_TIMEOUT=30 (default: 30s)
Use ps --logs <id> to view, ps --kill <id> to stop.
Performance: Uses uvloop on macOS/Linux for 2-4x faster async I/O.
@@ -43,6 +44,7 @@ _using_uvloop = using_uvloop()
from mcp.server import FastMCP
from hanzo_tools.core import BaseTool, ToolRegistry, PermissionManager
from hanzo_tools.shell.base_process import AUTO_BACKGROUND_TIMEOUT
from hanzo_tools.shell.jq_tool import JqTool
from hanzo_tools.shell.ps_tool import PsTool, ps_tool
@@ -2,6 +2,9 @@
All process execution uses asyncio.subprocess for consistency.
All file I/O uses hanzo_async for non-blocking operations with uvloop support.
Auto-backgrounding timeout can be configured via:
export HANZO_AUTO_BACKGROUND_TIMEOUT=30 # seconds (default: 30)
"""
import os
@@ -19,6 +22,11 @@ from hanzo_tools.core import BaseTool, PermissionManager
from hanzo_tools.shell.truncate import truncate_response
# Configurable auto-background timeout (seconds)
# Set via HANZO_AUTO_BACKGROUND_TIMEOUT env var
AUTO_BACKGROUND_TIMEOUT = float(os.getenv("HANZO_AUTO_BACKGROUND_TIMEOUT", "30"))
class ProcessManager:
"""Singleton manager for background processes.
@@ -108,13 +116,15 @@ class ProcessManager:
class AutoBackgroundExecutor:
"""Executor that automatically backgrounds long-running processes.
IMPORTANT: Always backgrounds after MAX_FOREGROUND_TIMEOUT (30s) to keep
IMPORTANT: Always backgrounds after AUTO_BACKGROUND_TIMEOUT to keep
the agent loop responsive. Longer timeouts only affect the background
process lifetime, not the foreground wait time.
Configure via: export HANZO_AUTO_BACKGROUND_TIMEOUT=30
"""
DEFAULT_TIMEOUT = 30.0 # Default timeout for backgrounding
MAX_FOREGROUND_TIMEOUT = 30.0 # ALWAYS background after 30s, even if longer timeout given
DEFAULT_TIMEOUT = AUTO_BACKGROUND_TIMEOUT
MAX_FOREGROUND_TIMEOUT = AUTO_BACKGROUND_TIMEOUT
def __init__(self, process_manager: ProcessManager, timeout: float = DEFAULT_TIMEOUT):
"""Initialize the auto-background executor."""
@@ -463,10 +473,11 @@ class ShellExecutor:
Ensures consistent auto-backgrounding behavior across dag, zsh, shell, bash tools.
Uses a singleton pattern to share process management state.
Auto-backgrounds after 30s to keep agent loop responsive.
Configure via: export HANZO_AUTO_BACKGROUND_TIMEOUT=30
"""
DEFAULT_TIMEOUT = 30.0 # Auto-background after 30 seconds
DEFAULT_TIMEOUT = AUTO_BACKGROUND_TIMEOUT
_instance: Optional["ShellExecutor"] = None
+1 -1
View File
@@ -4,7 +4,7 @@ build-backend = "setuptools.build_meta"
[project]
name = "hanzo-tools-shell"
version = "0.5.4"
version = "0.5.5"
description = "Shell/command execution tools - cmd (unified DAG), zsh, bash, fish, dash, ps, npx, uvx, open, curl, jq, wget"
readme = "README.md"
requires-python = ">=3.12"