/** * isitup.org Simulator * * Mimics the isitup.org JSON API: * GET /api.json?url= * * status_code values match the real API: * 1 = site is up * 2 = site is down (connection failed / non-2xx/3xx) * 3 = bad URL (malformed) * * The simulator is deployed on internet-external and probes the target * from that network position — so it exercises the same public-facing * path a real external prober would. */ const PORT = Number(process.env.PORT) || 8080; interface ProbeResponse { domain: string; port: number; status_code: 1 | 2 | 3; response_ip: string; response_code: number; response_time: number; } async function probe(targetUrl: string): Promise { let parsed: URL; const withScheme = targetUrl.includes('://') ? targetUrl : `https://${targetUrl}`; try { parsed = new URL(withScheme); } catch { return { domain: targetUrl, port: 443, status_code: 3, response_ip: '', response_code: 0, response_time: 0, }; } const port = parsed.port ? Number(parsed.port) : parsed.protocol === 'https:' ? 443 : 80; const start = Date.now(); try { const response = await fetch(withScheme, { signal: AbortSignal.timeout(10_000), redirect: 'follow', }); const responseTime = (Date.now() - start) / 1000; // Real isitup treats 2xx/3xx as up. Anything else (or unreachable) is down. const isUp = response.status >= 200 && response.status < 400; console.log(`[isitup] ${withScheme} → HTTP ${response.status} in ${responseTime.toFixed(2)}s`); return { domain: parsed.hostname, port, status_code: isUp ? 1 : 2, response_ip: '', response_code: response.status, response_time: responseTime, }; } catch (error) { const message = error instanceof Error ? error.message : String(error); console.log(`[isitup] ${withScheme} → probe error: ${message}`); return { domain: parsed.hostname, port, status_code: 2, response_ip: '', response_code: 0, response_time: (Date.now() - start) / 1000, }; } } const server = Bun.serve({ port: PORT, async fetch(req) { const url = new URL(req.url); if (url.pathname === '/api.json') { const target = url.searchParams.get('url'); if (!target) { return Response.json({ domain: '', port: 443, status_code: 3, response_ip: '', response_code: 0, response_time: 0, }); } const result = await probe(target); console.log(`[isitup] ${target} → ${result.status_code} (${result.response_code})`); return Response.json(result); } if (url.pathname === '/' || url.pathname === '/health') { return Response.json({ ok: true, service: 'isitup.org simulator' }); } return new Response('Not Found', { status: 404 }); }, }); console.log(`[isitup] simulator listening on port ${server.port}`);