• Stars
    star
    296
  • Rank 140,464 (Top 3 %)
  • Language
    Python
  • License
    MIT License
  • Created almost 3 years ago
  • Updated over 1 year ago

Reviews

There are no reviews yet. Be the first to send feedback to the community and the maintainers!

Repository Details

Automatically reload your browser in development.

django-browser-reload

https://img.shields.io/github/actions/workflow/status/adamchainz/django-browser-reload/main.yml?branch=main&style=for-the-badge https://img.shields.io/badge/Coverage-100%25-success?style=for-the-badge https://img.shields.io/pypi/v/django-browser-reload.svg?style=for-the-badge https://img.shields.io/badge/code%20style-black-000000.svg?style=for-the-badge pre-commit

Automatically reload your browser in development.

Requirements

Python 3.8 to 3.12 supported.

Django 3.2 to 4.2 supported.

WSGI supported on all Django versions. ASGI supported on Django 4.2+.

Your browser needs to support:

  • EventSource - universally available.
  • SharedWorker - available on Chrome, Edge, Firefox, and Opera for a long time. Available on Safari since version 16 (2022-09-12).

Want to work smarter and faster? Check out my book Boost Your Django DX which covers django-browser-reload and many other tools. I wrote django-browser-reload whilst working on the book!


Installation

  1. Install with pip:

    python -m pip install django-browser-reload
  2. Ensure you have "django.contrib.staticfiles" in your INSTALLED_APPS.

  3. Add django-browser-reload to your INSTALLED_APPS:

    INSTALLED_APPS = [
        ...,
        "django_browser_reload",
        ...,
    ]
  4. Include the app URLs in your root URLconf:

    from django.urls import include, path
    
    urlpatterns = [
        ...,
        path("__reload__/", include("django_browser_reload.urls")),
    ]

    You can use another prefix if required.

  5. Add the middleware:

    MIDDLEWARE = [
        # ...
        "django_browser_reload.middleware.BrowserReloadMiddleware",
        # ...
    ]

    The middleware should be listed after any others that encode the response, such as Django’s GZipMiddleware.

    The middleware automatically inserts the required script tag on HTML responses before </body> when DEBUG is True. It does so to every HTML response, meaning it will be included on Django’s debug pages, admin pages, etc. If you want more control, you can instead insert the script tag in your templates—see below.

All done! 📯

For faster and more efficient reloading, also set up Django’s built-in Watchman support.

What It Does

When DEBUG is True, the template tag includes a small script. This script connects back to the development server and will automatically reload when static assets or templates are modified, or after runserver restarts. The reload only happens in the most recently opened tab.

Example Project

See the example project in the example/ directory of the GitHub repository. Start it up and modify its files to see the reloading in action.

Template Tag

If the middleware doesn’t work for you, you can also use a template tag to insert the script on relevant pages. The template tag has both Django templates and Jinja versions, and only outputs the script tag when DEBUG is True.

For Django Templates, load the tag and use it in your base template. The tag can go anywhere, but it’s best just before </body>:

{% load django_browser_reload %}

...

    {% django_browser_reload_script %}
  </body>
</html>

To add django-browser-reload to Django’s admin, do so in a template called admin/base_site.html:

{% extends "admin/base_site.html" %}

{% load django_browser_reload %}

{% block extrahead %}
    {{ block.super }}
    {% django_browser_reload_script %}
{% endblock %}

This follows Django’s documentation on extending an overridden template.

For Jinja Templates, you need to perform two steps. First, load the tag function into the globals of your custom environment:

# myproject/jinja2.py
from jinja2 import Environment
from django_browser_reload.jinja import django_browser_reload_script


def environment(**options):
    env = Environment(**options)
    env.globals.update(
        {
            # ...
            "django_browser_reload_script": django_browser_reload_script,
        }
    )
    return env

Second, render the tag in your base template. It can go anywhere, but it’s best just before </body>:

...
    {{ django_browser_reload_script() }}
  </body>
</html>

Ta-da!

How It Works

Here’s a diagram:

                                     Browser

                             Tab 1    Tab 2     Tab N
                           listener  listener  listener
                                \       |       /
  Django                         \      |      /
                                  \     |     /
Events View --------------------> Shared worker

The template tag includes a listener script on each page. This listener script starts or connects to a SharedWorker, running a worker script. The worker script then connects to the events view in Django, using an EventSource to receive server-sent events.

This event source uses StreamingHttpResponse to send events to the worker. The view continues streaming events indefinitely, until disconnected. (This requires a thread and will not work if you use runserver’s --nothreading option.)

On a relevant event, the worker will reload the most recently connected tab. (It avoids reloading all tabs since that could be expensive.)

