Node.js Examples: Complete Integration Guide
Production-ready Node.js and TypeScript code for integrating FetchHook into your applications and agents.
#Basic Fetch (TypeScript)
Fetch webhooks using the native fetch API available in Node.js 18+.
Simple Fetch
typescript
const API_KEY = process.env.FETCHHOOK_API_KEY!;
const SOURCE_ID = process.env.FETCHHOOK_SOURCE_ID!;
interface WebhookEvent {
event_id: string;
provider: string;
event_type?: string;
payload: any;
headers: Record<string, string>;
received_at: string;
}
interface WebhooksResponse {
events: WebhookEvent[];
count: number;
}
async function fetchWebhooks(): Promise<WebhooksResponse> {
const response = await fetch(
`https://api.fetchhook.app/api/v1/${SOURCE_ID}`,
{
headers: {
'Authorization': `Bearer ${API_KEY}`
}
}
);
if (!response.ok) {
throw new Error(`HTTP ${response.status}: ${response.statusText}`);
}
return response.json();
}
const data = await fetchWebhooks();
console.log(`Received ${data.count} webhooks`);
data.events.forEach(event => {
console.log(`Event: ${event.event_id} from ${event.provider}`);
});#Polling Loop with Error Handling
Continuously poll for webhooks with proper error handling and retry logic.
Production Polling
typescript
async function pollWebhooks() {
const POLL_INTERVAL = 5000; // 5 seconds
let retryCount = 0;
const MAX_RETRIES = 3;
while (true) {
try {
const response = await fetch(
`https://api.fetchhook.app/api/v1/${SOURCE_ID}`,
{
headers: { 'Authorization': `Bearer ${API_KEY}` },
signal: AbortSignal.timeout(10000) // 10s timeout
}
);
if (!response.ok) {
throw new Error(`HTTP ${response.status}`);
}
const data: WebhooksResponse = await response.json();
if (data.count > 0) {
for (const event of data.events) {
await processWebhook(event);
}
}
retryCount = 0; // Reset on success
await sleep(POLL_INTERVAL);
} catch (error) {
console.error('Polling error:', error);
retryCount++;
if (retryCount >= MAX_RETRIES) {
console.error('Max retries reached, waiting longer...');
await sleep(POLL_INTERVAL * 5);
retryCount = 0;
} else {
await sleep(POLL_INTERVAL * Math.pow(2, retryCount));
}
}
}
}
function sleep(ms: number): Promise<void> {
return new Promise(resolve => setTimeout(resolve, ms));
}
async function processWebhook(event: WebhookEvent) {
console.log(`Processing ${event.event_id}`);
// Your business logic here
}
pollWebhooks();#Stripe Webhook Integration
Fetch and verify Stripe webhooks with the official Stripe SDK.
Stripe + FetchHook
typescript
import Stripe from 'stripe';
const stripe = new Stripe(process.env.STRIPE_SECRET_KEY!);
const webhookSecret = process.env.STRIPE_WEBHOOK_SECRET!;
async function fetchAndVerifyStripeWebhooks() {
const response = await fetch(
`https://api.fetchhook.app/api/v1/${SOURCE_ID}`,
{
headers: { 'Authorization': `Bearer ${API_KEY}` }
}
);
const data: WebhooksResponse = await response.json();
for (const eventData of data.events) {
if (eventData.provider !== 'stripe') continue;
try {
// Verify Stripe signature
const event = stripe.webhooks.constructEvent(
JSON.stringify(eventData.payload),
eventData.headers['stripe-signature'],
webhookSecret
);
// Handle verified event
switch (event.type) {
case 'payment_intent.succeeded':
const paymentIntent = event.data.object as Stripe.PaymentIntent;
console.log(`Payment succeeded: ${paymentIntent.id}`);
break;
case 'customer.subscription.created':
const subscription = event.data.object as Stripe.Subscription;
console.log(`New subscription: ${subscription.id}`);
break;
}
} catch (err) {
console.error('Stripe verification failed:', err);
}
}
}
fetchAndVerifyStripeWebhooks();#Express.js API Integration
Build an Express API that fetches webhooks on-demand.
Express Endpoint
typescript
import express from 'express';
const app = express();
app.get('/webhooks', async (req, res) => {
try {
const response = await fetch(
`https://api.fetchhook.app/api/v1/${SOURCE_ID}`,
{
headers: { 'Authorization': `Bearer ${API_KEY}` }
}
);
if (!response.ok) {
throw new Error('Failed to fetch webhooks');
}
const data = await response.json();
res.json(data);
} catch (error) {
console.error('Error:', error);
res.status(500).json({ error: 'Failed to fetch webhooks' });
}
});
app.listen(3000, () => {
console.log('Server running on http://localhost:3000');
});Agent Protocol Instruction
For production: Use TypeScript for type safety, implement AbortController for request timeouts, add proper logging (Winston/Pino), use environment variables for configuration, and consider using a job queue (Bull/BullMQ) for webhook processing.
←All Resources
Verified for Agentic Workflowsv1.0.4