Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
- Loading branch information
0 parents
commit 0299032
Showing
15 changed files
with
238 additions
and
0 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,9 @@ | ||
node_modules/ | ||
.DS* | ||
TAGS | ||
dist | ||
cabal-dev | ||
*.pyc | ||
build/ | ||
py/ua_parser.egg-info/ | ||
|
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,3 @@ | ||
Author: | ||
|
||
* Selwin Ong (https://github.com/selwin) |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,20 @@ | ||
Copyright (c) 2013 Selwin Ong | ||
|
||
Permission is hereby granted, free of charge, to any person obtaining | ||
a copy of this software and associated documentation files (the | ||
"Software"), to deal in the Software without restriction, including | ||
without limitation the rights to use, copy, modify, merge, publish, | ||
distribute, sublicense, and/or sell copies of the Software, and to | ||
permit persons to whom the Software is furnished to do so, subject to | ||
the following conditions: | ||
|
||
The above copyright notice and this permission notice shall be | ||
included in all copies or substantial portions of the Software. | ||
|
||
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, | ||
EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF | ||
MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND | ||
NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE | ||
LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION | ||
OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION | ||
WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,2 @@ | ||
include LICENSE.txt | ||
include README.rst |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,76 @@ | ||
Django User Agents | ||
================== | ||
|
||
A django package that allows easy identification of visitor's browser, OS and device information, | ||
including whether the visitor uses a mobile phone, tablet or a touch capable device. Under the hood, | ||
it uses `user-agents <https://github.com/selwin/python-user-agents>`_. | ||
|
||
|
||
How to Use | ||
========== | ||
|
||
1. Install ``django-user-agents``, you'll have to make sure that `user-agents`_ is installed first:: | ||
|
||
pip install pyyaml ua-parser user-agents | ||
pip install django-user-agents | ||
|
||
2. Configure ``settings.py``: | ||
|
||
.. code-block:: python | ||
MIDDLEWARE_CLASSES = ( | ||
# other middlewares... | ||
'django_user_agents.middleware.UserAgentMiddleware', | ||
) | ||
# Cache backend is optional, but recommended to speed up user agent parsing | ||
CACHES = { | ||
'default': { | ||
'BACKEND': 'django.core.cache.backends.memcached.MemcachedCache', | ||
'LOCATION': '127.0.0.1:11211', | ||
} | ||
} | ||
3. ``UserAgentMiddleware`` will add a ``user_agent`` attribute to ``request``: | ||
|
||
.. code-block:: python | ||
# Let's assume that the visitor uses an iPhone... | ||
request.user_agent.is_mobile # returns True | ||
request.user_agent.is_tablet # returns False | ||
request.user_agent.is_touch_capable # returns True | ||
request.user_agent.is_pc # returns False | ||
# Accessing user agent's browser attributes | ||
request.user_agent.browser # returns Browser(family=u'Mobile Safari', version=(5, 1), version_string='5.1') | ||
request.user_agent.browser.family # returns 'Mobile Safari' | ||
request.user_agent.browser.version # returns (5, 1) | ||
request.user_agent.browser.version_string # returns '5.1' | ||
# Operating System properties | ||
request.user_agent.os # returns OperatingSystem(family=u'iOS', version=(5, 1), version_string='5.1') | ||
request.user_agent.os.family # returns 'iOS' | ||
request.user_agent.os.version # returns (5, 1) | ||
request.user_agent.os.version_string # returns '5.1' | ||
# Device properties | ||
request.user_agent.device # returns Device(family='iPhone') | ||
request.user_agent.device.family # returns 'iPhone' | ||
You can find out more about user agent attributes at `here <https://github.com/selwin/python-user-agents>`_. | ||
|
||
|
||
Running Tests | ||
============= | ||
|
||
`which django-admin.py` test django_user_agents --settings=django_user_agents.tests.settings --pythonpath=. | ||
|
||
|
||
Changelog | ||
========= | ||
|
||
0.1 | ||
--- | ||
|
||
* Initial release |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1 @@ | ||
VERSION = (0, 1) |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,23 @@ | ||
from django.core.cache import cache | ||
from django.template.defaultfilters import slugify | ||
from django.utils.functional import SimpleLazyObject | ||
|
||
from user_agents import parse | ||
|
||
|
||
def get_user_agent_cached(ua_string): | ||
# Tries to get UserAgent objects from cache before constructing a UserAgent | ||
# from scratch because parsing regexes.yaml/json (ua-parser) is slow | ||
key = slugify(ua_string) | ||
user_agent = cache.get(key) | ||
if user_agent is None: | ||
user_agent = parse(ua_string) | ||
cache.set(key, user_agent) | ||
return user_agent | ||
|
||
|
||
class UserAgentMiddleware(object): | ||
# A middleware that adds a "user_agent" object to request | ||
def process_request(self, request): | ||
request.user_agent = SimpleLazyObject( | ||
lambda: get_user_agent_cached(request.META['HTTP_USER_AGENT'])) |
Empty file.
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1 @@ | ||
from .tests import MiddlewareTest |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,33 @@ | ||
from os import path | ||
|
||
|
||
DATABASES = { | ||
'default': { | ||
'ENGINE': 'django.db.backends.sqlite3', | ||
'NAME': ':memory:', | ||
}, | ||
} | ||
|
||
INSTALLED_APPS = ['django_user_agents'] | ||
|
||
MIDDLEWARE_CLASSES = ( | ||
'django_user_agents.middleware.UserAgentMiddleware', | ||
) | ||
|
||
ROOT_URLCONF = 'django_user_agents.tests.urls' | ||
|
||
TEMPLATE_LOADERS = ( | ||
'django.template.loaders.filesystem.Loader', | ||
'django.template.loaders.app_directories.Loader', | ||
) | ||
|
||
CACHES = { | ||
'default': { | ||
'BACKEND': 'django.core.cache.backends.locmem.LocMemCache', | ||
'TIMEOUT': 60, | ||
} | ||
} | ||
|
||
TEMPLATE_DIRS = ( | ||
path.join(path.dirname(__file__), "templates"), | ||
) |
Empty file.
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,25 @@ | ||
from django.core.cache import cache, get_cache | ||
from django.core.urlresolvers import reverse | ||
from django.template.defaultfilters import slugify | ||
from django.test.client import Client | ||
from django.utils import unittest | ||
|
||
from user_agents.parsers import parse, UserAgent | ||
|
||
|
||
iphone_ua_string = 'Mozilla/5.0 (iPhone; CPU iPhone OS 5_1 like Mac OS X) AppleWebKit/534.46 (KHTML, like Gecko) Version/5.1 Mobile/9B179 Safari/7534.48.3' | ||
ipad_ua_string = 'Mozilla/5.0(iPad; U; CPU iPhone OS 3_2 like Mac OS X; en-us) AppleWebKit/531.21.10 (KHTML, like Gecko) Version/4.0.4 Mobile/7B314 Safari/531.21.10' | ||
|
||
|
||
class MiddlewareTest(unittest.TestCase): | ||
|
||
def test_middleware_assigns_user_agent(self): | ||
client = Client(HTTP_USER_AGENT=ipad_ua_string) | ||
response = client.get(reverse('user_agent_test')) | ||
self.assertIsInstance(response.context['user_agent'], UserAgent) | ||
|
||
def test_cache_is_set(self): | ||
client = Client(HTTP_USER_AGENT=iphone_ua_string) | ||
response = client.get(reverse('user_agent_test')) | ||
self.assertIsInstance(response.context['user_agent'], UserAgent) | ||
self.assertIsInstance(cache.get(slugify(iphone_ua_string)), UserAgent) |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,6 @@ | ||
from django.conf.urls import patterns, url | ||
|
||
|
||
urlpatterns = patterns('django_user_agents.tests.views', | ||
url(r'^user-agents/', 'test', name='user_agent_test'), | ||
) |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,5 @@ | ||
from django.shortcuts import render | ||
|
||
|
||
def test(request): | ||
return render(request, "test.html", {'user_agent': request.user_agent}) |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,34 @@ | ||
# -*- coding: utf-8 -*- | ||
from setuptools import setup | ||
|
||
|
||
description = "A django package that allows easy identification of visitor's " | ||
"browser, operating system and device information (mobile phone, " | ||
"tablet or a touch capable)." | ||
|
||
setup( | ||
name='django-user_agents', | ||
version='0.1', | ||
author='Selwin Ong', | ||
author_email='selwin.ong@gmail.com', | ||
packages=['django_user_agents'], | ||
url='https://github.com/selwin/django-user_agents', | ||
license='MIT', | ||
description=description, | ||
long_description=open('README.rst').read(), | ||
zip_safe=False, | ||
include_package_data=True, | ||
package_data = { '': ['README.rst'] }, | ||
#install_requires=['user-agents'], | ||
classifiers=[ | ||
'Development Status :: 4 - Beta', | ||
'Environment :: Web Environment', | ||
'Framework :: Django', | ||
'Intended Audience :: Developers', | ||
'License :: OSI Approved :: MIT License', | ||
'Operating System :: OS Independent', | ||
'Programming Language :: Python', | ||
'Topic :: Internet :: WWW/HTTP', | ||
'Topic :: Software Development :: Libraries :: Python Modules', | ||
] | ||
) |