REMOTE AGENT ADAPTER · BOUNDED WAIT

Agno-style remote agent: bound the Java adapter wait

Call an Agno-style remote agent from a Java adapter with a small thread pool and watch hung calls pin threads until a timeout frees them.

Computed experiment · sixty inspection seconds

Your experiment

Twelve requests arrive one per second. Two remote runs hang and request 10 is slow. With two threads and no timeout, watch both threads get pinned and the queue stop moving. Then add a timeout, then remote cancellation, then more threads.

Play replays the computed run over sixty inspection seconds; Next event steps, Restart rewinds, and Inspection time scrubs. Any input change recomputes the run and rewinds it without autoplay.

Event trace

    Computed data

    Final metrics

    Discrete-time model in 50 ms steps, not a client library. The remote agent runs at most three requests at once and queues the rest; a client timeout frees the adapter thread but the remote run continues unless it is cancelled. Latencies are fixed fixture values. Nothing is sent over a network and no Agno or ADK API is called.

    A blocking adapter in front of a remote agent

    A Java service calls a remote Python agent, in the style of an Agno agent behind an HTTP endpoint, through an adapter whose thread pool size is set by Adapter worker threads. Each call holds a thread until the remote answers. Twelve requests arrive one per second; the remote agent runs at most three at once and queues the rest. With the opening settings requests 4 and 8 never answer and request 10 takes six seconds.

    Two hung calls stop everything

    With two threads and Adapter timeout per call at 0, request 4 pins one thread at 3 s and request 8 pins the other at 7.9 s. Requests 1, 2, 3, 5, 6 and 7 are answered; after that both threads stay busy forever and requests 9 to 12 never start. Six of twelve requests are unfinished at 60 s although the remote agent is idle. Set Remote calls that never answer to Request 4 hangs only and eleven are answered; choose None and all twelve are.

    A timeout bounds the damage

    Set the timeout to 5 s. Requests 4 and 8 time out at 8 s and 12.9 s, request 10 times out because six seconds exceeds the limit, and the other nine are answered: zero unfinished. Raising Adapter worker threads to 6 without a timeout is not a fix: ten requests are answered but the two hung calls are still unfinished and two threads are lost for good.

    Timed out is not cancelled

    Cancel the remote run when the adapter times out only applies once a timeout is set. With a 5 s timeout and cancellation off, the two hung runs keep two of the three remote slots after their adapter threads give up, so request 11 waits in the remote queue and finishes at 16.4 s; with cancellation on it finishes at 14.2 s. With four adapter threads the extra concurrency meets the occupied remote slots and four requests time out instead of three; cancellation brings it back to three.

    Reading the run and its limits

    Play, Next event, Restart, Speed and Inspection time replay replies and timeouts over sixty seconds; the chart shows busy threads and requests waiting for a thread, and the table lists when each request got a thread, when it finished and how. This is a deterministic queueing model with fixed latencies; it has no retries, no network errors and no virtual threads, and it does not model Agno or any HTTP client API.

    Views are my own and do not represent any employer, past or present.

    Search