geoip2-golang
Unofficial Go reader for MaxMind GeoIP2 and GeoLite2 databases, exposing typed City, Country, ASN, ISP, and Enterprise IP lookups over a fast memory-mapped mmdb decoder.
Repository Health
Technical Analysis
geoip2-golang is a Go client for reading MaxMind’s GeoIP2 and GeoLite2 binary database files (.mmdb format). It wraps the lower-level maxminddb-golang reader with a typed, database-aware API: callers open a database once and then call the method matching its type (City, Country, ASN, ISP, Domain, ConnectionType, AnonymousIP, AnonymousPlus, or Enterprise) with a netip.Addr, getting back a fully typed struct with localized place names, coordinates, ASN/ISP metadata, or anonymizer signals depending on which MaxMind product is loaded.
Version 2 is a deliberate rewrite around Go’s modern netip.Addr type and generated (rather than reflection-based) decoders, cutting allocations by 56% and memory use by 34% versus v1 while keeping the same per-database-type method calls. Every result struct exposes a HasData() check so callers can distinguish “no data for this IP” from a decode error, and the library validates the loaded database’s declared type before running a lookup, returning a descriptive InvalidMethodError instead of silently returning zero values.
What You Get
- A single Reader type opened via Open() (file path) or OpenBytes() (in-memory), memory-mapping the .mmdb file for fast repeated lookups
- One typed method per MaxMind database (City, Country, ASN, ISP, Domain, ConnectionType, AnonymousIP, AnonymousPlus, Enterprise) that refuses to run against the wrong database type
- Fully typed result structs with localized Names (en, de, es, fr, ja, pt-BR, ru, zh-CN), HasData()/HasCoordinates() predicates, and populated Network/IPAddress fields on every result
- Generated (non-reflection) decoders for the model structs, checked in and regenerated via go generate against the maxminddb-golang code generator
- A documented MIGRATION.md covering every v1-to-v2 breaking change, plus GoDoc examples for every supported database type
Common Use Cases
- Enriching web server access logs or analytics events with visitor city/country before they’re written downstream
- Blocking or flagging requests from anonymizing VPNs, proxies, or Tor exit nodes using the AnonymousIP/AnonymousPlus databases
- Attributing traffic to an ISP or autonomous system for abuse detection, fraud scoring, or network-quality routing decisions
- Geo-based content localization or feature gating in a Go backend without an external geolocation API call per request
Under The Hood
Architecture
The library is a thin, single-package (geoip2) typed facade over maxminddb-golang/v2’s memory-mapped reader. reader.go defines a Reader struct holding the underlying mmdbReader plus a databaseType bitmask (built with iota-based flags) computed once at Open/OpenBytes time from the mmdb file’s declared Metadata.DatabaseType string. Each public lookup method (City, Country, ASN, Enterprise, ISP, Domain, ConnectionType, AnonymousIP, AnonymousPlus) first checks its own bit against that mask — returning a typed InvalidMethodError if the database doesn’t support it — then delegates to mmdbReader.Lookup(ip).Decode(&result) and back-fills Network/IPAddress on the decoded struct from the lookup result. There is no internal layering or DI: the model types in models.go are pure data with a handful of convenience predicates (HasData, HasCoordinates), and a custom Date type implements mmdbdata.Unmarshaler/json.Marshaler for MaxMind’s ISO-8601 date fields. Swapping the core decode strategy (reflection vs. generated) required no changes to this public surface, which is the intended seam.
Tech Stack
A Go 1.25 module (github.com/oschwald/geoip2-golang/v2) with a single runtime dependency, github.com/oschwald/maxminddb-golang/v2 (same author), which supplies the actual mmdb file format decoder and memory-mapping. Tests depend on stretchr/testify. The module declares maxminddb-golang/v2/maxminddb-gen as a Go 1.24-style tool dependency, invoked via a //go:generate directive in models.go to regenerate models_maxminddb.go’s hand-off-free decoders; CI (golangci-lint with default: all linters, tuned via .golangci.yml) and a GitHub Actions Go workflow plus CodeQL scanning gate every change, including a check that generated files are current.
Code Quality
reader_test.go carries 14 test functions plus a table-driven generated_test.go pair asserting the generated decoders match the reflection path bit-for-bit; reflection_benchmark_test.go benchmarks the two decode strategies against each other, and example_test.go supplies compiler-checked GoDoc examples for every database type. Errors are explicit and typed (InvalidMethodError, UnknownDatabaseTypeError) rather than sentinel strings or panics, both implementing error with a descriptive message naming the offending method and database type. Naming and struct tags (json + maxminddb on every field) are consistent throughout, and the golangci-lint config opts into nearly every available linter rather than a minimal subset.
API Design
Getting a result takes three calls: Open, netip.ParseAddr, and the matching typed method — no configuration object or builder required, though functional Option values are supported for advanced maxminddb tuning. Every returned record exposes HasData() so callers don’t need to hand-check zero values, and coordinate access goes through HasCoordinates() rather than nil-checking two pointer fields directly. Failure modes are self-describing (calling ISP() on a City database names both the method and the database type in the error) instead of returning an ambiguous empty struct. A package-level GoDoc comment doubles as a runnable quick-start, and MIGRATION.md documents every v1→v2 signature and field change for upgraders.
Used by 3 apps in this directory
Authgear
Authentication
Open-source, self-hostable authentication platform with passkeys, biometric login, SSO, MFA, and GraphQL admin API — a full Auth0/Clerk/Firebase alternative for SaaS and mobile apps.
Cosmos-Server
Security · Authentication
All-in-one self-hosted home server with SmartShield anti-DDoS, Nebula mesh VPN, automatic HTTPS, and a 250-app marketplace — all secured behind a unified auth layer.
highlight.io
Developer Tools · Analytics · Monitoring
Open-source full-stack monitoring that unifies session replay, error tracking, logging, and distributed tracing so you can stop context-switching between tools.