Was setting up a new agent to crawl some internal APIs and hit the usual headache: how to give it credentials without handing over the keys to the kingdom. Service accounts with long-lived tokens? No thanks. 😬
Stumbled on using **OAuth 2.0 Device Authorization Grant** (RFC 8628) for this. Agent requests a user code, you authorize it once in a browser (with MFA, scopes, the works), and the agent gets a short-lived access token. Token expires, agent's done. Perfect for one-off tasks.
Basic flow the agent initiates:
```http
POST /oauth/device_authorization
Content-Type: application/x-www-form-urlencoded
client_id=your_agent_client&scope=api.read
```
Response:
```json
{
"device_code": "G-xyz",
"user_code": "WDJB-MJHT",
"verification_uri": "https://example.com/device",
"expires_in": 900
}
```
Human visits the URI, enters code, approves. Agent polls for token:
```http
POST /oauth/token
Content-Type: application/x-www-form-urlencoded
grant_type=urn:ietf:params:oauth:grant-type:device_code&device_code=G-xyz&client_id=your_agent_client
```
* Scoped tokens (only what the agent needs)
* No long-term secret storage on the agent side
* Full audit trail of who approved it
Beats a static API key in a config file any day. Still have to trust the initial client auth, but the blast radius is tiny. Found a fun edge case where you can keep polling after expiry if the server doesn't revoke… but that's for another post.
if it moves, fuzz it