Pace an agent's API calls under a rolling quota

Agent buildMedium25 min

Your task

Your research agent calls a search API that allows at most limit units of work in any window seconds. A plain search costs 1 unit and a batch search costs more. The agent's client queues calls instead of failing them, and sends each one as soon as the quota allows.

Write send_times(calls, limit, window) that returns the second at which each call is sent.

  • calls: a list of [requested_at, cost] in request order. requested_at is a whole second, 0 or more, and never decreases along the list. cost is a whole number of units, at least 1.
  • limit, window: whole numbers, at least 1.
  • Return a list with one send time per call, in the same order.

Rules:

  1. A call is sent no earlier than it was requested, and no earlier than any call before it that was sent.
  2. The calls sent in any span of window seconds cost at most limit units in total. A span that starts at second x holds the calls sent at seconds x through x + window - 1.
  3. Each call is sent at the earliest second that keeps rules 1 and 2, given the send times of the calls before it.
  4. A call that costs more than limit can never be sent. Its send time is -1, and later calls act as if it did not exist.
  5. Any number of calls may go out in the same second.

Examples

send_times(calls: list[list[int]], limit: int, window: int) -> list[int]
Example 1
Inputsend_times([[0, 1], [0, 1], [0, 1], [1, 1], [2, 1]], 3, 10)
Output[0, 0, 0, 10, 10]
Example 2
Inputsend_times([[0, 1], [1, 1], [2, 3]], 3, 5)
Output[0, 1, 6]
Example 3
Inputsend_times([[0, 3], [0, 9], [1, 3]], 5, 4)
Output[0, -1, 4]