{"record":{"id":"38c5e48076453ab5","repo":"langchain-ai/deepagents","slug":"key-must-be-a-positive-integer","errorCode":null,"errorMessage":"{key} must be a positive integer","messagePattern":"(.+?) must be a positive integer","errorType":"validation","errorClass":"ValueError","httpStatus":null,"severity":"error","filePath":"libs/talon/deepagents_talon/runtime.py","lineNumber":803,"sourceCode":"    \"\"\"Resolve the recursion limit from the environment with a code fallback.\n\n    The `DEEPAGENTS_TALON_RECURSION_LIMIT` env var, when set, overrides the\n    caller-supplied value so operators can tune the graph recursion limit\n    without changing code. Falls back to the caller value when unset.\n    \"\"\"\n    resolved = _positive_int_from_env(env, RECURSION_LIMIT_ENV_KEY)\n    return resolved if resolved is not None else fallback\n\n\ndef _positive_int_from_env(env: Mapping[str, str], key: str) -> int | None:\n    raw = env.get(key)\n    if raw is None or not raw.strip():\n        return None\n    try:\n        value = int(raw)\n    except ValueError as exc:\n        msg = f\"{key} must be a positive integer\"\n        raise ValueError(msg) from exc\n    if value <= 0:\n        msg = f\"{key} must be a positive integer\"\n        raise ValueError(msg)\n    return value\n\n\ndef _has_summarization_tool_middleware(\n    middleware: Sequence[AgentMiddleware[Any, Any, Any]],\n) -> bool:\n    return any(isinstance(item, SummarizationToolMiddleware) for item in middleware)\n\n\ndef _apply_context_size(model: BaseChatModel, context_size: int) -> None:\n    profile = getattr(model, \"profile\", None)\n    merged = (\n        {**profile, \"max_input_tokens\": context_size}\n        if isinstance(profile, dict)\n        else {\"max_input_tokens\": context_size}","sourceCodeStart":785,"sourceCodeEnd":821,"githubUrl":"https://github.com/langchain-ai/deepagents/blob/a1af029e6e73cb17c36bff823d227747b28e91e1/libs/talon/deepagents_talon/runtime.py#L785-L821","documentation":"_positive_int_from_env reads an environment variable (used by _context_size_from_env and _recursion_limit_from_env) and raises this ValueError when its value is not parseable as an int or parses to <= 0. It exists so misconfigured env values fail fast at startup with a clear message naming the offending key.","triggerScenarios":"Setting the relevant env variable (context size or recursion limit) to a non-integer string like \"25.5\", \"default\", \"\", whitespace with junk, or to 0 / a negative integer.","commonSituations":"Docker/compose files quoting values oddly; putting a float where an int is required; secrets manager injecting an unset placeholder like \"${VAR}\"; operators setting 0 expecting 'disabled/unlimited'.","solutions":["Set the env variable to a positive integer string (e.g. `export AGENT_RECURSION_LIMIT=50`)","Remove/unset the variable to fall back to the built-in default","Fix template substitution so placeholders like `${VAR}` are replaced before the process starts"],"exampleFix":"// before\nAGENT_CONTEXT_SIZE=25.5\n// after\nAGENT_CONTEXT_SIZE=128000","handlingStrategy":"validation","validationCode":"import os, re\n\n_INT_RE = re.compile(r\"^[1-9][0-9]*$\")\n\ndef require_positive_env(key: str) -> int | None:\n    raw = os.environ.get(key)\n    if raw is None or not raw.strip():\n        return None\n    if not _INT_RE.match(raw.strip()):\n        raise ValueError(f\"{key} must be a positive integer, got {raw!r}\")\n    return int(raw)\n\nrequire_positive_env(\"AGENT_RECURSION_LIMIT\")\nrequire_positive_env(\"AGENT_CONTEXT_SIZE\")","typeGuard":"def is_positive_int_str(raw: str) -> bool:\n    try:\n        return int(raw) > 0\n    except (TypeError, ValueError):\n        return False","tryCatchPattern":null,"preventionTips":["Validate all agent env vars at process startup, before constructing the runtime","Never store floats or placeholders (${VAR}) in integer env settings","Treat 0 as invalid, not 'unlimited'; unset the var to use defaults"],"tags":["env","configuration","validation"],"backgroundTag":"invalid-env-var","analyzedSha":"a1af029e6e73cb17c36bff823d227747b28e91e1","analyzedAt":"2026-08-29T11:43:24.718Z","schemaVersion":2},"datasetVersion":"2026-08-29T12:17:43.993Z"}