Initial commit
This commit is contained in:
commit
32d9e15843
15 changed files with 5589 additions and 0 deletions
25
Dockerfile
Normal file
25
Dockerfile
Normal file
|
@ -0,0 +1,25 @@
|
||||||
|
## Buildstage ##
|
||||||
|
FROM ghcr.io/linuxserver/baseimage-alpine:3.12 as buildstage
|
||||||
|
|
||||||
|
# The verison of oauth2-proxy to use
|
||||||
|
ARG PROXY_VERSION
|
||||||
|
# The architecture (amd64/arm64) to use
|
||||||
|
ARG ARCHITECTURE
|
||||||
|
|
||||||
|
RUN \
|
||||||
|
echo "**** downloading oauth2-proxy ****" && \
|
||||||
|
mkdir -p /root-layer && \
|
||||||
|
wget -O - \
|
||||||
|
https://github.com/oauth2-proxy/oauth2-proxy/releases/download/v$PROXY_VERSION/oauth2-proxy-v$PROXY_VERSION.linux-$ARCHITECTURE.tar.gz | \
|
||||||
|
tar -Ozxf - \
|
||||||
|
oauth2-proxy-v$PROXY_VERSION.linux-$ARCHITECTURE/oauth2-proxy > /root-layer/oauth2-proxy && \
|
||||||
|
chmod +x /root-layer/oauth2-proxy
|
||||||
|
|
||||||
|
# copy local files
|
||||||
|
COPY root/ /root-layer/
|
||||||
|
|
||||||
|
## Single layer deployed image ##
|
||||||
|
FROM scratch
|
||||||
|
|
||||||
|
# Add files from buildstage
|
||||||
|
COPY --from=buildstage /root-layer/ /
|
21
LICENSE
Normal file
21
LICENSE
Normal file
|
@ -0,0 +1,21 @@
|
||||||
|
MIT License
|
||||||
|
|
||||||
|
Copyright (c) 2024 Tyler Beckman
|
||||||
|
|
||||||
|
Permission is hereby granted, free of charge, to any person obtaining a copy
|
||||||
|
of this software and associated documentation files (the "Software"), to deal
|
||||||
|
in the Software without restriction, including without limitation the rights
|
||||||
|
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
||||||
|
copies of the Software, and to permit persons to whom the Software is
|
||||||
|
furnished to do so, subject to the following conditions:
|
||||||
|
|
||||||
|
The above copyright notice and this permission notice shall be included in all
|
||||||
|
copies or substantial portions of the Software.
|
||||||
|
|
||||||
|
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||||
|
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||||
|
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
||||||
|
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
||||||
|
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
||||||
|
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
|
||||||
|
SOFTWARE.
|
26
README.md
Normal file
26
README.md
Normal file
|
@ -0,0 +1,26 @@
|
||||||
|
# Oauth2 qBittorrent mod
|
||||||
|
|
||||||
|
This is a docker mod compatible with the qBittorrent container at https://github.com/linuxserver/docker-qbittorrent, which integrates Oauth2 (with OpenID Connect) into the WebUI authentication.
|
||||||
|
|
||||||
|
## Versioning
|
||||||
|
|
||||||
|
Because all this does is add another program to the qBittorrent container, the versioning is primarily based on oauth2-proxy versioning. The docker tagging format follows the following format: `git.myriation.xyz/myriation/oauth2-qbittorrent-mod:v<PROXY_VERSION>-r<MOD_REVISION>[-ARCHITECTURE]`. For example, the tag `git.myriation.xyz/myriation/oauth2-qbittorrent-mod:v7.5.1-r0-arm64` would reference the first revision of the mod that uses version 7.5.1 of oauth2-proxy, and supports only arm architectures.
|
||||||
|
|
||||||
|
## Configuration
|
||||||
|
|
||||||
|
This mod can be configured through a few environment variables as listed below. These should be provided alongside the variables provided to the qBittorrent container. All of the listed variables are required, or else this will not function correctly.
|
||||||
|
|
||||||
|
| Variable name | Description |
|
||||||
|
| ----------------- | ----------------------------------------------------------------------------------------------------------------------------------------------------------------- |
|
||||||
|
| OAUTH2_CLIENT_ID | The client ID of the oauth2 application to authenticate against |
|
||||||
|
| OAUTH2_ISSUER_URL | The issuer URL of the OIDC provider, used to fetch setup information through the discovery endpoint (`/.well-known/openid-configuration`) |
|
||||||
|
| OAUTH2_PUBLIC_URL | The root URL that qBittorrent is intended to be accessible from, used for redirect URL configuration (the redirect URL is `"$OAUTH2_PUBLIC_URL/oauth2/callback"`) |
|
||||||
|
| OAUTH2_PROXY_PORT | The port the oauth2-proxy process will listen on (this should be the port you intend to be publically accessible) |
|
||||||
|
|
||||||
|
## Important things to know when using this mod (please read before use)
|
||||||
|
|
||||||
|
Firstly, because this effectively overrides the authentication, using this will disable any attempts to login with normal authentication by replacing the login with a randomly generated password, to force any authentication attempts to pass through the proxy first. Due to how this configures qBittorrent, any request seen as "localhost" by qBittorrent will be allowed through, which notably includes requests by the oauth2-proxy process.
|
||||||
|
|
||||||
|
In addition, due to the nature of proxying requests, this requires that the port set via `$WEBUI_PORT` be set to a port that you DO NOT want qBittorrent to be accessible from. The port you want it to be accessible from should instead be set via `$OAUTH2_PROXY_PORT`, so that requests through this port will be correctly proxied and authenticated before being redirected to qBittorrent. For example, if you want qBittorrent WebUI to be accessible at :80, `$OAUTH2_PROXY_PORT` should be set to `80`, and `$WEBUI_PORT` should be set to something other than `80`, such as `81`.
|
||||||
|
|
||||||
|
Lastly, because this is mainly designed for my personal use, I modified the signin page template from oauth2-proxy to include generated [Dark Reader](https://github.com/darkreader/darkreader) css, as the light mode was blinding me and dark mode is cool. If someone besides me wants to use this, I will gladly change that to be configurable (and probably will in the future anyways, template folder should likely be configurable through a runtime env var), but as of right now, it is hardcoded to use the dark-modeified sign-in page.
|
5449
root/etc/oauth2-proxy/templates/sign_in.html
Normal file
5449
root/etc/oauth2-proxy/templates/sign_in.html
Normal file
File diff suppressed because it is too large
Load diff
46
root/etc/s6-overlay/s6-rc.d/init-oauth2-qbittorrent-config/run
Executable file
46
root/etc/s6-overlay/s6-rc.d/init-oauth2-qbittorrent-config/run
Executable file
|
@ -0,0 +1,46 @@
|
||||||
|
#!/usr/bin/with-contenv bash
|
||||||
|
# shellcheck shell=bash
|
||||||
|
|
||||||
|
## Override the webui username & password with a custom one for this session,
|
||||||
|
## to effectively make localhost requests the only valid kind. This was originally
|
||||||
|
## intended to pass directly to oauth2-proxy, but the qbittorrent auth process
|
||||||
|
## requires making a request to /api/v2/auth/login, which isn't really possible.
|
||||||
|
|
||||||
|
# Generate password and hash into an array in the format of [BASE64_SALT, PASSWORD, BASE64_HASH]
|
||||||
|
mapfile \
|
||||||
|
-d ':' \
|
||||||
|
-t generated \
|
||||||
|
< <(
|
||||||
|
python3 \
|
||||||
|
-c "from hashlib import pbkdf2_hmac; import os, base64, string, random; salt = os.urandom(16); password = ''.join(random.choices(string.ascii_uppercase+string.ascii_lowercase+string.digits, k=64)); print(f'{base64.standard_b64encode(salt).decode()}:{base64.standard_b64encode(pbkdf2_hmac(\"sha512\", password.encode(), salt, 100000)).decode()}', end='')"
|
||||||
|
)
|
||||||
|
# Detect if the qbittorrent config file has the LocalHostAuth key already (it doesn't by default)
|
||||||
|
grep -qF 'WebUI\LocalHostAuth' /config/qBittorrent/qBittorrent.conf
|
||||||
|
LOCALHOSTAUTH_MISSING=$?
|
||||||
|
# Modify the qbittorrent config file to
|
||||||
|
# 1. Replace the username & password entry (username is always DO_NOT_CHANGE)
|
||||||
|
# 2. Enable localhost whitelisting to allow oauth2-proxy to bypass auth
|
||||||
|
awk \
|
||||||
|
-v "salt=${generated[0]}" \
|
||||||
|
-v "hash=${generated[1]}" \
|
||||||
|
-v "localhostauth_missing=$LOCALHOSTAUTH_MISSING" \
|
||||||
|
'/^WebUI\\Password_PBKDF2=/ { \
|
||||||
|
printf "WebUI\\Password_PBKDF2=\"@ByteArray(%s:%s)\"\n",salt,hash; \
|
||||||
|
next; \
|
||||||
|
}; \
|
||||||
|
/^WebUI\\Username=/ { \
|
||||||
|
print "WebUI\\Username=DO_NOT_CHANGE"; \
|
||||||
|
next; \
|
||||||
|
}; \
|
||||||
|
/^WebUI\\LocalHostAuth=/ { \
|
||||||
|
print "WebUI\\LocalHostAuth=false"; \
|
||||||
|
next; \
|
||||||
|
} \
|
||||||
|
/^\[Preferences]/ { \
|
||||||
|
print;
|
||||||
|
if (localhostauth_missing == 1) print "WebUI\\LocalHostAuth=false"; \
|
||||||
|
next;
|
||||||
|
} \
|
||||||
|
{ print; }' \
|
||||||
|
/config/qBittorrent/qBittorrent.conf \
|
||||||
|
> tmp && mv tmp /config/qBittorrent/qBittorrent.conf
|
|
@ -0,0 +1 @@
|
||||||
|
oneshot
|
|
@ -0,0 +1 @@
|
||||||
|
/etc/s6-overlay/s6-rc.d/init-oauth2-qbittorrent-config/run
|
19
root/etc/s6-overlay/s6-rc.d/svc-mod-oauth2-qbittorrent/run
Executable file
19
root/etc/s6-overlay/s6-rc.d/svc-mod-oauth2-qbittorrent/run
Executable file
|
@ -0,0 +1,19 @@
|
||||||
|
#!/usr/bin/with-contenv bash
|
||||||
|
# shellcheck shell=bash
|
||||||
|
|
||||||
|
/oauth2-proxy \
|
||||||
|
--api-route '^/api/v2' \
|
||||||
|
--client-id "$OAUTH2_CLIENT_ID" \
|
||||||
|
--client-secret "NO_SECRET_NEEDED" \
|
||||||
|
--code-challenge-method 'S256' \
|
||||||
|
--cookie-secret "$(python -c 'import os,base64; print(base64.urlsafe_b64encode(os.urandom(32)).decode())')" \
|
||||||
|
--cookie-secure "true" \
|
||||||
|
--email-domain '*' \
|
||||||
|
--http-address "0.0.0.0:$OAUTH2_PROXY_PORT" \
|
||||||
|
--oidc-issuer-url "$OAUTH2_ISSUER_URL" \
|
||||||
|
--provider "oidc" \
|
||||||
|
--provider-display-name "OpenID Connect" \
|
||||||
|
--redirect-url "$OAUTH2_PUBLIC_URL/oauth2/callback" \
|
||||||
|
--scope "openid email profile" \
|
||||||
|
--upstream "http://127.0.0.1:$WEBUI_PORT" \
|
||||||
|
--custom-templates-dir /etc/oauth2-proxy/templates > /dev/null
|
|
@ -0,0 +1 @@
|
||||||
|
longrun
|
Loading…
Reference in a new issue