Skip to content

Commit

Permalink
Added developer debugging tools (#1479)
Browse files Browse the repository at this point in the history
  • Loading branch information
daveoconnor committed Nov 28, 2024
1 parent 765a5b7 commit f233f27
Show file tree
Hide file tree
Showing 12 changed files with 106 additions and 3 deletions.
10 changes: 10 additions & 0 deletions config/settings.py
Original file line number Diff line number Diff line change
Expand Up @@ -22,6 +22,7 @@

# Whether or not we're in local development mode
LOCAL_DEVELOPMENT = env.bool("LOCAL_DEVELOPMENT", default=False)
DEBUG_TOOLBAR = env.bool("DEBUG_TOOLBAR", default=False)
CI = env.bool("CI", default=False)

if DEBUG:
Expand Down Expand Up @@ -567,3 +568,12 @@
SLACK_BOT_TOKEN = env("SLACK_BOT_TOKEN", default="")

ACCOUNT_DELETION_GRACE_PERIOD_DAYS = 10

if DEBUG_TOOLBAR:
INSTALLED_APPS += ["debug_toolbar"]
INTERNAL_IPS = ["127.0.0.1", "localhost"]
DEBUG_TOOLBAR_CONFIG = {
"SHOW_TOOLBAR_CALLBACK": lambda x: True,
"ROOT_TAG_EXTRA_ATTRS": "hx-preserve",
}
MIDDLEWARE.append("debug_toolbar.middleware.DebugToolbarMiddleware")
6 changes: 6 additions & 0 deletions config/test_settings.py
Original file line number Diff line number Diff line change
Expand Up @@ -18,6 +18,12 @@ def __getitem__(self, item):

DEBUG = False

OAUTH2_PROVIDER_APPLICATION_MODEL = "oauth2_provider.Application"
OAUTH2_PROVIDER_ACCESS_TOKEN_MODEL = "oauth2_provider.AccessToken"
OAUTH2_PROVIDER_ID_TOKEN_MODEL = "oauth2_provider.IDToken"
OAUTH2_PROVIDER_GRANT_MODEL = "oauth2_provider.Grant"
OAUTH2_PROVIDER_REFRESH_TOKEN_MODEL = "oauth2_provider.RefreshToken"

EMAIL_BACKEND = "django.core.mail.backends.locmem.EmailBackend"

MIGRATION_MODULES = DisableMigrations()
Expand Down
17 changes: 16 additions & 1 deletion config/urls.py
Original file line number Diff line number Diff line change
@@ -1,3 +1,5 @@
import logging

from django.conf import settings
from django.conf.urls.static import static
from django.contrib import admin
Expand All @@ -13,6 +15,7 @@
NotFoundView,
OKView,
)
from config.settings import DEBUG_TOOLBAR
from core.views import (
BSLView,
CalendarView,
Expand Down Expand Up @@ -78,6 +81,17 @@
VersionDetail,
)

djdt_urls = []
try:
if DEBUG_TOOLBAR:
from debug_toolbar.toolbar import debug_toolbar_urls

djdt_urls = debug_toolbar_urls()
except ModuleNotFoundError:
logging.error(
"DEBUG_TOOLBAR enabled but Django Debug Toolbar not installed. Run `just build`"
)

register_converter(BoostVersionSlugConverter, "boostversionslug")

router = routers.SimpleRouter()
Expand Down Expand Up @@ -358,11 +372,12 @@
),
# Static content
re_path(
r"^(?P<content_path>.+)/?",
r"^(?!__debug__)(?P<content_path>.+)/?",
StaticContentTemplateView.as_view(),
name="static-content-page",
),
]
+ djdt_urls
)

handler404 = "ak.views.custom_404_view"
6 changes: 6 additions & 0 deletions docker-compose.yml
Original file line number Diff line number Diff line change
Expand Up @@ -25,6 +25,8 @@ services:
build:
context: .
dockerfile: docker/Dockerfile
args:
LOCAL_DEVELOPMENT: "true"
command: [ "/bin/bash", "/code/docker/compose-start.sh" ]
depends_on:
- db
Expand Down Expand Up @@ -96,6 +98,8 @@ services:
/code/docker/wait-for-it.sh -h web -p 8000 -t 20 -- celery -A config worker --concurrency=10 -P gevent --loglevel=debug
networks:
- backend
environment:
DEBUG_TOOLBAR: "false"
env_file:
- .env
depends_on:
Expand All @@ -109,6 +113,8 @@ services:
context: .
dockerfile: docker/Dockerfile
command: [ "celery", "-A", "config", "beat", "--loglevel=debug" ]
environment:
DEBUG_TOOLBAR: "false"
env_file:
- .env
depends_on:
Expand Down
9 changes: 9 additions & 0 deletions docker/Dockerfile
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,8 @@

FROM python:3.11-slim AS builder-py

ARG LOCAL_DEVELOPMENT

