Django Device Detector
Django Device Detector is a high-performance Django package built on top of the powerful device-detector library to parse User-Agent strings.
It provides a cached Device object on every request, making it easy to detect mobiles, tablets, desktops, TVs, bots, brands, models, browsers, and OS versions.
This package is inspired by django-user_agents, aiming to provide a similar developer experience but powered by the more comprehensive device_detector backend.
Key Features
- 🚀 High Performance: Uses __slots__ and dataclasses for minimal memory footprint.
- 🧠 Cached: parsed results are cached in your configured Django cache (Redis, Memcached, etc.) to avoid expensive re-parsing.
- 🛡️ Safe defaults: Guaranteed to return a consistent Device object, even without caching.
- 📱 Comprehensive: Detects thousands of devices (brands, models), browsers, bots, and OS versions.
- ⚡Lazy parsing:: Uses Django's SimpleLazyObject to ensure parsing only happens if the request.device object is accessed.
- Template Friendly: Provides a simple device object with boolean properties and filters (e.g., device.is_mobile) (e.g., request|is_mobile) for use in templates.
Installation
-
Install the package:
pip install django-device-detector -
Add to INSTALLED_APPS:
INSTALLED_APPS = [
# ...
'django_device_detector',
] -
Add the Middleware: Add DeviceDetectorMiddleware to your MIDDLEWARE setting. It works best after SessionMiddleware and AuthenticationMiddleware.
MIDDLEWARE = [
# ...
'django.contrib.sessions.middleware.SessionMiddleware',
'django.contrib.auth.middleware.AuthenticationMiddleware',
# ...
'django_device_detector.middleware.DeviceDetectorMiddleware',
] -
Add the Context Processor (Optional): If you want to access the device variable directly in your templates (e.g., {{ device.is_mobile }}), add this to context_processors.
TEMPLATES = [
{
'BACKEND': 'django.template.backends.django.DjangoTemplates',
# ...
'OPTIONS': {
'context_processors': [
# ...
'django.template.context_processors.request',
'django_device_detector.context_processors.device',
],
},
},
]
Usage
In Views
You can access request.device directly.
from django.shortcuts import render
from django.http import HttpResponseForbidden
def home(request):
# Parsing occurs on first access
device = request.device
if device.is\_bot:
return HttpResponseForbidden("No bots allowed\!")
if device.is\_mobile:
\# Redirect to mobile site or render mobile template
return render(request, 'home\_mobile.html', {'device': device})
return render(request, 'home\_desktop.html', {'device': device})
In Templates
Using the Context Processor variable
Once configured, device is globally available.
<!DOCTYPE html>
<html>
<head>
<title>My Site</title>
</head>
<body>
{% if device.is_mobile %}
<h1>Welcome, Mobile User!</h1>
<p>You are using a {{ device.device_brand }} {{ device.device_model }}.</p>
{% else %}
<h1>Welcome, Desktop User!</h1>
<p>You are browsing on {{ device.os_name }} {{ device.os_version }}.</p>
{% endif %}
{% if device.is\_tablet %}
\<div class="tablet-banner"\>Looks like you're on a tablet\!\</div\>
{% endif %}
\<footer\>
\<small\>Debug: {{ device.pretty\_print }}\</small\>
\</footer\>
</body>
</html>
Using Template Filters
If you prefer not to use the context processor (or if you only have the request object), you can use the provided template filters.
First, load the tags:
{% load device_detector %}
Then use the filters on the request object:
{% if request|is_mobile %}
Mobile View
{% endif %}
{% if request|is_tablet %}
Tablet View
{% endif %}
{% if request|is_desktop %}
Desktop View
{% endif %}
{% if request|is_bot %}
Bot View
{% endif %}
{% if request|is_television %}
TV View
{% endif %}
Configuration
You can customize the behavior in your settings.py.
| Setting | Description | Default |
|---|---|---|
| DEVICE_DETECTOR_CACHE | The alias of the cache backend to use (e.g., 'default', 'redis'). Set to None to disable caching. | 'default' |
| DEVICE_DETECTOR_CLASS | The class used for parsing. Use 'device_detector.SoftwareDetector' for faster, lighter parsing if you only need OS/Browser info (skips device/bot detection). | 'device_detector.DeviceDetector' |
Example:
# settings.py
# Use a specific cache backend for devices
CACHES = {
'default': { ... },
'devices': {
'BACKEND': 'django.core.cache.backends.redis.RedisCache',
'LOCATION': 'redis://127.0.0.1:6379/1',
}
}
DEVICE_DETECTOR_CACHE = 'devices'
API Reference: The Device Object
The request.device object is a data class containing the following properties.
Booleans fall back to False and strings to "" when a value isn’t known.
1. Top-Level Convenience Properties
Common flags for routing and UI logic.
| Attribute | Type | Description |
|---|---|---|
is_known |
bool |
True f any part of the UA was recognized. |
is_bot |
bool |
True if the UA is a bot. |
is_mobile |
bool |
True for mobile devices (smartphones, tablets, wearables, etc.). |
is_desktop |
bool |
True for desktops, laptops, and notebooks. |
is_television |
bool |
True for TVs and set-top boxes. |
uses_mobile_browser |
bool |
True if the browser is mobile-only. |
is_tablet |
bool |
True if the device_type is 'tablet'. |
is_smartphone |
bool |
True if the device_type is 'smartphone'. |
is_console |
bool |
True if the device_type is 'console'. |
is_wearable |
bool |
True if the device_type is 'wearable'. |
is_car_browser |
bool |
True if the device_type is 'car browser'. |
is_feature_phone |
bool |
True if the device_type is 'feature phone'. |
preferred_client_name |
str |
Returns the most specific client name. (e.g., "Facebook" vs "Chrome Mobile WebView"). |
preferred_client_version |
str |
Version corresponding to the preferred_client_name. |
preferred_client_type |
str |
Type corresponding to the preferred_client_name. |
pretty_name |
str |
A human-readable classification for "worthless" (low-signal) UAs (e.g., 'Numeric', 'UUID') or the original UA. |
user_agent_string |
str |
The original User-Agent string. |
2. Bot Details (if is_bot is True)
These properties are only populated if is_bot is True.
| Attribute | Type | Description |
|---|---|---|
bot_name |
str |
Bot name (e.g., "Googlebot"). |
bot_category |
str |
Bot category (e.g., "Search bot", "Crawler"). |
bot_url |
str |
A URL with more information about the bot. |
bot_producer_name |
str |
Bot owner name (e.g., "Google Inc."). |
bot_producer_url |
str |
The homepage of the bot's producer. |
3. Client (Software)
Describes the application, browser, or library that made the request.
Primary Client
| Attribute | Type | Description |
|---|---|---|
client_name |
str |
Primary client name (e.g., "Chrome Mobile", "curl", "Facebook"). |
client_version |
str |
Primary client version. |
client_type |
str |
Client type (e.g., "browser", "mobile app", "library"). |
client_app_id |
str |
Application ID if present (e.g., "com.facebook.katana"). |
Browser-Specific (if client_type is 'browser')
| Attribute | Type | Description |
|---|---|---|
client_short_name |
str |
Two-letter browser code (e.g., "CH" for Chrome). |
client_family |
str |
Browser family (e.g., "Chrome"). |
client_engine |
str |
Rendering engine (e.g., "Blink", "WebKit", "Gecko"). |
client_engine_version |
str |
Engine version. |
client_is_mobile_only |
bool |
True if the browser only runs on mobile. |
Secondary Client
(Populated when an app (e.g., Facebook) is identified as using an in-app browser (e.g., Chrome Mobile WebView))
| Attribute | Type | Description |
|---|---|---|
secondary_client_name |
str |
The name of the secondary app (e.g., "Facebook"). |
secondary_client_version |
str |
The version of the secondary app. |
secondary_client_type |
str |
The type of the secondary app. |
4. Operating System (OS)
| Attribute | Type | Description |
|---|---|---|
os_name |
str |
Full OS name (e.g., "Android", "Windows", "iOS"). |
os_version |
str |
OS version (e.g., "10", "14.1"). |
os_short_name |
str |
Three-letter OS code (e.g., "WIN", "AND"). |
os_family |
str |
OS family (e.g., "Windows", "GNU/Linux"). |
os_platform |
str |
CPU platform/architecture, if known (e.g., "x64", "ARM"). |
5. Device (Hardware)
| Attribute | Type | Description |
|---|---|---|
device_type |
str |
Specific hardware type (e.g., "smartphone", "tablet", "desktop", "tv"). See is_tablet, is_smartphone, etc. for boolean checks. |
device_brand |
str |
Vendor brand (e.g., "Apple", "Samsung", "Google"). |
device_model |
str |
Model name (e.g., "iPhone", "Pixel 6", "SM-G998U"). |
6. Advanced / Internal Attributes
These attributes store the results of intermediate calculations performed by the parser. They are useful for debugging and advanced logic.
| Attribute | Type | Description |
|---|---|---|
calculated_android_feature_phone |
bool |
True if identified as an Android feature phone. |
calculated_android_device_type |
str |
The device type ('tablet' or 'smartphone') inferred from Android fragments. |
calculated_windows_tablet |
bool |
True if the parser inferred a Windows Tablet from a "Touch" token. |
calculated_opera_tablet |
bool |
True if inferred from an "Opera Tablet" fragment. |
raw_details |
dict |
The raw, nested dictionary of all data populated by the device-detector parsers. |
7. Utility Methods
- pretty_print(): Returns a human-readable summary string (e.g., "Client: Chrome (Browser) Device: iPhone (Smartphone) OS: iOS 16.0").
License
This project is licensed under the MIT License.
Metadata
Release files for django-device-detector 0.1.0
For a detailed explanation of source distributions (sdists) and built distributions (wheels), please see the package formats documentation.
Built distribution (wheel)
| File | Interpreter | ABI | Platform | Actions Reset |
|---|---|---|---|---|
| django_device_detector-0.1.0-py3-none-any.whl | Python 3 | none | any | Details for django_device_detector-0.1.0-py3-none-any.whl |
Release files / django_device_detector-0.1.0-py3-none-any.whl
| Download URL | django_device_detector-0.1.0-py3-none-any.whl |
|---|---|
| Size | 14.9 kB |
| Tags | Python 3 |
|
SHA-256 checksum How to use checksums |
356b94d118a5ca79292df380a8aad4c8169005a1398babe98a44d24e60c14f49
|
|
BLAKE2b-256 checksum How to use checksums |
6a914ac60f18efe3232c9f9232e4b984da8582c8d783b3faf529361ae32ed81d
|
| Upload date | |
|
Uploaded using Trusted Publishing? What is trusted publishing? |
No |
| Uploaded via |
twine/6.2.0 CPython/3.10.10
|
Security for django-device-detector 0.1.0
Provenance
Provenance describes where a file came from. On PyPI, provenance is shared via attestations, which provide a verifiable record of the build or publishing details. View details, limitations and caveats.
No provenance found
None of the files in this release were uploaded with provenance metadata.
A note on package security
PyPI is a repository for distributing packages, not a service for auditing them. While third-party security researchers and our staff do their best to detect and remove malicious packages, PyPI cannot guarantee the quality, security or suitability of any given package.
To learn more about protecting yourself from malicious actors, visit our package security documentation.