created a plugin for authentik / auth request#200
Conversation
|
No actionable comments were generated in the recent review. 🎉 ℹ️ Recent review info⚙️ Run configurationConfiguration used: Repository UI Review profile: ASSERTIVE Plan: Pro Run ID: 📒 Files selected for processing (2)
📜 Recent review details🧰 Additional context used📓 Path-based instructions (1)**/plugin.json⚙️ CodeRabbit configuration file
Files:
🔇 Additional comments (2)
Authentik Plugin (New)Summary
Functional behaviour
User-visible changes
Configuration / plugin.json schema
Documentation
Security impact & notes
Compatibility / packaging / deployment
Tests
Impact summary for reviewers
WalkthroughAdds a new Authentik forward-auth plugin: plugin schema, Lua access-phase handler performing Authentik outpost subrequests, Nginx outpost proxy template, full plugin documentation, and repository housekeeping (.gitignore and README link). ChangesAuthentik Plugin Implementation
Estimated code review effort🎯 3 (Moderate) | ⏱️ ~25 minutes Poem
🚥 Pre-merge checks | ✅ 1 | ❌ 1❌ Failed checks (1 inconclusive)
✅ Passed checks (1 passed)
✏️ Tip: You can configure your own custom pre-merge checks in the settings. Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out. Comment |
There was a problem hiding this comment.
Actionable comments posted: 4
🤖 Prompt for all review comments with AI agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.
Inline comments:
In `@authentik/authentik.lua`:
- Around line 151-156: The loop that forwards identity headers uses exact key
lookup on res.headers (for _, h in
ipairs(split_headers(self.variables["AUTHENTIK_IDENTITY_HEADERS"])) ... local
value = res.headers[h]) which fails when header casing differs; update the
forwarding in the block that calls ngx_req.clear_header and ngx_req.set_header
to perform a case-insensitive lookup on res.headers (for example, check
res.headers[h] first, then res.headers[string.lower(h)] or build a lowercased
copy of res.headers once and read from that) so split_headers, the loop that
references res.headers, and the set_header/clear_header calls forward the header
values regardless of case.
In `@authentik/confs/server-http/authentik.conf`:
- Line 1: The template currently only checks USE_AUTHENTIK in authentik.conf and
can render an empty proxy_pass when AUTHENTIK_URL is unset; update the template
guard (the if that references USE_AUTHENTIK) to also verify AUTHENTIK_URL is
non-empty before emitting the authentik block, and apply the same non-empty
check around the proxy_pass lines (the proxy_pass entries on lines that
currently reference AUTHENTIK_URL) so Nginx never gets an empty target; refer to
the USE_AUTHENTIK and AUTHENTIK_URL variables and the proxy_pass entries in
authentik.conf when making this change.
In `@authentik/plugin.json`:
- Line 86: The current "regex" allows any header token; update it to only permit
header names that start with "X-authentik-" (case-insensitive) so the
identity-header allowlist can't include unrelated headers. Replace the existing
value for the "regex" property with a pattern enforcing case-insensitive
"X-authentik-" prefix followed by token chars and allowing multiple entries
separated by commas/spaces (e.g. use an inline case-insensitive regex such as
(?i)^X-authentik-[A-Za-z0-9-]+([ ,]+X-authentik-[A-Za-z0-9-]+)*$) so the schema
and the Lua flow only accept X-authentik-* headers.
In `@authentik/README.md`:
- Around line 136-149: The settings table in authentik/README.md is manually
maintained and must be regenerated from plugin.json; run the generation script
.tests/misc/json2md.py against this plugin's plugin.json and replace the current
hardcoded Settings table with the output so docs stay in sync. Locate
README.md's Settings section and plugin.json in the same module, run
.tests/misc/json2md.py to produce the markdown table, and commit the updated
README.md ensuring the generated table replaces the existing table (do not
hand-edit the rows).
🪄 Autofix (Beta)
Fix all unresolved CodeRabbit comments on this PR:
- Push a commit to this branch (recommended)
- Create a new PR with the fixes
ℹ️ Review info
⚙️ Run configuration
Configuration used: Repository UI
Review profile: ASSERTIVE
Plan: Pro
Run ID: 85d93dd3-d9c8-4791-ad0d-282147e90e3f
📒 Files selected for processing (6)
.gitignoreREADME.mdauthentik/README.mdauthentik/authentik.luaauthentik/confs/server-http/authentik.confauthentik/plugin.json
📜 Review details
🧰 Additional context used
📓 Path-based instructions (3)
**/*.md
⚙️ CodeRabbit configuration file
**/*.md: Documentation should be concise, accurate, and written in British English:
- Keep the structure clear with a sensible heading hierarchy.
- Each plugin README contains a settings table generated from
plugin.jsonvia.tests/misc/json2md.py; regenerate it whenever settings change rather than hand-editing the table.- The repository README shows a compatibility badge tied to the plugins-collection version in
COMPATIBILITY.json— keep it in sync with any version bump.- Prefer concrete instructions, accurate examples, and explicit prerequisites (Docker,
sudo, required env vars likeVIRUSTOTAL_API_KEY).- When a PR changes behaviour, defaults, packaging, or security posture, ask for the corresponding documentation update.
Files:
README.mdauthentik/README.md
**/*.lua
⚙️ CodeRabbit configuration file
**/*.lua: Lua code runs on OpenResty inside the BunkerWeb nginx container and sits on the request hot path:
- Every plugin subclasses
bunkerweb.pluginviamiddleclass:local <name> = class("<name>", plugin)andplugin.initialize(self, "<id>", ctx)ininitialize. Hook methods (init_worker,access,log,preread, ...) must returnself:ret(ok_bool, msg, [http_status]). To deny a request, returnself:ret(true, "reason", utils.get_deny_status()).- Gate expensive work at
init_workerwithutils.has_variable("USE_<PLUGIN>", "yes")and skip whenself.is_loadingis true, matching the pattern used acrossclamav.lua,coraza.lua, andvirustotal.lua.- Use local variables and local module tables; avoid globals. Cache
ngx.var.*andngx.req.*values in locals instead of re-reading them repeatedly.- Precompile regular expressions in module-level locals; never compile inside request loops. For
ngx.re.match/find/gmatch/sub, pass the option string"jo"(jenables PCRE JIT,ocompiles the pattern once and caches it), anchor patterns with^...$when a full match is intended, and cap input length before matching to prevent ReDoS.- Validate and sanitise all request-derived input. Never evaluate request-derived code via
load,loadstring, or similar mechanisms.- Use
ngx.socketfor raw TCP (see the ClamAV INSTREAM pattern inclamav.lua) andresty.httpfor HTTP upstreams (seevirustotal.luaandcoraza.lua). Preferresty.uploadfor streaming request bodies —clamav.luais the reference.- Cache upstream scan results by a strong digest of the body (SHA-512 in
virustotal.lua) rather than by filename or weaker hashes; mind cache key length.- Shared-dictionary read-modify-write sequences are race-prone; prefer atomic operations such as
incror explicit locking where correctness matters.- Never log request bodies, cookies, bearer tokens, webhook secrets, or API keys.
- Use
pcallor explicit error...
Files:
authentik/authentik.lua
**/plugin.json
⚙️ CodeRabbit configuration file
**/plugin.json:plugin.jsonfiles define the settings schema that BunkerWeb reads to register settings and render the UI:
- The top-level fields
id,name,version, andstream(yes/no/partial) must stay consistent with the plugin directory name and its Lua module.- Ensure setting IDs remain stable unless there is an intentional breaking change documented in the PR.
- Each setting must declare
context(globalormultisite),default,help,id,label,regex, andtype. Regex validators must be anchored where appropriate, compile cleanly, and avoid catastrophic backtracking. Default values must satisfy their own validators.USE_<PLUGIN>toggles are the standard gate forinit_workershort-circuiting; keep them in sync with the Lua implementation.- Bump the per-plugin
versionfield through./misc/update_version.sh <new_version>so everyplugin.jsonand the README badge move together. Do not edit the version in a singleplugin.jsonby hand.- If a PR changes a setting ID, type, context, accepted value shape, or compatibility behaviour, require migration notes and confirm that the README settings table is regenerated via
.tests/misc/json2md.py.
Files:
authentik/plugin.json
🪛 LanguageTool
authentik/README.md
[uncategorized] ~35-~35: A comma may be missing after the conjunctive/linking adverb ‘Otherwise’.
Context: ... flow itself, served by the outpost. 3. Otherwise the handler does an HTTP GET against ...
(SENT_START_CONJUNCTIVE_LINKING_ADVERB_COMMA)
[uncategorized] ~40-~40: Use a comma before ‘so’ if it connects two independent clauses (unless they are closely connected and short).
Context: ... Authentik is relayed to the client so the session refreshes correctly. - *...
(COMMA_COMPOUND_SENTENCE_2)
[uncategorized] ~63-~63: Possible missing comma found.
Context: ...ed to be able to reach that public URL; otherwise login redirects from `/outpost.../start...
(AI_HYDRA_LEO_MISSING_COMMA)
[uncategorized] ~131-~131: Possible missing comma found.
Context: ...'s response. 4. In the Authentik server logs you should see one `/outpost.goauthenti...
(AI_HYDRA_LEO_MISSING_COMMA)
[formatting] ~152-~152: Insert a comma before quoting reported speech: “says, "”…
Context: ...0 on every protected URL, scheduler log says "AUTHENTIK_URL not configured".** `USE_...
(SAID_COMMA_SPEECH)
[uncategorized] ~172-~172: Possible missing comma found.
Context: ...ntity headers downstream (opt-in).** By default this plugin only gates access and for...
(AI_HYDRA_LEO_MISSING_COMMA)
I originally managed this through config files, but as the number grew, it became messy and hard to maintain. To streamline the process, I developed a plugin to organize everything more cleanly. Since others might find it useful, I decided to share it here.