export default defineCachedEventHandler(async (event) => { const { flightno } = getQuery(event) if (!flightno || typeof flightno !== 'string') { throw createError({ statusCode: 400, message: 'flightno is required' }) } const code = flightno.replace(/\s/g, '').toUpperCase() const fr24Url = `https://www.flightradar24.com/data/flights/${code.toLowerCase()}` // FR24 live feed const data = await $fetch(`https://data-live.flightradar24.com/zones/fcgi/feed.js`, { query: { flightno: code, faa: 1, satellite: 1, mlat: 1, flarm: 1, adsb: 1, gnd: 1, air: 1, vehicles: 0, estimated: 1, gliders: 0 }, headers: { 'User-Agent': 'Mozilla/5.0 (Macintosh; Intel Mac OS X 10_15_7) AppleWebKit/537.36', 'Accept': 'application/json' } }).catch(() => null) if (!data) return { found: false, fr24Url } // Parse flight entries (skip metadata keys) const flights = Object.entries(data) .filter(([key]) => !['full_count', 'version', 'stats'].includes(key)) .map(([id, val]: [string, any]) => { if (!Array.isArray(val) || val.length < 18) return null return { fr24Id: id, icao24: val[0], lat: val[1], lon: val[2], heading: val[3], altitude: val[4], speed: val[5], squawk: val[6], aircraft: val[8], registration: val[9], timestamp: val[10], origin: val[11], destination: val[12], flightNumber: val[13], onGround: val[14] === 1, verticalSpeed: val[15], callsign: val[16], airline: val[18] } }) .filter((f): f is NonNullable => f != null && (f.lat !== 0 || f.lon !== 0 || f.aircraft != null)) if (flights.length === 0) return { found: false, fr24Url } const flight = flights[0] // Get detail for richer data let detail: any = null if (flight.fr24Id) { detail = await $fetch(`https://data-live.flightradar24.com/clickhandler/`, { query: { version: '1.5', flight: flight.fr24Id }, headers: { 'User-Agent': 'Mozilla/5.0 (Macintosh; Intel Mac OS X 10_15_7) AppleWebKit/537.36' } }).catch(() => null) } // Determine status let status = 'Programado' if (detail?.status?.text) { status = detail.status.text } else if (flight.altitude > 0 && !flight.onGround) { status = 'En vuelo' } else if (flight.onGround && flight.speed > 5) { status = 'En tierra (taxiing)' } else if (flight.onGround) { status = 'En tierra' } return { found: true, fr24Url, flight: { flightNumber: flight.flightNumber || code, callsign: flight.callsign, aircraft: detail?.aircraft?.model?.text || flight.aircraft || null, aircraftCode: flight.aircraft, registration: flight.registration, airline: detail?.airline?.name || flight.airline || null, origin: flight.origin, destination: flight.destination, lat: flight.lat, lon: flight.lon, altitude: flight.altitude, speed: flight.speed, heading: flight.heading, onGround: flight.onGround, verticalSpeed: flight.verticalSpeed, status, departureDelay: detail?.time?.historical?.delay?.departure ?? null, arrivalDelay: detail?.time?.historical?.delay?.arrival ?? null } } }, { maxAge: 60 * 5 }) // Cache 5 min