To reload when a template changes, django-browser-reload piggybacks on Django’s autoreloading infrastructure. An internal Django signal indicates when a template file has changed. The events view receives this signal and sends an event to the worker, which triggers a reload. There is no smart filtering - if any template file changes, the view is reloaded.

To reload when the server restarts, django-browser-reload uses a version ID. This ID is randomly generated when the view module is imported, so it will be different every time the server starts. When the server restarts, the worker’s EventSource reconnects with minimal delay. On connection, the events view sends the version ID, which the worker sees as different, so it triggers a reload.

The events view also sends the version ID every second to keep the connection alive.

More Repositories

1

django-cors-headers

Django app for handling the server headers required for Cross-Origin Resource Sharing (CORS)
Python
5,087
star
2

django-htmx

Extensions for using Django with htmx.
JavaScript
866
star
3

django-upgrade

Automatically upgrade your Django projects.
Python
641
star
4

django-mysql

🐬 🐴 Extensions to Django for use with MySQL/MariaDB
Python
535
star
5

blacken-docs

Run `black` on python code blocks in documentation files
Python
513
star
6

time-machine

Travel through time in your tests.
Python
447
star
7

flake8-comprehensions

❄️ A flake8 plugin to help you write better list/set/dict comprehensions.
Python
446
star
8

django-perf-rec

Keep detailed records of the performance of your Django code.
Python
330
star
9

mac-ansible

🐄 Configuring my mac with Ansible
Shell
170
star
10

patchy

⚓ Patch the inner source of python functions at runtime.
Python
163
star
11

apig-wsgi

Wrap a WSGI application in an AWS Lambda handler function for running on API Gateway or an ALB.
Python
146
star
12

django-linear-migrations

Ensure your migration history is linear.
Python
136
star
13

treepoem

Barcode rendering for Python supporting QRcode, Aztec, PDF417, I25, Code128, Code39 and many more types.
PostScript
115
star
14

ec2-metadata

An easy interface to query the EC2 metadata API, with caching.
Python
102
star
15

django-rich

Extensions for using Rich with Django.
Python
90
star
16

django-permissions-policy

Set the draft security HTTP header Permissions-Policy (previously Feature-Policy) on your Django app.
Python
81
star
17

django-watchfiles

Use watchfiles in Django’s autoreloader.
Python
81
star
18

django-read-only

Disable Django database writes.
Python
75
star
19

django-minify-html

Use minify-html, the extremely fast HTML + JS + CSS minifier, with Django.
Python
73
star
20

flake8-tidy-imports

❄️ A flake8 plugin that helps you write tidier imports.
Python
60
star
21

heroicons

Use heroicons in your Django and Jinja templates.
Python
58
star
22

SublimeFiglet

Add in ASCII text art from "figlet"
Python
46
star
23

lifelogger

📅 Track your life like a pro on Google Calendar via your terminal.
Python
40
star
24

pip-lock

Check for differences between requirements.txt files and your environment
Python
36
star
25

django-capture-on-commit-callbacks

Capture and make assertions on transaction.on_commit() callbacks.
Python
35
star
26

django-version-checks

System checks for your project's environment.
Python
34
star
27

django-jsonfield

(Maintenance mode only) Cross-database JSON field for Django models.
Python
30
star
28

unittest-parametrize

Parametrize tests within unittest TestCases.
Python
29
star
29

scripts

Useful little scripts that I use on commandline. Work in OS-X + zsh at least.
Shell
27
star
30

multilint

✅ Run multiple python linters easily
Python
27
star
31

flake8-no-pep420

A flake8 plugin to ban PEP-420 implicit namespace packages.
Python
22
star
32

django-startproject-templates

Python
22
star
33

pytest-is-running

pytest plugin providing a function to check if pytest is running.
Python
21
star
34

SublimeHTMLMustache

✏️ Adds HTML Mustache as a language to Sublime Text 2/3, with snippets.
19
star
35

pytest-reverse

Pytest plugin to reverse test order.
Python
19
star
36

owela-club

Play the Namibian game of Owela against a terrible AI. Built using Django and htmx.
Python
18
star
37

nose-randomly

👃 Nose plugin to randomly order tests and control `random.seed`
Python
17
star
38

talk-how-to-hack-a-django-website

JavaScript
14
star
39

dynamodb_utils

A toolchain for Amazon's DynamoDB to make common operations (backup, restore backups) easier.
Python
12
star
40

sound-resynthesis

🔈 Sound Resynthesis with a Genetic Algorithm - my final year project from university
Java
12
star
41

mariadb-dyncol

💾 Python dicts <-> MariaDB Dynamic Column binary format
Python
11
star
42

pre-commit-oxipng

Mirror of oxipng for pre-commit.
Rust
11
star
43

pytest-flake8dir

