问题
Is there anyway that I can get the location of my device through python. Currently I am having to use selenium and open up a browser, use a location service website and setting the result of that to variables for lat/long.
But is there an easier way to do this?
UPDATE: I am using a 3G dongle on my RaspberryPi, so looking for a way to get the specific lat/long of it - I can successfully do this through web service, just wondering if there is a quicker way built into python for these requests?
回答1:
Update: This API endpoint is deprecated and will stop working on July 1st, 2018. For more information please visit: https://github.com/apilayer/freegeoip#readme"
Assumptions:
The device for which location is being sought is the one running the Python You have Internet access (seems fair since you mention a location service website)
In such a case, there are services similar to the one linked in the comment where the IP of the request is used to generate the location. For example, http://freegeoip.net/.
import requests
import json
send_url = 'http://freegeoip.net/json'
r = requests.get(send_url)
j = json.loads(r.text)
lat = j['latitude']
lon = j['longitude']
Drawbacks
Only IP is used to generate location.
回答2:
or, as simple as this
import geocoder
g = geocoder.ip('me')
print(g.latlng)
回答3:
Others have mentioned a few services, but another one to consider is my own, https://ipinfo.io, which'll give you latitude, longitude and a bunch of other information:
Usage for Bash:
$ curl ipinfo.io
{
"ip": "24.6.61.239",
"hostname": "c-24-6-61-239.hsd1.ca.comcast.net",
"city": "Mountain View",
"region": "California",
"country": "US",
"loc": "37.3845,-122.0881",
"org": "AS7922 Comcast Cable Communications, LLC",
"postal": "94040"
}
If you only want the coordinate data you can get just that by requesting /loc
:
$ curl ipinfo.io/loc
37.3845,-122.0881
See https://ipinfo.io/developers for more details.
回答4:
Since http://freegeoip.net/json
API endpoint is deprecated and will stop working on July 1st, 2018. So, they release new API http://api.ipstack.com
.
So, you may try out this with new API:
import requests
import json
send_url = "http://api.ipstack.com/check?access_key=YOUR_ACCESS_KEY"
geo_req = requests.get(send_url)
geo_json = json.loads(geo_req.text)
latitude = geo_json['latitude']
longitude = geo_json['longitude']
city = geo_json['city']
In order to get your own ACCESS_KEY
, you have to first create an account on ipstack.com
which is free at https://ipstack.com/signup/free.
Along with latitude
, longitude
and city
; you can also fetch zip
, continent_code
, continent_name
, country_code
, country_name
, region_code
, region_name
.
Limitation: Free account only allow you 10,000 requests/month. If you requirement is more then you can upgrade you account.
For more information about this new API you can visit at https://github.com/apilayer/freegeoip
Reference: @JishnuM answer
回答5:
Here's a Python Geocoding Module that has GeoFreeIP
Example: http://geocoder.readthedocs.io/
$ pip install geocoder
Using CLI
$ geocode '99.240.181.199' --provider freegeoip --pretty --json
Using Python
>>> import geocoder
>>> g = geocoder.freegeoip('99.240.181.199')
<[OK] Freegeoip - Geocode [Ottawa, Ontario Canada]>
>>> g.json
回答6:
been playing around with this, so thanks to all for the useful answers in this thread (and SO in general!) thought I'd share my short program in case anyone wants to see it in combination with great circle calc
import geocoder
import requests
freegeoip = "http://freegeoip.net/json"
geo_r = requests.get(freegeoip)
geo_json = geo_r.json()
address=input('enter an address: ')
g= geocoder.google(address)
lat_ad=g.latlng[0]
lon_ad=g.latlng[1]
user_postition = [geo_json["latitude"], geo_json["longitude"]]
lat_ip=user_postition[0]
lon_ip=user_postition[1]
#Calculate the great circle distance between two points on the earth (specified in decimal degrees)
from math import radians, cos, sin, asin, sqrt
# convert decimal degrees to radians
lon_ad, lat_ad, lon_ip, lat_ip = map(radians, [lon_ad, lat_ad, lon_ip, lat_ip])
# haversine formula
dlon = lon_ip - lon_ad
dlat = lat_ip - lat_ad
a = sin(dlat/2)**2 + cos(lat_ad) * cos(lat_ip) * sin(dlon/2)**2
c = 2 * asin(sqrt(a))
km = 6367 * c
#end of calculation
#limit decimals
km = ('%.0f'%km)
print(address+' is about '+str(km)+' km away from you')
回答7:
With the ipdata.co API
This answer uses a 'test' API Key that is very limited and only meant for testing a few calls. Signup for your own Free API Key and get up to 1500 requests daily for development.
import requests
r = requests.get('https://api.ipdata.co?api-key=test').json()
r['country_name']
# United States
回答8:
Ipregistry returns location data along with currency, time zone, and more for your current IP address or the given one (disclaimer, I run the service). There also exists an official Python client available on PyPI:
$ pip install ipregistry
from ipregistry import IpregistryClient
client = IpregistryClient("tryout")
ipInfo = client.lookup()
print(ipInfo)
回答9:
@JishnuM answered the questions marvelously.
2 cents from me. You don't really need to import json library.
You can go as follows:
freegeoip = "http://freegeoip.net/json"
geo_r = requests.get(freegeoip)
geo_json = geo_r.json()
user_postition = [geo_json["latitude"], geo_json["longitude"]]
print(user_postition)
回答10:
Location based on IP address gives only location for your server. To find location based on where your current location is, you would need to give the browser access to location. This can be done using selenium.
from selenium import webdriver
from selenium.webdriver.chrome.options import Options
from selenium.webdriver.support.ui import WebDriverWait
def getLocation():
chrome_options = Options()
chrome_options.add_argument("--use-fake-ui-for-media-stream")
timeout = 20
driver = webdriver.Chrome(chrome_options=chrome_options)
driver.get("https://mycurrentlocation.net/")
wait = WebDriverWait(driver, timeout)
longitude = driver.find_elements_by_xpath('//*[@id="longitude"]')
longitude = [x.text for x in longitude]
longitude = str(longitude[0])
latitude = driver.find_elements_by_xpath('//*[@id="latitude"]')
latitude = [x.text for x in latitude]
latitude = str(latitude[0])
driver.quit()
return (latitude,longitude)
print getLocation()
A tutorial on how to do it is here or find the GitHub repo here
回答11:
The freegoip.net and the api.ipstack.com endpoints appear to use the location of the internet service provider (ISP), not the location of my device. I tried curl http://api.ipstack.com/check?access_key=YOUR_KEY, and what I got was
{"ip":"106.51.151.31","type":"ipv4","continent_code":"AS","continent_name":"Asia","country_code":"IN","country_name":"India","region_code":"KA","region_name":"Karnataka","city":"Bengaluru","zip":"560008","latitude":12.9833,"longitude":77.5833,"location":{"geoname_id":1277333,"capital":"New Delhi","languages":[{"code":"hi","name":"Hindi","native":"\u0939\u093f\u0928\u094d\u0926\u0940"},{"code":"en","name":"English","native":"English"}],"country_flag":"http:\/\/assets.ipstack.com\/flags\/in.svg","country_flag_emoji":"\ud83c\uddee\ud83c\uddf3","country_flag_emoji_unicode":"U+1F1EE U+1F1F3","calling_code":"91","is_eu":false}}
Checking the location lat, long on Google maps indicates that this is the location of the service provider, not the location of the server/device.
This solution is still usable, but probably only to a granularity of a city or country, based on how the ISP organises and locates its gateways.
来源:https://stackoverflow.com/questions/24906833/get-your-location-through-python