CloakHQ/CloakBrowser · error · InvalidOperationException
GeoIP resolution failed: GeoIP database is unavailable
Error message
GeoIP resolution failed: GeoIP database is unavailable
What it means
An egress IP was discovered, but the resolver could not locate a MaxMind GeoIP database file on disk (dbPath == null), so the city/timezone lookup cannot run. The library ships or downloads this database lazily, and this error means that acquisition/lookup failed. It is an environment/setup problem, not a network-egress one.
Source
Thrown at dotnet/src/CloakBrowser/GeoIp.cs:124
// Exit IP (through proxy, or the machine's own public IP when proxyUrl is
// null/empty) is most accurate - gateway DNS may differ from exit. Resolved
// even when the DB is unavailable: the IP does not need the DB, and dropping
// it on a DB hiccup would let WebRTC fall back to the real IP behind a proxy
// while the connection shows the proxy IP - a real deanonymization.
var ip = await ResolveExitIpAsync(proxyUrl, RemainingSeconds(deadline), ct).ConfigureAwait(false);
// Hostname fallback only applies to a proxy; no proxy -> echo services only.
if (ip == null && !string.IsNullOrEmpty(proxyUrl) && !DeadlineExpired(deadline))
ip = ResolveProxyIp(proxyUrl);
if (ip == null || DeadlineExpired(deadline))
{
if (deadline != null && DeadlineExpired(deadline))
throw new InvalidOperationException($"GeoIP resolution timed out after {timeout:0.0}s");
throw new InvalidOperationException("GeoIP resolution failed: could not discover the egress IP");
}
if (dbPath == null)
throw new InvalidOperationException("GeoIP resolution failed: GeoIP database is unavailable");
try
{
using var reader = new DatabaseReader(dbPath);
var resp = reader.City(ip);
var timezone = resp.Location?.TimeZone;
var country = resp.Country?.IsoCode;
string? locale = country != null && CountryLocaleMap.TryGetValue(country, out var l) ? l : null;
CloakLog.Debug("GeoIP: {0} -> tz={1}, country={2}, locale={3}", ip, timezone, country, locale);
return (timezone, locale, ip);
}
catch (Exception exc)
{
throw new InvalidOperationException($"GeoIP lookup failed for {ip}: {exc.Message}", exc);
}
}
// -----------------------------------------------------------------------View on GitHub (pinned to d6bad5de26)
Solutions
- Ensure outbound access to the GeoIP database source on first run so it can download, then retry.
- Check the cache/data directory for the .mmdb file and restore or re-download it manually.
- Verify the library's data-directory configuration points to a writable, persistent location.
- If GeoIP data is not needed, use the code path that skips GeoIP resolution.
Example fix
// before
var geo = await browser.GeoIp.ResolveProxyGeoAsync(proxyUrl); // throws: db unavailable
// after
if (GeoIp.IsDatabaseAvailable())
var geo = await browser.GeoIp.ResolveProxyGeoAsync(proxyUrl);
else
await GeoIp.EnsureDatabaseAsync(ct); // fetch/reinstall the MaxMind db first Defensive patterns
Strategy: validation
Validate before calling
if (!GeoIp.IsDatabaseAvailable())
await GeoIp.EnsureDatabaseAsync(ct); // download/repair the .mmdb before resolving Try / catch
catch (InvalidOperationException ex) when (ex.Message.Contains("GeoIP database is unavailable"))
{
await GeoIp.EnsureDatabaseAsync(default);
geo = await browser.GeoIp.ResolveProxyGeoAsync(proxyUrl); // retry once
} Prevention
- Pin the GeoIP database in your container/image build.
- Keep the data directory persistent and excluded from cleanup jobs.
- Verify the .mmdb file exists and is non-zero size at startup.
When it happens
Trigger: Calling ResolveProxyGeoAsync / MaybeResolveGeoIpAsync / Collect after egress IP discovery succeeded, when the GeoIP database path lookup returned null — database never downloaded, deleted from the cache directory, moved, or failed to initialize.
Common situations: First run in an offline environment where the MaxMind DB download failed silently; antivirus or cleanup tools deleting the .mmdb cache file; container images built without the GeoIP database; a broken or relocated cache directory after an upgrade.
Related errors
- GeoIP lookup failed for {ip}: {exc.Message}
- GeoIP resolution failed: GeoIP database is unavailable
- GeoIP lookup failed for ${ip}: ${detail}
- GeoIP resolution failed: could not discover the egress IP
- HTTP ${response.status}
AI-assisted analysis of CloakHQ/CloakBrowser@d6bad5de26 (2026-08-28).
Data as JSON: /api/errors/38732ab512554c76.
Report an issue: GitHub.