Skip to content

Commit

Permalink
lifecycle: much improved debugging experience
Browse files Browse the repository at this point in the history
Signed-off-by: Jens Langhammer <jens@goauthentik.io>
  • Loading branch information
BeryJu committed Jan 24, 2025
1 parent 62187e6 commit 0ff63e4
Show file tree
Hide file tree
Showing 14 changed files with 76 additions and 25 deletions.
7 changes: 4 additions & 3 deletions .vscode/extensions.json
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,7 @@
"recommendations": [
"bashmish.es6-string-css",
"bpruitt-goddard.mermaid-markdown-syntax-highlighting",
"charliermarsh.ruff",
"dbaeumer.vscode-eslint",
"EditorConfig.EditorConfig",
"esbenp.prettier-vscode",
Expand All @@ -10,12 +11,12 @@
"Gruntfuggly.todo-tree",
"mechatroner.rainbow-csv",
"ms-python.black-formatter",
"charliermarsh.ruff",
"ms-python.black-formatter",
"ms-python.debugpy",
"ms-python.python",
"ms-python.vscode-pylance",
"ms-python.black-formatter",
"redhat.vscode-yaml",
"Tobermory.es6-string-html",
"unifiedjs.vscode-mdx"
"unifiedjs.vscode-mdx",
]
}
22 changes: 15 additions & 7 deletions .vscode/launch.json
Original file line number Diff line number Diff line change
Expand Up @@ -2,26 +2,34 @@
"version": "0.2.0",
"configurations": [
{
"name": "Python: PDB attach Server",
"type": "python",
"name": "Debug: Attach Server Core",
"type": "debugpy",
"request": "attach",
"connect": {
"host": "localhost",
"port": 6800
"port": 9901
},
"justMyCode": true,
"django": true
"django": true,
},
{
"name": "Python: PDB attach Worker",
"type": "python",
"name": "Debug: Attach Worker",
"type": "debugpy",
"request": "attach",
"connect": {
"host": "localhost",
"port": 6900
"port": 9901
},
"justMyCode": true,
"django": true
},
{
"name": "Debug: Attach Server Router",
"type": "go",
"request": "launch",
"mode": "auto",
"program": "${workspaceFolder}/cmd/server",
"cwd": "${workspaceFolder}"
}
]
}
2 changes: 2 additions & 0 deletions authentik/core/management/commands/dev_server.py
Original file line number Diff line number Diff line change
Expand Up @@ -5,6 +5,7 @@
from daphne.management.commands.runserver import Command as RunServer
from daphne.server import Server

from authentik.lib.debug import start_debug_server
from authentik.root.signals import post_startup, pre_startup, startup


Expand All @@ -13,6 +14,7 @@ class SignalServer(Server):

def __init__(self, *args, **kwargs):
super().__init__(*args, **kwargs)
start_debug_server()

def ready_callable():
pre_startup.send(sender=self)
Expand Down
6 changes: 2 additions & 4 deletions authentik/core/management/commands/worker.py
Original file line number Diff line number Diff line change
Expand Up @@ -9,6 +9,7 @@
from structlog.stdlib import get_logger

from authentik.lib.config import CONFIG
from authentik.lib.debug import start_debug_server
from authentik.root.celery import CELERY_APP

LOGGER = get_logger()
Expand All @@ -28,10 +29,7 @@ def add_arguments(self, parser):
def handle(self, **options):
LOGGER.debug("Celery options", **options)
close_old_connections()
if CONFIG.get_bool("remote_debug"):
import debugpy

