Watch-IP

Watch-IP vs IPinfo

IPinfo and Watch-IP both offer a batch endpoint for resolving many supplied IPs in one call, with different batch limits, response shapes, and pricing. The facts below were checked directly against IPinfo's own site; neither table declares an overall winner.

IPinfo facts on this page were checked directly against the pages listed under Sources on 2026-09-08 and can change without notice — re-check the vendor's own site before relying on a specific number. Watch-IP facts come from this repository's own code and current /pricing page. Report anything that looks stale via /contact.

What this page compares

This page compares server-side, supplied-IP lookup — IPinfo's Core API and batch endpoint against Watch-IP's GET /v1/lookup/{ip} and POST /v1/lookup (secret key, third-party geolocation database). It does not compare Watch-IP's separate browser visitor-geolocation product (GET /v1/geo, publishable key, origin-locked), which has no equivalent in this comparison.

Feature comparison

Watch-IPIPinfo
AuthenticationSecret key via Authorization: Bearer header.Token via a ?token= query parameter.IPinfo batch enrichment API docs · 2026-09-08
Free tierNone for lookup. Plans start at $19/month for 5,000 lookups. (Watch-IP's separate visitor-geolocation product has its own free tier for browser use, not arbitrary-IP lookup.)IPinfo Lite: $0/month, described as unlimited requests, country-level geolocation only, plus 50 web-dashboard lookups.IPinfo pricing · 2026-09-08
Entry paid tier$19/month, 5,000 lookups/month, 20 requests/minute.IPinfo Core: $26/month, 150,000 requests/month; per-tier rate limit not itemized on the pricing page.IPinfo pricing · 2026-09-08
Batch size per callUp to 100 IPs per POST /v1/lookup call.Up to 1,000 IPs per POST /batch call.IPinfo batch enrichment API docs · 2026-09-08
Batch response shapeA "results" array, in the same order the "ips" array was submitted.A JSON object keyed by IP address; response ordering isn't documented as preserved.IPinfo batch enrichment API docs · 2026-09-08
Response fields (single lookup)ip, country, region (subdivision name via GeoNames), regionCode, city, postalCode (via a compiled GeoNames index, where covered), latitude, longitude, continent, timezone (computed from coordinates), isEUCountry, asn, asOrganization, currency, callingCode, compliance, locale, sun, holiday, age, tax, found; userAgent/hostname/security optional.Core tier: city, region, region_code, country, country_code, continent, continent_code, latitude, longitude, timezone, postal_code; ASN/organization fields are documented separately for higher tiers.IPinfo Core API geolocation data · 2026-09-08

Migrating from IPinfo

A runnable version of every step below is in examples/migrate-from-ipinfo.mjs in the Watch-IP GitHub repository — it makes both requests and prints both responses so you can diff them yourself.

1. Swap the batch request

The token moves from a query parameter to an Authorization header, and the request body changes from a bare array to an object with an "ips" key.

IPinfo

curl -X POST "https://api.ipinfo.io/batch?token=$IPINFO_TOKEN" \
  -H "Content-Type: application/json" \
  -d '["203.0.113.1", "2001:db8::1"]'

Watch-IP

curl https://api.watch-ip.com/v1/lookup \
  -H "Authorization: Bearer YOUR_SECRET_KEY" \
  -H "Content-Type: application/json" \
  -d '{"ips": ["203.0.113.1", "2001:db8::1"]}'

2. Rebuild an IP-keyed map if your code expects one

IPinfo's batch response is an object you index by IP directly. Watch-IP returns an ordered array instead — zip it against the request's "ips" array to get the same lookup-by-IP shape your existing code may expect.

Reading an IPinfo response

const city = data["203.0.113.1"].city;

Reading a Watch-IP response

const map = Object.fromEntries(ips.map((ip, i) => [ip, results[i]]));
const city = map["203.0.113.1"].city;

3. Split larger batches

A job batching close to IPinfo's 1,000-IP limit needs to be split into multiple sequential calls against Watch-IP's 100-IP limit — plan for roughly 10x as many requests for the same total volume.

One IPinfo call

await fromIpinfoBatch(thousandIps);

Multiple Watch-IP calls

for (let i = 0; i < ips.length; i += 100) {
  await fromWatchIpBatch(ips.slice(i, i + 100));
}

See examples/migrate-from-ipinfo.mjs in the Watch-IP monorepo on GitHub for the runnable version of this migration.

Frequently asked questions

Why is Watch-IP's batch limit smaller than IPinfo's?

IPinfo documents a 1,000-IP limit per batch call; Watch-IP's is 100. If you regularly batch more than 100 IPs per job, plan for multiple sequential POST /v1/lookup calls rather than one large one.

Does Watch-IP have a free tier like IPinfo Lite?

No, as of 2026-09-08. IPinfo Lite offers unlimited country-level requests free; Watch-IP's IP lookup product has no free tier. Watch-IP's separate visitor-geolocation product has its own free tier for browser use, which is a different product and key type from arbitrary-IP lookup.

Is the order of results preserved in a batch response?

Watch-IP's POST /v1/lookup always returns its "results" array in the same order the "ips" array was submitted. IPinfo's batch response is a JSON object keyed by IP rather than an ordered array, so code reading either response needs to be written for that response's actual shape, not assumed to be interchangeable.

Sources

Related pages