The official Python SDK for the IPWho IP Geolocation API - Get detailed IP geolocation, timezone, connection, and security information with full type safety.
Project description
IPWho (ipwho.org) Python SDK
Official Python client for the IPWho Geolocation API — fetch geolocation, timezone, connection and security information for IP addresses using a lightweight, type-safe SDK.
Installation
Install via pip:
pip install ipwho-ip-geolocation-api
Or install from source:
git clone https://github.com/lavrox/SDK-IPWho-Python.git
cd sdk-ipwho-python
pip install -e .
Quick Start
from src import IPWho
client = IPWho(api_key="your-api-key")
# Get caller's location (uses your IP by default)
import asyncio
location = asyncio.run(client.get_location())
print(location)
# Get location for a specific IP
location = asyncio.run(client.get_location("8.8.8.8"))
print(f"Country: {location.country}")
print(f"City: {location.city}")
Example minimal response (normalized):
{
"continent": "North America",
"continent_code": "NA",
"country": "United States",
"country_code": "US",
"capital": "Washington",
"region": "California",
"region_code": "CA",
"city": "San Francisco",
"latitude": 37.7749,
"longitude": -122.4194,
"postal_code": "94105",
"dial_code": "+1",
"is_in_eu": False
}
API Reference
IPWho Client
The main client class for interacting with the IPWho API.
Constructor
client = IPWho(api_key: str)
- api_key (str): Your IPWho API key. Required.
- Raises:
ValueErrorif API key is empty.
Methods
get_location(ip: Optional[str] = None) -> Optional[GeoLocation]
Get geolocation data for an IP address.
location = await client.get_location("8.8.8.8")
if location:
print(f"Country: {location.country}")
get_timezone(ip: Optional[str] = None) -> Optional[Timezone]
Get timezone data for an IP address.
timezone = await client.get_timezone("8.8.8.8")
if timezone:
print(f"Time Zone: {timezone.time_zone}")
print(f"Offset: {timezone.offset}")
get_connection(ip: Optional[str] = None) -> Optional[Connection]
Get connection/network data for an IP address.
connection = await client.get_connection("8.8.8.8")
if connection:
print(f"ISP: {connection.isp}")
print(f"ASN: {connection.asn_number}")
get_security(ip: Optional[str] = None) -> Optional[Security]
Get security information for an IP address.
security = await client.get_security("8.8.8.8")
if security:
print(f"Is VPN: {security.is_vpn}")
print(f"Is Tor: {security.is_tor}")
get_ip(ip: str) -> IPWhoData
Get complete data for a specific IP address.
data = await client.get_ip("8.8.8.8")
print(f"IP: {data.ip}")
print(f"Country: {data.geo_location.country}")
print(f"ISP: {data.connection.isp}")
get_me() -> IPWhoData
Get complete data for the caller's IP address.
data = await client.get_me()
print(f"Your IP: {data.ip}")
print(f"Your location: {data.geo_location.city}, {data.geo_location.country}")
Type Definitions
GeoLocation
@dataclass
class GeoLocation:
continent: str
continent_code: str
country: str
country_code: str
capital: Optional[str]
region: Optional[str]
region_code: Optional[str]
city: Optional[str]
postal_code: Optional[str]
dial_code: Optional[str]
is_in_eu: Optional[bool]
latitude: Optional[float]
longitude: Optional[float]
accuracy_radius: Optional[int]
Timezone
@dataclass
class Timezone:
time_zone: str
abbr: Optional[str]
offset: Optional[int]
is_dst: Optional[bool]
utc: Optional[str]
current_time: Optional[str]
Connection
@dataclass
class Connection:
asn_number: Optional[int]
asn_org: Optional[str]
isp: Optional[str]
org: Optional[str]
domain: Optional[str]
connection_type: Optional[str]
Security
@dataclass
class Security:
is_vpn: Optional[bool]
is_tor: Optional[bool]
is_threat: Optional[str]
IPWhoData
The main response object containing all available data:
@dataclass
class IPWhoData:
ip: str
geo_location: Optional[GeoLocation]
timezone: Optional[Timezone]
flag: Optional[Flag]
currency: Optional[Currency]
connection: Optional[Connection]
user_agent: Optional[UserAgent]
security: Optional[Security]
Testing
Run the test suite:
pytest tests/
Run tests with coverage:
pytest --cov=src tests/
Troubleshooting
"API Key is required" Error
Make sure you're providing a valid API key:
# ❌ Wrong
client = IPWho("")
# ✅ Correct
client = IPWho("your-api-key")
No data returned
Some fields may be None if they're not available for a given IP:
location = await client.get_location("8.8.8.8")
if location and location.city:
print(f"City: {location.city}")
else:
print("City data not available")
Changelog
v1.0.0 (2026-02-24)
- Initial release
- Support for geolocation, timezone, connection, and security lookups
- Type-safe dataclass definitions
- Comprehensive test suite
- Full parity with TypeScript and PHP SDKs
License
MIT License - see LICENSE file for details.
Support
- Contact: Contact
- GitHub Issues: https://github.com/lavrox/SDK-IPWho-Python/issues
- Documentation: Documentation
Project details
Release history Release notifications | RSS feed
Download files
Download the file for your platform. If you're not sure which to choose, learn more about installing packages.
Source Distribution
Built Distribution
Filter files by name, interpreter, ABI, and platform.
If you're not sure about the file name format, learn more about wheel file names.
Copy a direct link to the current filters
File details
Details for the file ipwho_ip_geolocation_api-1.0.1.tar.gz.
File metadata
- Download URL: ipwho_ip_geolocation_api-1.0.1.tar.gz
- Upload date:
- Size: 9.2 kB
- Tags: Source
- Uploaded using Trusted Publishing? No
- Uploaded via: twine/6.2.0 CPython/3.12.3
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
a2d7da915f2e1761340c8ef16e20543225cc604411e9718fb3936eeb65b2b8c1
|
|
| MD5 |
7dfd9a76a8b077529df0dcfe965ad6eb
|
|
| BLAKE2b-256 |
12b6eb5d8100a9932d4070e66f2abfef605f40b6825e51adf9074f646bce577e
|
File details
Details for the file ipwho_ip_geolocation_api-1.0.1-py3-none-any.whl.
File metadata
- Download URL: ipwho_ip_geolocation_api-1.0.1-py3-none-any.whl
- Upload date:
- Size: 8.2 kB
- Tags: Python 3
- Uploaded using Trusted Publishing? No
- Uploaded via: twine/6.2.0 CPython/3.12.3
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
d1919317f8d1ddaa28c038818a304077a601a7575c04349569caf1cfd5f84fca
|
|
| MD5 |
0fefac8a467503c9bd961faa67701e10
|
|
| BLAKE2b-256 |
9845cfab442fc6272f0723583640ea46d786b4e5663db7f68a70e953a9ce01de
|