RUN apt update && apt install -y build-essential gcc python-dev-is-python3 libpq-dev postgresql-client ruby ruby-dev && rm -rf /var/lib/apt/lists/*

# Install ruby's asciidoctor.
Expand All @@ -13,6 +15,8 @@ RUN pip install --upgrade pip
# Boostrap uv.
RUN pip install 'uv>=0.2.27,<0.3'
COPY ./requirements.txt ./code/requirements.txt
COPY ./requirements-dev.txt ./code/requirements-dev.txt


# Create the virtualenv.
RUN uv venv venv
Expand All @@ -22,6 +26,11 @@ RUN --mount=type=cache,target=/root/.cache \
. /venv/bin/activate && \
uv pip install -r /code/requirements.txt

RUN --mount=type=cache,target=/root/.cache if [ "${LOCAL_DEVELOPMENT}" = "true" ]; then \
. /venv/bin/activate && \
uv pip install -r /code/requirements-dev.txt; \
fi


# Builder step for JS.
FROM node:22-slim AS builder-js
Expand Down
16 changes: 16 additions & 0 deletions docs/development_setup_notes.md
Original file line number Diff line number Diff line change
Expand Up @@ -340,3 +340,19 @@ Setup should be complete and you should be able to see an option to "Use Google"

#### Additional Notes:
**Working locally**: If you need to run through the login flows multiple times, create a superuser so you can log into the admin. Then, log into the admin and delete your "Social Account" from the admin. This will test a fresh connection to GitHub for your logged-in GitHub user.

### Debugging
For local development there is Django Debug Toolbar, and the option to set a debugger.

#### Common Options
In your env:
- Django Debug Toolbar, enabled by default, can be disabled by setting DEBUG_TOOLBAR=False
- IDE Debugging, disabled by default, can be enabled by uncommenting `PYTHONBREAKPOINT` in your .env file.


#### Set Up Pycharm
You can set up your IDE with a new "Python Debug Server" configuration as:
<img src="images/pycharm_debugger_settings.png" alt="The GitHub screen that registers a new OAuth app" width="400">

#### Common Usage
To use the debugger add `breakpoint()` somewhere before you want to start debugging and then add breakpoints by clicking on the gutter. The debugger will stop at these point, you can then step/inspect the variables.
Binary file added docs/images/pycharm_debugger_settings.png
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
5 changes: 5 additions & 0 deletions env.template
Original file line number Diff line number Diff line change
Expand Up @@ -55,3 +55,8 @@ GOOGLE_OAUTH_CLIENT_ID=
GOOGLE_OAUTH_CLIENT_SECRET=

SLACK_BOT_TOKEN=changeme
DEBUG_TOOLBAR=True
# uncomment whichever is appropriate for your editor
# currently only pycharm is supported, vscode kept for example of alternative options
# PYTHONBREAKPOINT=pycharm_debugger.set_trace
# PYTHONBREAKPOINT=vscode_debugger.set_trace
5 changes: 3 additions & 2 deletions justfile
Original file line number Diff line number Diff line change
Expand Up @@ -51,10 +51,10 @@ alias shell := console
docker compose --file docker-compose.yml run --rm web python manage.py migrate --noinput

@test_pytest: ## runs pytest
-docker compose run --rm web pytest -s --create-db
-docker compose run --rm -e DEBUG_TOOLBAR="False" web pytest -s --create-db

@test_pytest_asciidoctor: ## runs asciidoctor tests
-docker compose run --rm web pytest -m asciidoctor -s
-docker compose run --rm -e DEBUG_TOOLBAR="False" web pytest -m asciidoctor -s --create-db

@test_interrogate: ## runs interrogate tests
docker compose run --rm web interrogate -vv --fail-under 100 --whitelist-regex "test_.*" .
Expand Down Expand Up @@ -122,6 +122,7 @@ alias shell := console
# Dependency management
@pip-compile ARGS='': ## rebuilds our pip requirements
docker compose run --rm web uv pip compile {{ ARGS }} ./requirements.in --no-strip-extras --output-file ./requirements.txt
docker compose run --rm web uv pip compile {{ ARGS }} ./requirements-dev.in --no-strip-extras --output-file ./requirements-dev.txt

@pip-compile-upgrade: ## Upgrade existing Python dependencies to their latest versions
just pip-compile --upgrade
13 changes: 13 additions & 0 deletions pycharm_debugger.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,13 @@
def set_trace():
import pydevd_pycharm

# this ip address is for the gateway IP, equivalent to host.docker.internal which
# isn't available on all platforms
gateway_ip = "172.17.0.1"
pydevd_pycharm.settrace(
host=gateway_ip,
port=12345, # Use the same port number configured in PyCharm
stdoutToServer=True,
stderrToServer=True,
suspend=False,
)
3 changes: 3 additions & 0 deletions requirements-dev.in
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
-c requirements.txt
django-debug-toolbar
pydevd-pycharm==242.23726.102 # pinned to appropriate version for current pycharm
19 changes: 19 additions & 0 deletions requirements-dev.txt
Original file line number Diff line number Diff line change
@@ -0,0 +1,19 @@
# This file was autogenerated by uv via the following command:
# uv pip compile ./requirements-dev.in --no-strip-extras --output-file ./requirements-dev.txt
asgiref==3.8.1
# via
# -c ./requirements.txt
# django
django==4.2.16
# via
# -c ./requirements.txt
# django-debug-toolbar
django-debug-toolbar==4.4.6
# via -r ./requirements-dev.in
pydevd-pycharm==242.23726.102
# via -r ./requirements-dev.in
sqlparse==0.5.1
# via
# -c ./requirements.txt
# django
# django-debug-toolbar

0 comments on commit f233f27

Please sign in to comment.