debugpy.listen(("0.0.0.0", 6900)) # nosec
start_debug_server()
worker: Worker = CELERY_APP.Worker(
no_color=False,
quiet=True,
Expand Down
2 changes: 1 addition & 1 deletion authentik/lib/config.py
Original file line number Diff line number Diff line change
Expand Up @@ -421,4 +421,4 @@ def django_db_config(config: ConfigLoader | None = None) -> dict:
if len(argv) < 2: # noqa: PLR2004
print(dumps(CONFIG.raw, indent=4, cls=AttrEncoder))
else:
print(CONFIG.get(argv[1]))
print(CONFIG.get(argv[-1]))
23 changes: 23 additions & 0 deletions authentik/lib/debug.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,23 @@
from structlog.stdlib import get_logger

from authentik.lib.config import CONFIG

LOGGER = get_logger()

def start_debug_server(**kwargs) -> bool:
"""Attempt to start a debugpy server in the current process.
Returns true if the server was started successfully, otherwise false"""
if not CONFIG.get_bool("debug"):
return
try:
import debugpy
except ImportError:
LOGGER.warning("Failed to import debugpy. debugpy is not included "
"in the default release dependencies and must be installed manually")
return False

listen: str = CONFIG.get("listen.listen_debug_py", "127.0.0.1:9901")
host, _, port = listen.rpartition(":")
debugpy.listen((host, int(port)), **kwargs) # nosec
LOGGER.debug("Starting debug server", host=host, port=port)
return True
2 changes: 1 addition & 1 deletion authentik/lib/default.yml
Original file line number Diff line number Diff line change
Expand Up @@ -21,6 +21,7 @@ listen:
listen_radius: 0.0.0.0:1812
listen_metrics: 0.0.0.0:9300
listen_debug: 0.0.0.0:9900
listen_debug_py: 0.0.0.0:9901
trusted_proxy_cidrs:
- 127.0.0.0/8
- 10.0.0.0/8
Expand Down Expand Up @@ -57,7 +58,6 @@ cache:
# transport_options: ""

debug: false
remote_debug: false

log_level: info

Expand Down
1 change: 0 additions & 1 deletion internal/debug/debug.go
Original file line number Diff line number Diff line change
Expand Up @@ -15,7 +15,6 @@ import (
func EnableDebugServer() {
l := log.WithField("logger", "authentik.go_debugger")
if !config.Get().Debug {
l.Info("not enabling debug server, set `AUTHENTIK_DEBUG` to `true` to enable it.")
return
}
h := mux.NewRouter()
Expand Down
4 changes: 2 additions & 2 deletions lifecycle/ak
Original file line number Diff line number Diff line change
Expand Up @@ -62,7 +62,7 @@ function prepare_debug {
chown authentik:authentik /unittest.xml
}

if [[ "${AUTHENTIK_REMOTE_DEBUG}" == "true" ]]; then
if [[ "$(python -m authentik.lib.config debug 2> /dev/null)" == "True" ]]; then
prepare_debug
fi

Expand Down Expand Up @@ -92,7 +92,7 @@ elif [[ "$1" == "test-all" ]]; then
elif [[ "$1" == "healthcheck" ]]; then
run_authentik healthcheck $(cat $MODE_FILE)
elif [[ "$1" == "dump_config" ]]; then
exec python -m authentik.lib.config
exec python -m authentik.lib.config $@
elif [[ "$1" == "debug" ]]; then
exec sleep infinity
else
Expand Down
7 changes: 2 additions & 5 deletions lifecycle/gunicorn.conf.py
Original file line number Diff line number Diff line change
Expand Up @@ -13,6 +13,7 @@

from authentik import get_full_version
from authentik.lib.config import CONFIG
from authentik.lib.debug import start_debug_server
from authentik.lib.logging import get_logger_config
from authentik.lib.utils.http import get_http_session
from authentik.lib.utils.reflection import get_env
Expand Down Expand Up @@ -146,9 +147,5 @@ def post_worker_init(worker: DjangoUvicornWorker):
except Exception: # nosec
pass

if CONFIG.get_bool("remote_debug"):
import debugpy

debugpy.listen(("0.0.0.0", 6800)) # nosec

start_debug_server()
run_migrations()
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
21 changes: 21 additions & 0 deletions website/docs/developer-docs/setup/debugging.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,21 @@
---
title: Debugging authentik
---

This page describes how to debug different parts of an authentik instance, running either in production or in a development setup.

## authentik Server & Worker - Python

The majority of the authentik codebase is in Python, running in gunicorn for the server and celery for the worker. These instructions show how this code can be debugged/inspected.

Note that authentik uses [debugpy](https://github.com/microsoft/debugpy), which relies on the "Debug Adapter Protocol". These instructions demonstrate debugging using [Visual Studio Code](https://code.visualstudio.com/), however they should be adaptable to other editors which support DAP.

To enable the debugging server, set the environment variable `AUTHENTIK_DEBUG` to `true`. This will by default launch the debugging server on port 9901.

With this setup in place, you can set Breakpoints in VS Code. To connect to the debugging server, run the command `> Debug: Start Debugging" in VS Code.

![](./debug_vscode.png)

:::info
Note that due to the Python debugger for VS Code, when a python file in authentik is saved and the Django process restarts, you must manually reconnect the Debug session. Automatic re-connection is not supported for the Python debugger (see [here](https://github.com/microsoft/vscode-python/issues/19998) and [here](https://github.com/microsoft/vscode-python/issues/1182))
:::
Original file line number Diff line number Diff line change
Expand Up @@ -167,6 +167,7 @@ Additionally, you can set `AUTHENTIK_POSTGRESQL__CONN_HEALTH_CHECK` to perform h
- `AUTHENTIK_LISTEN__LDAPS`: Listening address:port (e.g. `0.0.0.0:6636`) for LDAPS (Applies to LDAP outpost)
- `AUTHENTIK_LISTEN__METRICS`: Listening address:port (e.g. `0.0.0.0:9300`) for Prometheus metrics (Applies to All)
- `AUTHENTIK_LISTEN__DEBUG`: Listening address:port (e.g. `0.0.0.0:9900`) for Go Debugging metrics (Applies to All)
- `AUTHENTIK_LISTEN__DEBUG_PY`: Listening address:port (e.g. `0.0.0.0:9901`) for Python debugging server (Applies to Server, see [Debugging](../../developer-docs/setup/debugging.md))
- `AUTHENTIK_LISTEN__TRUSTED_PROXY_CIDRS`: List of comma-separated CIDRs that proxy headers should be accepted from (Applies to Server)

Defaults to `127.0.0.0/8`, `10.0.0.0/8`, `172.16.0.0/12`, `192.168.0.0/16`, `fe80::/10`, `::1/128`.
Expand Down
3 changes: 2 additions & 1 deletion website/sidebars.js
Original file line number Diff line number Diff line change
Expand Up @@ -607,11 +607,12 @@ export default {
items: [
{
type: "category",
label: "Setup",
label: "Development environment",
items: [
"developer-docs/setup/full-dev-environment",
"developer-docs/setup/frontend-dev-environment",
"developer-docs/setup/website-dev-environment",
"developer-docs/setup/debugging",
],
},
{
Expand Down

0 comments on commit 0ff63e4

Please sign in to comment.