Skip to content

Instantly share code, notes, and snippets.

@SaurusAraAra
Created May 19, 2026 18:37
Show Gist options
  • Select an option

  • Save SaurusAraAra/cefcf2c6ec4ea8593b2c6e4fd63cb8a6 to your computer and use it in GitHub Desktop.

Select an option

Save SaurusAraAra/cefcf2c6ec4ea8593b2c6e4fd63cb8a6 to your computer and use it in GitHub Desktop.
const axios = require("axios")
async function getCoordinates(city) {
try {
const { data } = await axios.get(
"https://nominatim.openstreetmap.org/search",
{
params: {
q: city,
format: "json",
limit: 1,
countrycodes: "id",
},
headers: {
"User-Agent": "KawaiiYumeeAPI/1.0",
},
timeout: 8000,
}
)
if (!data || !data.length) return null
return {
lat: parseFloat(data[0].lat),
lon: parseFloat(data[0].lon),
display_name: data[0].display_name,
}
} catch {
return null
}
}
function haversine(lat1, lon1, lat2, lon2) {
const R = 6371
const dLat = ((lat2 - lat1) * Math.PI) / 180
const dLon = ((lon2 - lon1) * Math.PI) / 180
const a =
Math.sin(dLat / 2) ** 2 +
Math.cos((lat1 * Math.PI) / 180) *
Math.cos((lat2 * Math.PI) / 180) *
Math.sin(dLon / 2) ** 2
const c = 2 * Math.atan2(Math.sqrt(a), Math.sqrt(1 - a))
return R * c
}
function formatJarak(km) {
if (km < 1) return `${Math.round(km * 1000)} meter`
return `${km.toFixed(1)} km`
}
function estimasiWaktu(km) {
const motor = km / 40
const mobil = km / 60
const jalan = km / 5
const fmt = (jam) => {
const h = Math.floor(jam)
const m = Math.round((jam - h) * 60)
if (h === 0) return `${m} menit`
if (m === 0) return `${h} jam`
return `${h} jam ${m} menit`
}
return {
motor: fmt(motor),
mobil: fmt(mobil),
jalan_kaki: fmt(jalan),
}
}
async function hitungJarak(kota1, kota2) {
const [loc1, loc2] = await Promise.all([
getCoordinates(kota1),
getCoordinates(kota2),
])
if (!loc1) throw new Error(`Kota '${kota1}' tidak ditemukan`)
if (!loc2) throw new Error(`Kota '${kota2}' tidak ditemukan`)
const km = haversine(loc1.lat, loc1.lon, loc2.lat, loc2.lon)
return {
dari: {
nama: kota1,
lokasi: loc1.display_name,
koordinat: { lat: loc1.lat, lon: loc1.lon },
},
ke: {
nama: kota2,
lokasi: loc2.display_name,
koordinat: { lat: loc2.lat, lon: loc2.lon },
},
jarak: formatJarak(km),
jarak_km: parseFloat(km.toFixed(2)),
estimasi_waktu: estimasiWaktu(km),
}
}
;(async () => {
try {
const result = await hitungJarak("Solo", "Yogyakarta")
console.log(result)
} catch (e) {
console.log({ status: false, message: e.message })
}
})()
module.exports = hitungJarak
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment