Registry / web-framework / django-environ

django-environ

JSON →
library0.14.0pypypi✓ verified 31d ago

django-environ is a Python library that allows Django applications to be configured using 12-factor inspired environment variables. It simplifies parsing various types of settings (e.g., databases, caches, emails, booleans, integers) from `os.environ` or `.env` files into Django-compatible formats. The current version is 0.13.0, with a release cadence that generally follows Django versions and addresses bug fixes.

pip install django-environ
INSTALL
IMPORT
SIG · DJANGO-ENVIRON
D
django-environ
web-frameworkpythonv0.14.0
Install
1.6s avg
Import
58ms
Disk
16MB
Pass rate
10/ 10
Env Coverage10 / 10
glibc
3.9–3.13
musl
3.9–3.13
Install & Compatibility
Where this runs
tested against v0.14.0 · pip install
no network on importno background threads
Install × environment matrix
Each cell = how many times install + import succeeded across repeated harness runs. Partial = flaky.
glibc = Debian/Ubuntu slim · musl = Alpine Linux
musl
py 3.10–3.95 runs
installs and imports cleanly · install 0.0s · import 0.062s · 17.9MB
glibc
py 3.10–3.95 runs
installs and imports cleanly · install 1.6s · import 0.054s · 18MB
16MB installed
● package 16MB
Code
Verified usage

Verified import paths — ran on the pinned version, not inferred.

Env
✓ from environ import Env
Path
✓ from environ import Path
Used for path handling, typically to define BASE_DIR, etc.
InvalidPathSetting
✓ from environ import InvalidPathSetting
An exception that can be caught when path-related settings are invalid.

This quickstart demonstrates how to initialize `django-environ`, set up default type casting, and access various types of environment variables including complex ones like database and cache URLs. It simulates environment variables for a runnable example without requiring a physical `.env` file to be present.

