MaxMind GeoIP2 API
项目描述
描述
安装
要安装geoip2模块,请输入
$ pip install geoip2
如果您无法使用pip,您也可以从源目录使用easy_install
$ easy_install .
数据库读取器扩展
如果您希望使用数据库读取器的C扩展,您必须首先安装libmaxminddb C API。请参阅随附的说明。
IP地理定位使用
IP地理定位本身就不精确。位置通常位于人口中心的附近。不应使用GeoIP2数据库或网络服务提供的任何位置来识别特定的地址或家庭。
网络服务使用
要使用此API,首先构造一个geoip2.webservice.Client
或geoip2.webservice.AsyncClient
,将您的MaxMind account_id
和license_key
传递给构造函数。要使用GeoLite2网络服务而不是GeoIP2网络服务,将可选的host
关键字参数设置为geolite.info
。要使用Sandbox GeoIP2网络服务而不是生产GeoIP2网络服务,将可选的host
关键字参数设置为sandbox.maxmind.com
。
完成此操作后,您可以调用对应请求类型的方法(例如city
或country
),并将您要查询的IP地址传递给它。
如果请求成功,方法调用将返回您调用的端点对应的模型类。该模型随后包含多个记录类,每个类代表网络服务返回的数据的一部分。
如果请求失败,客户端类将抛出一个异常。
同步网络服务示例
>>> import geoip2.webservice
>>>
>>> # This creates a Client object that can be reused across requests.
>>> # Replace "42" with your account ID and "license_key" with your license
>>> # key. Set the "host" keyword argument to "geolite.info" to use the
>>> # GeoLite2 web service instead of the GeoIP2 web service. Set the
>>> # "host" keyword argument to "sandbox.maxmind.com" to use the Sandbox
>>> # GeoIP2 web service instead of the production GeoIP2 web service.
>>> with geoip2.webservice.Client(42, 'license_key') as client:
>>>
>>> # Replace "city" with the method corresponding to the web service
>>> # that you are using, i.e., "country", "city", or "insights". Please
>>> # note that Insights is not supported by the GeoLite2 web service.
>>> response = client.city('203.0.113.0')
>>>
>>> response.country.iso_code
'US'
>>> response.country.name
'United States'
>>> response.country.names['zh-CN']
u'美国'
>>>
>>> response.subdivisions.most_specific.name
'Minnesota'
>>> response.subdivisions.most_specific.iso_code
'MN'
>>>
>>> response.city.name
'Minneapolis'
>>>
>>> response.postal.code
'55455'
>>>
>>> response.location.latitude
44.9733
>>> response.location.longitude
-93.2323
>>>
>>> response.traits.network
IPv4Network('203.0.113.0/32')
异步网络服务示例
>>> import asyncio
>>>
>>> import geoip2.webservice
>>>
>>> async def main():
>>> # This creates an AsyncClient object that can be reused across
>>> # requests on the running event loop. If you are using multiple event
>>> # loops, you must ensure the object is not used on another loop.
>>> #
>>> # Replace "42" with your account ID and "license_key" with your license
>>> # key. Set the "host" keyword argument to "geolite.info" to use the
>>> # GeoLite2 web service instead of the GeoIP2 web service. Set the
>>> # "host" keyword argument to "sandbox.maxmind.com" to use the Sandbox
>>> # GeoIP2 web service instead of the production GeoIP2 web service.
>>> async with geoip2.webservice.AsyncClient(42, 'license_key') as client:
>>>
>>> # Replace "city" with the method corresponding to the web service
>>> # that you are using, i.e., "country", "city", or "insights". Please
>>> # note that Insights is not supported by the GeoLite2 web service.
>>> response = await client.city('203.0.113.0')
>>>
>>> response.country.iso_code
'US'
>>> response.country.name
'United States'
>>> response.country.names['zh-CN']
u'美国'
>>>
>>> response.subdivisions.most_specific.name
'Minnesota'
>>> response.subdivisions.most_specific.iso_code
'MN'
>>>
>>> response.city.name
'Minneapolis'
>>>
>>> response.postal.code
'55455'
>>>
>>> response.location.latitude
44.9733
>>> response.location.longitude
-93.2323
>>>
>>> response.traits.network
IPv4Network('203.0.113.0/32')
>>>
>>> asyncio.run(main())
网络服务客户端异常
有关网络服务本身返回的可能错误的详细信息,请参阅GeoIP2网络服务的文档:https://dev.maxmind.com/geoip/docs/web-services?lang=en
如果网络服务返回显式的错误文档,则根据适当的情况抛出AddressNotFoundError
、AuthenticationError
、InvalidRequestError
或OutOfQueriesError
。这些都是GeoIP2Error
的子类。
如果发生其他类型的错误,则抛出HTTPError
。这发生在出现某种不可预见错误的情况下,例如网络服务返回500或无效的错误文档。如果网络服务返回除200以外的任何状态码,这也将成为一个HTTPError
。
最后,如果网络服务返回200但正文无效,客户端将抛出GeoIP2Error
。
数据库使用
要使用数据库API,首先使用文件路径作为第一个参数构造一个geoip2.database.Reader
。完成此操作后,您可以调用对应数据库类型的方法(例如city
或country
),并将您要查询的IP地址传递给它。
如果查询成功,方法调用将返回您调用的数据库方法对应的模型类。该模型随后包含多个记录类,每个类代表记录的数据的一部分。
如果请求失败,读取器类将抛出一个异常。
数据库示例
城市数据库
>>> import geoip2.database
>>>
>>> # This creates a Reader object. You should use the same object
>>> # across multiple requests as creation of it is expensive.
>>> with geoip2.database.Reader('/path/to/GeoLite2-City.mmdb') as reader:
>>>
>>> # Replace "city" with the method corresponding to the database
>>> # that you are using, e.g., "country".
>>> response = reader.city('203.0.113.0')
>>>
>>> response.country.iso_code
'US'
>>> response.country.name
'United States'
>>> response.country.names['zh-CN']
u'美国'
>>>
>>> response.subdivisions.most_specific.name
'Minnesota'
>>> response.subdivisions.most_specific.iso_code
'MN'
>>>
>>> response.city.name
'Minneapolis'
>>>
>>> response.postal.code
'55455'
>>>
>>> response.location.latitude
44.9733
>>> response.location.longitude
-93.2323
>>>
>>> response.traits.network
IPv4Network('203.0.113.0/24')
匿名IP数据库
>>> import geoip2.database
>>>
>>> # This creates a Reader object. You should use the same object
>>> # across multiple requests as creation of it is expensive.
>>> with geoip2.database.Reader('/path/to/GeoIP2-Anonymous-IP.mmdb') as reader:
>>>
>>> response = reader.anonymous_ip('203.0.113.0')
>>>
>>> response.is_anonymous
True
>>> response.is_anonymous_vpn
False
>>> response.is_hosting_provider
False
>>> response.is_public_proxy
False
>>> response.is_residential_proxy
False
>>> response.is_tor_exit_node
True
>>> response.ip_address
'203.0.113.0'
>>> response.network
IPv4Network('203.0.113.0/24')
ASN数据库
>>> import geoip2.database
>>>
>>> # This creates a Reader object. You should use the same object
>>> # across multiple requests as creation of it is expensive.
>>> with geoip2.database.Reader('/path/to/GeoLite2-ASN.mmdb') as reader:
>>> response = reader.asn('203.0.113.0')
>>> response.autonomous_system_number
1221
>>> response.autonomous_system_organization
'Telstra Pty Ltd'
>>> response.ip_address
'203.0.113.0'
>>> response.network
IPv4Network('203.0.113.0/24')
连接类型数据库
>>> import geoip2.database
>>>
>>> # This creates a Reader object. You should use the same object
>>> # across multiple requests as creation of it is expensive.
>>> with geoip2.database.Reader('/path/to/GeoIP2-Connection-Type.mmdb') as reader:
>>> response = reader.connection_type('203.0.113.0')
>>> response.connection_type
'Corporate'
>>> response.ip_address
'203.0.113.0'
>>> response.network
IPv4Network('203.0.113.0/24')
域名数据库
>>> import geoip2.database
>>>
>>> # This creates a Reader object. You should use the same object
>>> # across multiple requests as creation of it is expensive.
>>> with geoip2.database.Reader('/path/to/GeoIP2-Domain.mmdb') as reader:
>>> response = reader.domain('203.0.113.0')
>>> response.domain
'umn.edu'
>>> response.ip_address
'203.0.113.0'
企业数据库
>>> import geoip2.database
>>>
>>> # This creates a Reader object. You should use the same object
>>> # across multiple requests as creation of it is expensive.
>>> with geoip2.database.Reader('/path/to/GeoIP2-Enterprise.mmdb') as reader:
>>>
>>> # Use the .enterprise method to do a lookup in the Enterprise database
>>> response = reader.enterprise('203.0.113.0')
>>>
>>> response.country.confidence
99
>>> response.country.iso_code
'US'
>>> response.country.name
'United States'
>>> response.country.names['zh-CN']
u'美国'
>>>
>>> response.subdivisions.most_specific.name
'Minnesota'
>>> response.subdivisions.most_specific.iso_code
'MN'
>>> response.subdivisions.most_specific.confidence
77
>>>
>>> response.city.name
'Minneapolis'
>>> response.country.confidence
11
>>>
>>> response.postal.code
'55455'
>>>
>>> response.location.accuracy_radius
50
>>> response.location.latitude
44.9733
>>> response.location.longitude
-93.2323
>>>
>>> response.traits.network
IPv4Network('203.0.113.0/24')
ISP数据库
>>> import geoip2.database
>>>
>>> # This creates a Reader object. You should use the same object
>>> # across multiple requests as creation of it is expensive.
>>> with geoip2.database.Reader('/path/to/GeoIP2-ISP.mmdb') as reader:
>>> response = reader.isp('203.0.113.0')
>>> response.autonomous_system_number
1221
>>> response.autonomous_system_organization
'Telstra Pty Ltd'
>>> response.isp
'Telstra Internet'
>>> response.organization
'Telstra Internet'
>>> response.ip_address
'203.0.113.0'
>>> response.network
IPv4Network('203.0.113.0/24')
数据库读取器异常
如果数据库文件不存在或不可读,构造函数将引发FileNotFoundError
或PermissionError
。如果传递给方法的方法的IP地址无效,将引发ValueError
。如果文件无效或读取器中存在错误,将引发描述问题的maxminddb.InvalidDatabaseError
。如果IP地址不在数据库中,将引发AddressNotFoundError
。
AddressNotFoundError
引用了没有找到地址的最大子网。这可以用来有效地枚举整个子网。
import geoip2.database
import geoip2.errors
import ipaddress
# This creates a Reader object. You should use the same object
# across multiple requests as creation of it is expensive.
with geoip2.database.Reader('/path/to/GeoLite2-ASN.mmdb') as reader:
network = ipaddress.ip_network("192.128.0.0/15")
ip_address = network[0]
while ip_address in network:
try:
response = reader.asn(ip_address)
response_network = response.network
except geoip2.errors.AddressNotFoundError as e:
response = None
response_network = e.network
print(f"{response_network}: {response!r}")
ip_address = response_network[-1] + 1 # move to next subnet
用于数据库或字典键的值
我们强烈建议您不要将任何 ``names`` 属性的值用作数据库或字典中的键。
这些名称可能在版本之间发生变化。我们建议您使用以下之一
geoip2.records.City - city.geoname_id
geoip2.records.Continent - continent.code 或 continent.geoname_id
geoip2.records.Country 和 geoip2.records.RepresentedCountry - country.iso_code 或 country.geoname_id
geoip2.records.subdivision - subdivision.iso_code 或 subdivision.geoname_id
返回哪些数据?
虽然许多模型包含相同的基本记录,但可以在不同的网络服务端点或数据库之间变化可填充的属性。此外,尽管模型可能提供特定数据,但MaxMind并不总是为任何给定的IP地址提供所有数据。
由于这些因素,任何请求都可能返回一个记录,其中一些或所有属性未填充。
始终返回的数据是geoip2.records.Traits记录中的ip_address属性。
与GeoNames集成
GeoNames 提供包含全球地理特征数据(包括人口密集地区)的Web服务和可下载数据库。他们提供免费和付费高级数据。每个特征由一个独特的 geoname_id 标识,它是一个整数。
GeoIP网络服务和数据库返回的许多记录都包括一个 geoname_id 字段。这是GeoNames数据库中地理特征(城市、地区、国家等)的ID。
MaxMind提供的一些数据也来源于GeoNames。我们从GeoNames高级数据集中获取诸如地名、ISO代码和其他类似数据。
报告数据问题
如果您发现的问题是IP地址被错误映射,请向MaxMind提交更正。
如果您发现其他类型的错误,例如拼写错误,请首先检查GeoNames网站。在搜索地点并在GeoNames地图视图中找到它之后,您可以使用多个链接来更正数据(“移动”、“编辑”、“别名”等)。一旦更正是GeoNames数据集的一部分,它将被自动纳入MaxMind未来的版本。
如果您是付费的MaxMind客户并且不确定在哪里提交更正,请联系MaxMind支持以获得帮助。
要求
需要Python 3.8或更高版本。不支持旧版本。
还需要Requests HTTP库。有关详细信息,请参阅 <https://pypi.ac.cn/project/requests/>。
版本控制
GeoIP2 Python API使用语义版本控制。
支持
请使用GitHub问题跟踪器报告此代码的所有问题
如果您遇到的问题不是针对客户端API的特定问题,请联系MaxMind支持以获得帮助。
项目详情
下载文件
下载适合您平台的文件。如果您不确定选择哪个,请了解有关安装包的更多信息。