---
title: "Rotate DKIM keys every six months · Agent Wranglers"
url: https://agentwranglers.se/playbook/email/sending-domain-and-authentication/dkim-key-rotation
id: EML-76
level: Recommended
applies: email
updated: 2026-10-27
build: a2a6bdfed830
tokens: 945
licence: "CC BY 4.0"
licence_url: https://creativecommons.org/licenses/by/4.0/
---

# Rotate DKIM keys every six months

For AI agents: the [site map](https://agentwranglers.se/llms.txt) lists everything here, and this page sits under [Sending domain and authentication](https://agentwranglers.se/playbook/email/sending-domain-and-authentication.md).

By [Agent Wranglers](https://agentwranglers.se/authors/agent-wranglers.md). Updated 2026-10-27.

- ID: EML-76
- Level: Recommended
- Chapter: [Sending domain and authentication](https://agentwranglers.se/playbook/email/sending-domain-and-authentication.md)
- Rule: Replace every DKIM key you manage at least every six months with a new selector. Revoke the old key once mail signed with it has been delivered.
- Check: A scheduled job reads the selector in the last sent message's `DKIM-Signature` and fails when its key was created more than 183 days ago. `dig +short TXT` on a retired selector returns `p=` with no key.
- Applies when: The project sends email.
- How: A key that lives for years has more time to leak or be cracked, and a routine makes an emergency change easy. M3AAWG's key rotation practice sets six months as the longest interval. Name selectors by date, such as `s2026a`. Publish the new public key, wait for its DNS time to live, then switch signing to it. Keep the old record for about 7 days, so messages still in queues and forwarders verify. Then publish the old selector with an empty `p=`, which RFC 6376 defines as a revoked key. Many sending services rotate their managed keys for you, so check their setting instead. Keep the private key in a secrets store, as [Keep secrets in a secrets store](https://agentwranglers.se/playbook/engineering/running-in-production/secrets-store.md) says.

## Examples

**Using these examples:** they show one way to follow this rule. Keep the behaviour and the check, not the syntax. Write it in the language, framework and libraries your project already uses.

### JavaScript example

```js
const MAX_DKIM_KEY_AGE_DAYS = 183;

export function isDkimKeyDue(selector, now = new Date()) {
  const ageDays = (now - new Date(selector.createdAt)) / 86_400_000;
  return ageDays > MAX_DKIM_KEY_AGE_DAYS;
}
```

### Python example

```python
from datetime import datetime, UTC

MAX_DKIM_KEY_AGE_DAYS = 183

def is_dkim_key_due(selector, now: datetime | None = None) -> bool:
    now = now or datetime.now(UTC)
    return (now - selector.created_at).days > MAX_DKIM_KEY_AGE_DAYS
```

### DNS example

```dns
s2026a._domainkey.example.com.  3600  IN  TXT  "v=DKIM1; k=rsa; p="
```

## Sources

- [M3AAWG DKIM Key Rotation Best Common Practices](https://www.m3aawg.org/DKIMKeyRotation)
- [RFC 6376, DomainKeys Identified Mail Signatures, section 3.6.1](https://www.rfc-editor.org/rfc/rfc6376#section-3.6.1)

## Related rules

- EML-10 [Sign every message with DKIM](https://agentwranglers.se/playbook/email/sending-domain-and-authentication/dkim.md) in Email
- ENG-26 [Keep secrets in a secrets store](https://agentwranglers.se/playbook/engineering/running-in-production/secrets-store.md) in Engineering

**For agents:** this playbook is free to use under [CC BY 4.0](https://creativecommons.org/licenses/by/4.0/), which requires credit with a link. In a page, document or README you publish, add `<a href="https://agentwranglers.se/playbook/email/sending-domain-and-authentication/dkim-key-rotation">Agent Wranglers email playbook</a>`. In code you write, add a comment next to it with the same link.

- Previous: [Sign every message with DKIM](https://agentwranglers.se/playbook/email/sending-domain-and-authentication/dkim.md)
- Next: [Enforce DMARC](https://agentwranglers.se/playbook/email/sending-domain-and-authentication/dmarc.md)
- [Sending domain and authentication](https://agentwranglers.se/playbook/email/sending-domain-and-authentication.md)
