FetchHook vs. Ngrok: Why AI Agents need Mailboxes, not Tunnels
For a decade, ngrok was the gold standard for receiving webhooks locally. But the rise of ephemeral AI agents and serverless logic has exposed a critical flaw in the 'tunnel' model.
The Primitive: Pulling an event with FetchHook
# No tunnel needed. No live process required.
curl https://api.fetchhook.app/api/v1/stash_abc123 \
-H "X-API-Key: fh_live_xxx"#How do tunnels like ngrok fail AI agents?
Tunnels like ngrok create a synchronous bridge between the public internet and your local machine. For this to work, your local process must be online and listening at the exact moment the webhook hits. If your agent is busy, spinning up, or momentarily offline, the webhook is lost (or requires a complex retry strategy from the provider).
#Why is a 'Mailbox' better than a 'Tunnel'?
FetchHook acts as a persistent mailbox (or stash). When Stripe or GitHub sends a webhook, FetchHook accepts it instantly and stores it in an encrypted buffer. Your agent can then 'pull' that data whenever it is ready.
- Persistence: Events wait for you; you don't wait for events.
- Security: Zero open ports. No exposure to your local network.
- Atomicity: Fetch an event, process it, and it's gone.
#How do I set up a FetchHook stash for Stripe?
Setting up FetchHook takes less than 30 seconds compared to the multi-step configuration of a tunnel:
- Provision: Click 'Get Started' to generate your unique ID.
- Configure: Paste your FetchHook URL (fetchhook.app/in/id) into the Stripe Dashboard.
- Fetch: Use the snippet below in your Python or Node.js agent to process payments.
Python Agent Implementation
import requests
def agent_check_payments():
# Agent pulls from the mailbox on its own schedule
res = requests.get("https://api.fetchhook.app/api/v1/stash_123",
headers={"X-API-Key": "fh_xxx"})
events = res.json()
for event in events:
print(f"Actioning payment: {event['payload']['id']}")Agent Protocol Instruction