❄️ A pytest fixture for testing flake8 plugins.
Python
11
star
44

logentries-cli

📒 Get your logs from Logentries on the comandline.
Python
10
star
45

pre-commit-dprint

Mirror of dprint for pre-commit.
9
star
46

sublime-rst-improved

Python
8
star
47

h

Python
8
star
48

talk-improve-startup-time

“How to profile and improve startup time” talk
JavaScript
8
star
49

sublime_text_settings

✏️ My settings for sublime text 3 - as in Packages/User
Python
8
star
50

talk-django-and-htmx

JavaScript
7
star
51

django-settings-file

Python
7
star
52

tox-py

Adds the --py flag to tox to run environments matching a given Python interpreter.
Python
6
star
53

kwargs-only

A decorator to make a function accept keyword arguments only, on both Python 2 and 3.
Python
6
star
54

pytest-super-check

🔒 Pytest plugin to ensure all your TestCase classes call super() in setUp, tearDown, etc.
Python
6
star
55

django_atomic_celery

Atomic transaction aware Celery tasks for Django
Python
6
star
56

django-coverage-example

Python
5
star
57

django-pymysql-backend

A Django database backend for MySQL using PyMySQL.
Python
5
star
58

pytest-restrict

🔒 Pytest plugin to restrict the test types allowed
Python
5
star
59

talk-data-oriented-django

JavaScript
4
star
60

talk-speed-up-your-tests-with-setuptestdata

JavaScript
4
star
61

talk-django-and-web-security-headers

JavaScript
3
star
62

fluentd.tmLanguage

Syntax highlighting for Fluentd configuration files
3
star
63

django-ticket-33153

https://code.djangoproject.com/ticket/33153
Python
3
star
64

pytest-flake8-path

A pytest fixture for testing flake8 plugins.
Python
3
star
65

django_atomic_signals

Signals for atomic transaction blocks in Django 1.6+
Python
3
star
66

flake8-no-types

A flake8 plugin to ban type hints.
Python
3
star
67

SublimeMoveTabs

✏️ A short plugin for Sublime Text 2 that allows rearrangement of tabs/'views' with the keyboard.
Python
3
star
68

dynamodb_local_utils

Automatically run DynamoDB Local on Mac OS X
Shell
3
star
69

pygments-git

Pygments lexers for Git output and files
Python
3
star
70

workshop-evenergy-concurrency-and-parallelism

Python
2
star
71

talk-how-complex-systems-fail

Talk for the Papers We Love London meetup
TeX
2
star
72

google_lifelog

Making a lifelog on google calendar.
Python
2
star
73

talk-building-interactive-pages-with-htmx

JavaScript
2
star
74

workshop-idiomatic-python

Python
2
star
75

ansible-talk-custom-template-filters

My talk for the Ansible London Meetup in March 2015
TeX
2
star
76

talk-django-vs-flask

JavaScript
2
star
77

django-talk-factory-boy

Talk for London Django Meetup
TeX
2
star
78

ProgrammingInterview

Solving the problems posted on ProgrammingInterview on YouTube
Python
2
star
79

example-pre-commit-ci-lite

example
2
star
80

django-server-push-demo

Python
2
star
81

talk-django-capture-on-commit-callbacks

JavaScript
2
star
82

techblog

Filled with little coding notes and fixes.
2
star
83

adamchainz

👋
Python
2
star
84

SublimeCowsay

✏️🐮 A silly little Sublime Text plugin for 2 and 3 to allow you to quickly convert a text selection to a cow speech bubble via the brilliant cowsay utility.
Python
2
star
85

djceu2019-workshop

Python
2
star
86

talk-what-happens-when-you-run-manage.py-test

JavaScript
2
star
87

talk-technologies-that-will-be-around-in-21-years

JavaScript
2
star
88

django-demo-constraint-single-column-not-null

Python
2
star
89

django-harlequin

Launch Harlequin, the SQL IDE for your Terminal, with your Django database configuration.
Python
2
star
90

channels-bug-connection-closed

Reproduction for Channels bug
Python
1
star
91

workshop-concurrency-and-parallelism

Python
1
star
92

django-talk-duth

Django Under The Hood 2015 Summary
TeX
1
star
93

workshop-rest-api-django

Python
1
star
94

workshop-recommended-practices

Python
1
star
95

talk-django-3.2-test-features

JavaScript
1
star
96

workshop-profiling-and-debugging

Python
1
star
97

django-feature-policy-shim

1
star
98

kvkit

high-level python toolkit for ordered key/value stores
Python
1
star
99

phabricator-csv-import

Python
1
star
100

django-blue-green-example

Reproducing the technique from “Smooth Database Changes in Blue-Green Deployments” by Mariusz Felisiak.
Python
1
star