Skip to content

Add configurable idempotency keys for paid requests to prevent accidental double-charging #808

@eater-dimmer

Description

@eater-dimmer

Overview

Clients integrating with x402-protected endpoints may retry requests due to network issues, timeouts, or user actions (e.g., page refresh). Without first-class idempotency support, retries can result in multiple accepted payments for what is logically a single action.

Problem Description

Today, developers must build their own idempotency layer to ensure that retried requests do not incur additional charges. This is error-prone and leads to inconsistent behavior across integrations. A standardized idempotency mechanism would make paid APIs safer and easier to consume.

Expected Behavior

  • Clients can include an idempotency key with a paid request.
  • Replays with the same idempotency key return the original result without re-charging.
  • Idempotency behavior is well-defined and documented.

Steps to Reproduce

  1. Send a paid request to an x402-protected endpoint.
  2. Retry the same request due to a client-side timeout.
  3. Observe that the payment may be processed again without safeguards.

Example code

```ts
fetch("/api/paid-action", {
  headers: {
    "X-402-Payment": "<signed-payment>",
    "Idempotency-Key": "order-123",
  },
});

Proposed Solution

  • Add support for an optional Idempotency-Key header in x402 middleware.
  • Store the mapping of idempotency key → payment result for a configurable TTL.
  • On repeated requests with the same key, return the cached result without re-processing payment.
  • Document idempotency guarantees and limitations.

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions