#!/bin/sh # --------------------------------------------------------------------------- # WeBrake installer — run INSIDE an existing Alpine Linux LXC container. # # wget -qO- https://gogs.av2x.dev/av2x/WeBrake/raw/main/install.sh | ash # # This script never touches the Proxmox host. It: # 1. Installs Python, HandBrakeCLI and VA-API drivers via apk # 2. Pulls app.py / index.html / update.sh from the repo # 3. Generates a local token.json (never fetched from, or pushed to, the repo) # 4. Registers and starts an OpenRC service # --------------------------------------------------------------------------- set -eu REPO_RAW="${WEBRAKE_REPO:-https://gogs.av2x.dev/av2x/WeBrake/raw/main}" APP_DIR="/opt/webrake" DATA_DIR="/var/lib/webrake" PORT="${WEBRAKE_PORT:-8090}" say() { printf '\033[1;33m[WeBrake]\033[0m %s\n' "$*"; } die() { printf '\033[1;31m[WeBrake]\033[0m %s\n' "$*" >&2; exit 1; } # --- sanity: Alpine, root, inside a container ------------------------------- [ "$(id -u)" = "0" ] || die "Run as root inside the Alpine container." [ -f /etc/alpine-release ] || die "This installer only supports Alpine Linux (run it inside the LXC, not on the Proxmox host)." if [ -r /proc/1/environ ] && grep -qa 'container=' /proc/1/environ 2>/dev/null; then :; fi say "Installing packages via apk..." # HandBrake lives in the community repository — make sure it is enabled. if ! grep -Eq '^[^#].*community' /etc/apk/repositories; then ALPINE_VER=$(cut -d. -f1,2 /etc/alpine-release) echo "https://dl-cdn.alpinelinux.org/alpine/v${ALPINE_VER}/community" >> /etc/apk/repositories say "Enabled the Alpine community repository." fi apk update apk add --no-cache python3 py3-flask wget ca-certificates if ! apk add --no-cache handbrake >/dev/null 2>&1; then say "handbrake not in this release's community repo — trying edge/community..." apk add --no-cache handbrake \ --repository=https://dl-cdn.alpinelinux.org/alpine/edge/community \ --repository=https://dl-cdn.alpinelinux.org/alpine/edge/main \ || die "Could not install HandBrakeCLI via apk. Install it manually, then re-run." fi # VA-API / QSV userspace drivers (harmless if no GPU is passed through) apk add --no-cache libva libva-utils mesa-va-gallium intel-media-driver 2>/dev/null || \ say "GPU driver packages unavailable on this release — software encoding will still work." command -v HandBrakeCLI >/dev/null || die "HandBrakeCLI is not on PATH after install." say "HandBrake: $(HandBrakeCLI --version 2>&1 | head -n1)" # --- fetch application files from the repo ---------------------------------- say "Pulling application files from ${REPO_RAW} ..." mkdir -p "$APP_DIR" "$DATA_DIR" for f in app.py index.html update.sh; do wget -q -O "$APP_DIR/$f.new" "$REPO_RAW/$f" || die "Failed to fetch $f from the repo." mv "$APP_DIR/$f.new" "$APP_DIR/$f" done chmod +x "$APP_DIR/update.sh" # --- generate token.json locally (NEVER pulled from or pushed to the repo) -- if [ ! -f "$APP_DIR/token.json" ]; then say "Generating local token.json ..." python3 - "$APP_DIR/token.json" <<'PY' import json, secrets, sys, os path = sys.argv[1] with open(path, "w") as f: json.dump({ "api_token": secrets.token_urlsafe(32), "secret_key": secrets.token_urlsafe(32), "note": "Generated locally by WeBrake. Do not commit this file." }, f, indent=2) os.chmod(path, 0o600) PY else say "Existing token.json found — keeping it." fi # --- OpenRC service ---------------------------------------------------------- say "Registering OpenRC service..." cat > /etc/init.d/webrake </dev/null 2>&1 || true rc-service webrake restart >/dev/null 2>&1 || rc-service webrake start IP=$(ip -4 addr show scope global 2>/dev/null | awk '/inet /{print $2}' | cut -d/ -f1 | head -n1) TOKEN=$(python3 -c "import json;print(json.load(open('$APP_DIR/token.json'))['api_token'])") say "----------------------------------------------------------------" say "WeBrake is up." say " URL: http://${IP:-}:${PORT}" say " API token: ${TOKEN}" say " Token file: $APP_DIR/token.json (local only — never in the repo)" say " Update: $APP_DIR/update.sh" if [ ! -e /dev/dri ] && [ ! -e /dev/nvidia0 ]; then say " GPU: no /dev/dri or /dev/nvidia* visible. To enable hardware" say " encoding, add a device passthrough to this container's" say " config on the Proxmox host (see README), then restart it." fi say "----------------------------------------------------------------"