Help us improve
Share bugs, ideas, or general feedback.
From acc
Generates PHP 8.4 idempotency handler: PSR-15 middleware with Redis deduplication, IdempotencyKey value object, storage interface, exceptions, and unit tests for safe API retries.
npx claudepluginhub dykyi-roman/awesome-claude-code --plugin accHow this skill is triggered — by the user, by Claude, or both
Slash command
/acc:create-idempotency-handlerThe summary Claude sees in its skill listing — used to decide when to auto-load this skill
Creates idempotency handling infrastructure for safe request deduplication.
Generates PHP 8.4 idempotent consumer components for message deduplication, including IdempotencyKey, Database/Redis stores, middleware, and unit tests.
Implements idempotency for API endpoints and message consumers to safely handle retries without duplicate side effects.
Provides patterns for designing idempotent APIs with keys to handle retries safely, prevent duplicates, and ensure at-most-once semantics in payments/orders.
Share bugs, ideas, or general feedback.
Creates idempotency handling infrastructure for safe request deduplication.
| Scenario | Example |
|---|---|
| Payment processing | Prevent duplicate charges on retry |
| Order creation | Avoid duplicate orders from network retries |
| Webhook handling | Deduplicate incoming webhook deliveries |
| API mutations | Ensure POST/PUT/PATCH safety on retry |
Idempotency-Key HTTP headerexists(), store(), get(), remove()Path: src/Infrastructure/Idempotency/
IdempotencyKey.php — Value Object with UUID validationIdempotencyException.php — Duplicate request exceptionStoredResponse.php — Serializable response wrapperPath: src/Infrastructure/Idempotency/
IdempotencyStorageInterface.php — Storage contractRedisIdempotencyStorage.php — Redis SETNX + TTL implementationPath: src/Infrastructure/Idempotency/
IdempotencyMiddleware.php — PSR-15 middlewareIdempotencyKeyTest.php — Value Object validation testsIdempotencyMiddlewareTest.php — Middleware behavior tests| Component | Path |
|---|---|
| All Classes | src/Infrastructure/Idempotency/ |
| Unit Tests | tests/Unit/Infrastructure/Idempotency/ |
| Component | Pattern | Example |
|---|---|---|
| Value Object | IdempotencyKey | IdempotencyKey |
| Storage Interface | IdempotencyStorageInterface | IdempotencyStorageInterface |
| Redis Storage | RedisIdempotencyStorage | RedisIdempotencyStorage |
| Middleware | IdempotencyMiddleware | IdempotencyMiddleware |
| Response VO | StoredResponse | StoredResponse |
| Exception | IdempotencyException | IdempotencyException |
| Test | {ClassName}Test | IdempotencyKeyTest |
final readonly class IdempotencyKey
{
public function __construct(public string $value)
{
// Validates UUID v4 format
}
public static function fromHeader(string $headerValue): self;
public function toString(): string;
}
interface IdempotencyStorageInterface
{
public function exists(IdempotencyKey $key): bool;
public function store(IdempotencyKey $key, StoredResponse $response, int $ttl): void;
public function get(IdempotencyKey $key): ?StoredResponse;
public function remove(IdempotencyKey $key): void;
}
final readonly class IdempotencyMiddleware implements MiddlewareInterface
{
public function process(
ServerRequestInterface $request,
RequestHandlerInterface $handler
): ResponseInterface;
}
$middleware = new IdempotencyMiddleware(
storage: $redisStorage,
ttl: 86400,
headerName: 'Idempotency-Key'
);
// Client sends: POST /orders with header Idempotency-Key: 550e8400-e29b-41d4-a716-446655440000
// First request: processes and stores response
// Retry request: returns cached response immediately
Request ──→ Extract Idempotency-Key header
│
Key exists in storage?
│ │
YES NO
│ │
Return stored Process request
response │
Store response
│
Return response
| Anti-pattern | Problem | Solution |
|---|---|---|
| No TTL on keys | Storage grows unbounded | Set TTL (e.g., 24h) |
| In-memory storage | Lost on restart, no clustering | Use Redis or database |
| Idempotency on GET | GET is already idempotent | Only apply to mutations |
| Missing key validation | Accept invalid keys | Validate UUID format |
| No response caching | Cannot replay response | Store full response |
| Race conditions | Concurrent duplicates | Use SETNX atomic operation |
For complete PHP templates and examples, see:
references/templates.md — IdempotencyKey, StorageInterface, RedisStorage, Middleware templatesreferences/examples.md — API integration examples and tests