Files
MikrotikManager/backend/src/services/traffic-flow-ripe.test.ts
T

160 lines
5.1 KiB
TypeScript

import assert from "node:assert/strict"
import {
disableRipeEnqueueForTests,
disableRipePersistForTests,
enqueueRipeMisses,
flushRipeQueueForTests,
lookupRipeCached,
resetRipeCacheForTests,
ripeFetchCountForTests,
ripeLastCandidateCountForTests,
seedRipeCacheForTests,
setRipeFetchForTests,
pauseRipeBackgroundWork,
resumeRipeBackgroundWork,
} from "./traffic-flow-ripe.js"
disableRipePersistForTests()
resetRipeCacheForTests()
disableRipeEnqueueForTests()
assert.equal(lookupRipeCached("10.1.1.8")?.ok, false)
assert.equal(lookupRipeCached("192.168.0.1")?.ok, false)
assert.equal(lookupRipeCached("100.64.1.2")?.ok, false)
assert.equal(ripeFetchCountForTests(), 0)
seedRipeCacheForTests({
prefix: "1.2.3.0/24",
asn: 64500,
country: "NL",
lat: 52.3,
lng: 4.9,
holder: "TEST",
ok: true,
fetchedAt: Date.now(),
})
assert.equal(lookupRipeCached("1.2.3.10")?.country, "NL")
assert.equal(lookupRipeCached("1.2.3.10")?.asn, 64500)
assert.equal(ripeFetchCountForTests(), 0)
resetRipeCacheForTests()
disableRipePersistForTests()
setRipeFetchForTests(async (input) => {
const url = String(input)
const body = url.includes("network-info")
? { data: { prefix: "8.8.8.0/24", asns: ["15169"] } }
: url.includes("maxmind-geo-lite")
? { data: { located_resources: [{ locations: [{ country: "US", latitude: 37.4, longitude: -122.1 }] }] } }
: { data: { holder: "GOOGLE" } }
return new Response(JSON.stringify(body), { status: 200, headers: { "Content-Type": "application/json" } })
})
enqueueRipeMisses(["8.8.8.8"])
await flushRipeQueueForTests()
assert.equal(lookupRipeCached("8.8.8.8")?.country, "US")
assert.equal(lookupRipeCached("8.8.8.10")?.prefix, "8.8.8.0/24")
const afterFirst = ripeFetchCountForTests()
assert.ok(afterFirst >= 2)
enqueueRipeMisses(["8.8.8.10"])
await flushRipeQueueForTests()
assert.equal(ripeFetchCountForTests(), afterFirst)
seedRipeCacheForTests({ prefix: "198.18.0.0/15", asn: 64500, country: "NL", lat: 52, lng: 4, holder: "STALE", ok: true, fetchedAt: Date.now() })
for (const ip of ["198.18.139.1", "198.19.255.255", "192.0.2.1", "198.51.100.1", "203.0.113.1", "240.0.0.1"]) {
assert.equal(lookupRipeCached(ip)?.ok, false, "Special ranges must bypass stale public cache")
}
enqueueRipeMisses(["198.18.139.1", "198.19.255.255", "192.0.2.1", "198.51.100.1", "203.0.113.1", "240.0.0.1"])
await flushRipeQueueForTests()
assert.equal(ripeFetchCountForTests(), afterFirst, "Special ranges must never query RIPE")
resetRipeCacheForTests()
disableRipePersistForTests()
setRipeFetchForTests(async () => {
throw new Error("timeout")
})
enqueueRipeMisses(["8.9.8.50"])
await flushRipeQueueForTests()
const neg = lookupRipeCached("8.9.8.50")
assert.equal(neg?.ok, false)
const afterNeg = ripeFetchCountForTests()
assert.ok(afterNeg > 0, "Upstream failure test must actually query a public address")
enqueueRipeMisses(["8.9.8.50"])
await flushRipeQueueForTests()
assert.equal(ripeFetchCountForTests(), afterNeg)
resetRipeCacheForTests()
disableRipePersistForTests()
seedRipeCacheForTests({
prefix: "1.1.1.0/24",
asn: 13335,
country: "?",
lat: null,
lng: null,
holder: "CLOUDFLARENET, US",
ok: true,
fetchedAt: Date.now(),
})
assert.equal(lookupRipeCached("1.1.1.1")?.country, "US")
assert.ok(lookupRipeCached("1.1.1.1")?.country !== "?")
resetRipeCacheForTests()
disableRipePersistForTests()
setRipeFetchForTests(async (input) => {
const url = String(input)
const body = url.includes("network-info")
? { data: { prefix: "1.0.0.0/24", asns: ["13335"] } }
: url.includes("maxmind-geo-lite")
? { data: { located_resources: [{ locations: [{ country: "?" }] }] } }
: { data: { holder: "CLOUDFLARENET, US" } }
return new Response(JSON.stringify(body), { status: 200, headers: { "Content-Type": "application/json" } })
})
enqueueRipeMisses(["1.0.0.1"])
await flushRipeQueueForTests()
assert.equal(lookupRipeCached("1.0.0.1")?.country, "US")
assert.equal(lookupRipeCached("1.0.0.1")?.asn, 13335)
resetRipeCacheForTests()
disableRipePersistForTests()
for (let i = 0; i < 3000; i++) {
const o2 = Math.floor(i / 256)
const o3 = i % 256
seedRipeCacheForTests({
prefix: `203.${o2}.${o3}.0/24`,
asn: 64500,
country: "NL",
lat: null,
lng: null,
holder: "NOISE",
ok: true,
fetchedAt: Date.now(),
})
}
seedRipeCacheForTests({
prefix: "8.8.8.0/24",
asn: 15169,
country: "US",
lat: null,
lng: null,
holder: "GOOGLE",
ok: true,
fetchedAt: Date.now(),
})
assert.equal(lookupRipeCached("8.8.8.8")?.asn, 15169)
assert.ok(
ripeLastCandidateCountForTests() < 8,
`index should not scan all prefixes, got ${ripeLastCandidateCountForTests()}`,
)
resetRipeCacheForTests()
disableRipePersistForTests()
setRipeFetchForTests(async () => new Response(JSON.stringify({ data: {} }), { status: 200 }))
await pauseRipeBackgroundWork()
enqueueRipeMisses(["8.8.4.4"])
await flushRipeQueueForTests()
assert.equal(ripeFetchCountForTests(), 0)
resumeRipeBackgroundWork()
enqueueRipeMisses(["8.8.4.4"])
await flushRipeQueueForTests()
assert.ok(ripeFetchCountForTests() > 0)
console.log("traffic-flow-ripe.test.ts: ok (including database pause/resume)")