feat: DNS-free WAN IP detection + add calibre to records

Use Cloudflare 1.1.1.1/cdn-cgi/trace as primary IP source (fixed IP, no resolver dependency — survives AdGuard/upstream DNS outages). Add calibre to DNS_RECORDS: its A record points at the dynamic WAN IP but was not guarded, so it would go stale on the next WAN change.
This commit is contained in:
Eddy de Vink 2026-09-25 10:44:53 +02:00
commit 4f9b2c064e
3 changed files with 15 additions and 8 deletions

View file

@ -43,16 +43,23 @@ async function fetchWithTimeout(url, options = {}, timeout = 15000) {
}
async function getWanIp() {
// Primary source is DNS-free: Cloudflare's 1.1.1.1 serves /cdn-cgi/trace over
// HTTPS on a fixed IP, so detection keeps working when the local resolver
// (AdGuard on this host) is down. The echo services below are fallbacks.
const services = [
'https://ifconfig.me',
'https://api.ipify.org',
'https://icanhazip.com',
{
url: 'https://1.1.1.1/cdn-cgi/trace',
parse: t => (t.split('\n').find(l => l.startsWith('ip=')) || '').split('=')[1],
},
{ url: 'https://ifconfig.me', parse: t => t },
{ url: 'https://api.ipify.org', parse: t => t },
{ url: 'https://icanhazip.com', parse: t => t },
];
for (const url of services) {
for (const { url, parse } of services) {
try {
const resp = await fetchWithTimeout(url, {}, 10000);
if (resp.ok) {
const ip = (await resp.text()).trim();
const ip = (parse(await resp.text()) || '').trim();
if (/^\d{1,3}(\.\d{1,3}){3}$/.test(ip)) {
log(`WAN IP obtained from ${url}: ${ip}`);
return ip;