I would like to redirect my users to specific location areas in my website, by detecting their location from their IP address.
What would be the best way to achieve this under Django 1.1.1 ?
Thanks
Edit: I want city based locationing on europe.
I would like to redirect my users to specific location areas in my website, by detecting their location from their IP address.
What would be the best way to achieve this under Django 1.1.1 ?
Thanks
Edit: I want city based locationing on europe.
GeoDjango looks like it will suit your needs. I'm not sure exactly how you would want to direct users, but using the GeoIP API, you can do something like:
from django.contrib.gis.utils import GeoIP
g = GeoIP()
ip = request.META.get('REMOTE_ADDR', None)
if ip:
city = g.city(ip)['city']
else:
city = 'Rome' # default city
# proceed with city
The Docs explain things in great detail; I would take a moment to read through them thoroughly.
GeoIP is already mentioned, but I find pygeoip less troublesome to install and no-brainer if you want to embed it in you application instead of installing in Python's site-packages. Still, it works great with free MaxMind databases, e.g GeoLite City one.
Example of use (almost the same as for GeoIP):
>>> import pygeoip
>>> gi = pygeoip.GeoIP(GEOIP_DATABASE, pygeoip.GEOIP_STANDARD)
>>> gi.record_by_addr(ip)
{'country': '...', 'country_code': '...', ...}
This is one solution, from DjangoSnippets; btw, not sure why the code below doesn't use urlparse; but that could be fixed :-)
(Looking at the other answers, it seems you have plenty of options to choose from. This option may not be preferred because it relies on a free 3rd party service.)
from urllib2 import urlopen, Request
import re, socket
from django.conf import settings
domain_re = re.compile('^(http|https):\/\/?([^\/]+)')
domain = domain_re.match(settings.SITE_URL).group(2)
def getUserCountry(ip):
url = "http://api.wipmania.com/" + ip + "?" + domain
socket.setdefaulttimeout(5)
headers = {'Typ':'django','Ver':'1.1.1','Connection':'Close'}
try:
req = Request(url, None, headers)
urlfile = urlopen(req)
land = urlfile.read()
urlfile.close()
return land[:2]
except Exception:
return "XX"
Note from WIPmania: "Using API is free for any purpose, personal or business, if you are making fewer than 10.000 requests per calendar day. A simple yet powerful API allowing you to query the WorldIP database with a single link."
location
of user
in DataBase
? –
Unthinking You could create a view which gets the user's IP and then issues an HTTP redirect which will cause their browser to load the page you want:
def redirect_based_on_ip(request):
ip = request.meta['REMOTE_ADDR']
if ip == SOMETHING:
return HttpResponseRedirect('/something')
elif ip == SOMETHING_ELSE:
return HttpResponseRedirect('/something_else')
# ...
You might find the SubnetTree library for Python helpful if you want to test to see if an IP is in a particular block.
Based on some free services.
it's not fast, but you can add more free services:
settings:
IPCOUNTRY_APYKEY = [
{# free tier 2 querys per second
"url": "http://api.ipinfodb.com/v3/ip-country/?ip={ip}&key={key}&format=json",
"params": {
"key": "*****************************",
},
"fieldname": "countryCode",
},
{# free tier 150 querys per minute and https is not suported in free tier
"url": "http://ip-api.com/json/{ip}?fields=2",
"params": {},
"fieldname": "countryCode",
},
{# free tier 1.500 queries per day
"url": "https://api.ipdata.co/{ip}?api-key={key}",
"params": {
"key": "*****************************",
},
"fieldname": "country_code",
},
{# free tier 10.000 queries per month and https is not suported in free tier
"url": "http://api.ipstack.com/{ip}?access_key={key}",
"params": {
"key": "*****************************",
},
"fieldname": "country_code",
},
{# free tier 10.000 queries per month and https is not suported in free tier
"url": "http://api.ipapi.com/{ip}?access_key={key}",
"params": {
"key": "*****************************",
},
"fieldname": "country_code",
},
]
CODE:
import json
import urllib3
from django.conf import settings
for service in settings.IPCOUNTRY_APYKEY:
url = service["url"].format(ip=ip,**service["params"])
headers = {'Type': 'django', 'Ver': '1.1.1', 'Connection': 'Close'}
urllib3.disable_warnings()
http_call = urllib3.PoolManager()
try:
r = http_call.request('GET', url, headers=headers, timeout=1.0)
if r.status == 200:
json_response = json.loads(r.data.decode("utf-8"))
print(json_response[service["fieldname"]])
except Exception as e:
pass
return None
I have made SO answer where I am using Cloudflare CDN, they provide extra header with GEO location of each visitor. Advantage is that we don't have to install any external library or make any API call. Redirection can be achieved by Django middleware.
You can achieve this by making use of IP2Location Python library and IP2Location BIN database. First, purchase a commercial IP2Location database from https://www.ip2location.com/database/ip2location or download a free IP2Location LITE database from https://lite.ip2location.com/. And also install the IP2Location Python library by using this command: pip install IP2Location
After that, open your views.py, and add the following code into the file:
from django.http import HttpResponse
from django.shortcuts import redirect
import IP2Location
database = IP2Location.IP2Location(YOUR_DATABASE_PATH)
def get_client_ip(request):
x_forwarded_for = request.META.get('HTTP_X_FORWARDED_FOR')
if x_forwarded_for:
ip = x_forwarded_for.split(',')[0]
else:
ip = request.META.get('REMOTE_ADDR')
if ip == '127.0.0.1': # Only define the IP if you are testing on localhost.
ip = '8.8.8.8'
return ip
def redirect_view(request):
ip = get_client_ip(request)
rec = database.get_all(ip)
if rec.city == 'London': # Or any other city name
response = redirect('PATH_REDIRECT_TO')
return response
def redirectsucess_view(request):
return HttpResponse('Welcome!')
After that, open the urls.py, and add the following codes into the urlpatterns list:
path('redirect/', views.redirect_view),
path('PATH_REDIRECT_TO/', views.redirectsucess_view)
© 2022 - 2024 — McMap. All rights reserved.