SKILL.md
Apollo Performance Tuning
Overview
Optimize Apollo.io API performance through response caching, connection pooling, bulk operations, parallel fetching, and result slimming. Key insight: search is free but slow (~500ms), enrichment costs credits — cache aggressively and batch enrichment calls.
Prerequisites
- Valid Apollo API key
- Node.js 18+
Instructions
Step 1: Connection Pooling
Reuse TCP connections to avoid TLS handshake overhead on every request.
// src/apollo/optimized-client.ts
import axios from 'axios';
import https from 'https';
const httpsAgent = new https.Agent({
keepAlive: true,
maxSockets: 10,
maxFreeSockets: 5,
timeout: 30_000,
});
export const optimizedClient = axios.create({
baseURL: 'https://api.apollo.io/api/v1',
headers: { 'Content-Type': 'application/json', 'x-api-key': process.env.APOLLO_API_KEY! },
httpsAgent,
timeout: 15_000,
});
Step 2: Response Caching with Per-Endpoint TTLs
// src/apollo/cache.ts
import { LRUCache } from 'lru-cache';
// Different TTLs based on data volatility
const CACHE_TTLS: Record<string, number> = {
'/organizations/enrich': 24 * 60 * 60 * 1000, // 24h — company data rarely changes
'/people/match': 4 * 60 * 60 * 1000, // 4h — contact data changes occasionally
'/mixed_people/api_search': 15 * 60 * 1000, // 15min — search results are dynamic
'/mixed_companies/search': 30 * 60 * 1000, // 30min — company search
'/contact_stages': 60 * 60 * 1000, // 1h — stages rarely change
};
const cache = new LRUCache<string, { data: any; at: number }>({
max: 5000,
maxSize: 50 * 1024 * 1024,
sizeCalculation: (v) => JSON.stringify(v).length,
});
function cacheKey(endpoint: string, params: any): string {
return `${endpoint}:${JSON.stringify(params)}`;
}
export async function cachedRequest<T>(
endpoint: string,
requestFn: () => Promise<T>,
params: any,
): Promise<T> {
const key = cacheKey(endpoint, params);
const ttl = CACHE_TTLS[endpoint] ?? 15 * 60 * 1000;
const cached = cache.get(key);
if (cached && Date.now() - cached.at < ttl) return cached.data;
const data = await requestFn();
cache.set(key, { data, at: Date.now() });
return data;
}
export function getCacheStats() {
return { entries: cache.size, sizeBytes: cache.calculatedSize };
}