import environ import os # --- Simulate environment variables for a runnable example --- # In a real application, these would come from your actual .env file or OS environment. # For local testing, you might create a .env file like: # SECRET_KEY=your-super-secret-key-from-env # DEBUG=True # DATABASE_URL=sqlite:///myproject.sqlite3 # EMAIL_URL=smtp://user:password@smtp.example.com:587 # CACHE_URL=redis://localhost:6379/1 # ------------------------------------------------------------ os.environ.setdefault('SECRET_KEY', 'your-super-secret-key-for-dev-fallback') os.environ.setdefault('DEBUG', 'True') os.environ.setdefault('DATABASE_URL', 'sqlite:///myproject.sqlite3') os.environ.setdefault('EMAIL_URL', 'smtp://user:password@smtp.example.com:587') os.environ.setdefault('CACHE_URL', 'redis://localhost:6379/1') # Initialize the Env object. # You can set default types and values here if not found in .env or os.environ. env = environ.Env( # default type for DEBUG is bool, default value is False if not set DEBUG=(bool, False) ) # Optional: Explicitly read .env file. By default, Env.read_env() looks for .env # in the current directory and its parents. If you don't call this, it implicitly # reads it on the first call to env() or similar, but explicit is better for control. # Note: This line assumes a .env file exists. For this example, we're relying on os.environ.setdefault. # environ.Env.read_env() # Accessing environment variables with type casting SECRET_KEY = env('SECRET_KEY') DEBUG = env('DEBUG') # Uses the (bool, False) casting defined above # Complex settings like database or cache URLs are parsed into Django-compatible dictionaries DATABASES = { 'default': env.db() # uses DATABASE_URL from environment } CACHES = { 'default': env.cache() # uses CACHE_URL from environment } EMAIL = env.email() # uses EMAIL_URL from environment print(f"SECRET_KEY: {SECRET_KEY}") print(f"DEBUG: {DEBUG} (type: {type(DEBUG)})") print(f"DATABASES (default): {DATABASES['default']}") print(f"CACHES (default): {CACHES['default']}") print(f"EMAIL (default): {EMAIL}") # Example of a missing variable with a default APP_VERSION = env('APP_VERSION', default='1.0.0') print(f"APP_VERSION: {APP_VERSION}")
Debug
Known issues
breakingThe `environ.Env` object no longer inherits from `dict` as of version 0.10.0. This means you cannot treat `env` as a dictionary (e.g., `env['KEY']` or `dict(env)`) directly. Access variables using the callable `env('KEY')` or its type-casting methods like `env.bool('KEY')`.
fix
Replace `env['KEY']` with `env('KEY', default=...)` or appropriate type-casting methods like `env.str('KEY')`, `env.bool('KEY')`.
affects: >=0.10.0
gotchaFor explicit `.env` file loading, ensure `environ.Env.read_env()` is called before `env()` attempts to access variables from the `.env` file. While `environ` attempts to implicitly read `.env` on first access, explicit calls with a correct path (e.g., `environ.Env.read_env(os.path.join(BASE_DIR, '.env'))`) provide better control and prevent unexpected behavior.
fix
Place `environ.Env.read_env()` early in your `settings.py` file, ideally right after `env` initialization and before any `env()` calls that rely on `.env` variables. Verify the `.env` file path is correct.
affects: All versions
gotchaAll variables accessed directly with `env('KEY')` are returned as strings. To get booleans, integers, URLs, or other types, you must use the specific type-casting methods (e.g., `env.bool('DEBUG')`, `env.int('TIMEOUT')`, `env.db('DATABASE_URL')`, `env.cache('CACHE_URL')`, `env.url('SITE_URL')`) or define the casting in the `Env` constructor `env = environ.Env(DEBUG=(bool, False))`.
fix
Always use `env.bool()`, `env.int()`, `env.db()`, `env.cache()`, etc., or constructor-defined type casting for non-string values.
affects: All versions
gotchaThe `SECRET_KEY` is a critical setting. While `django-environ` allows you to retrieve it via `env('SECRET_KEY')`, generating and managing it securely is paramount. Avoid hardcoding a default in production, and ensure it's loaded from a truly secure environment variable or a robust secrets manager.
fix
For development, use a fallback default like `env('SECRET_KEY', default='insecure-dev-key')`. In production, ensure `SECRET_KEY` is always provided via `os.environ` or a `.env` file that is securely managed, without a default.
affects: All versions
Errors
Common errors & fixes
django.core.exceptions.ImproperlyConfigured: Set the SECRET_KEY environment variable
This error occurs when `django-environ` cannot find the specified environment variable (e.g., `SECRET_KEY`) because it's missing from the `.env` file, the `.env` file isn't being read, or an existing environment variable is not being overridden.
fix
Ensure a `.env` file exists in your project's root directory (or the path specified for `read_env()`). Verify that the variable (e.g., `SECRET_KEY`) is present in the `.env` file with a value. Confirm that `environ.Env.read_env()` is called correctly in your `settings.py` before attempting to access variables. If an environment variable is set externally and needs to be overridden by the `.env` file, pass `overwrite=True` to `env.read_env()` (e.g., `env.read_env(overwrite=True)`).
ModuleNotFoundError: No module named 'environ'
The `django-environ` package (which provides the `environ` module) is not installed in your active Python environment, or the Python interpreter being used is not the one associated with the environment where `django-environ` is installed.
fix
Activate your Python virtual environment if you are using one. Install the `django-environ` package using pip: `pip install django-environ`. Also, check for any local Python files named `environ.py` that might be clashing with the library's import.
KeyError: 'SECRET_KEY'
This `KeyError` occurs when `env('VAR_NAME')` is called, but the environment variable `VAR_NAME` is not found in `os.environ` after `django-environ` attempts to load variables, and no default value has been provided in the `env()` call.
fix
Ensure the `.env` file contains an entry for the missing key (e.g., `SECRET_KEY=your_value`). Verify that `environ.Env.read_env()` is called successfully before you attempt to access the variable using `env('SECRET_KEY')`. For non-critical settings, you can provide a default value to prevent the `KeyError` (e.g., `DEBUG = env('DEBUG', default=False)`).
Issues with special characters in DATABASE_URL (e.g., '#' in password)
Special characters such as '#' in URL-parsed environment variables like `DATABASE_URL` are often not properly URL-encoded, causing `django-environ`'s underlying URL parser (which uses `urllib` following RFC 3986) to misinterpret the string (e.g., treating '#' as the start of a comment).
fix
URL-encode any unsafe characters within the values of your URL-based environment variables in the `.env` file. For instance, replace a pound sign (`#`) in a password with its URL-encoded equivalent (`%23`).

```
# Original (problematic)
DATABASE_URL="postgres://user:pass#word@host:port/dbname"

# Fix (URL-encode '#')
DATABASE_URL="postgres://user:pass%23word@host:port/dbname"
```
Upgrade
Version history
0.14.0latest on PyPI · released Jun 18, 2026
Audit
Dependencies
DjangorequiredCore functionality is built around Django's settings system.
Agent activity
14 hits · last 30 days
node
12
Resources