diff --git a/ct/authelia.sh b/ct/authelia.sh new file mode 100644 index 000000000..0831c4db1 --- /dev/null +++ b/ct/authelia.sh @@ -0,0 +1,48 @@ +#!/usr/bin/env bash +source <(curl -fsSL https://raw.githubusercontent.com/community-scripts/ProxmoxVED/main/misc/build.func) +# Copyright (c) 2021-2026 community-scripts ORG +# Author: thost96 (thost96) +# License: MIT | https://github.com/community-scripts/ProxmoxVE/raw/main/LICENSE +# Source: https://www.authelia.com/ + +APP="Authelia" +var_tags="${var_tags:-authenticator}" +var_cpu="${var_cpu:-1}" +var_ram="${var_ram:-512}" +var_disk="${var_disk:-2}" +var_os="${var_os:-debian}" +var_version="${var_version:-13}" +var_unprivileged="${var_unprivileged:-1}" + +header_info "$APP" +base_settings + +variables +color +catch_errors + +function update_script() { + header_info + check_container_storage + check_container_resources + if [[ ! -d /etc/authelia/ ]]; then + msg_error "No ${APP} Installation Found!" + exit + fi + + if check_for_gh_release "authelia" "authelia/authelia"; then + $STD apt update + $STD apt -y upgrade + fetch_and_deploy_gh_release "authelia" "authelia/authelia" "binary" + msg_ok "Updated successfully!" + fi + exit +} +start +build_container +description + +msg_ok "Completed successfully!\n" +echo -e "${CREATING}${GN}${APP} setup has been successfully initialized!${CL}" +echo -e "${INFO}${YW} Access it using the following URL:${CL}" +echo -e "${TAB}${GATEWAY}${BGN}http://${IP}:9091 or https://auth.YOURDOMAIN ${CL}" diff --git a/install/authelia-install.sh b/install/authelia-install.sh new file mode 100644 index 000000000..010be6cab --- /dev/null +++ b/install/authelia-install.sh @@ -0,0 +1,107 @@ +#!/usr/bin/env bash + +# Copyright (c) 2021-2026 community-scripts ORG +# Author: thost96 (thost96) +# License: MIT | https://github.com/community-scripts/ProxmoxVE/raw/main/LICENSE +# Source: https://www.authelia.com/ + +source /dev/stdin <<<"$FUNCTIONS_FILE_PATH" +color +verb_ip6 +catch_errors +setting_up_container +network_check +update_os + +fetch_and_deploy_gh_release "authelia" "authelia/authelia" "binary" + +MAX_ATTEMPTS=3 +attempt=0 +while true; do + attempt=$((attempt + 1)) + read -rp "${TAB3}Enter your domain or IP (ex. example.com or 192.168.1.100): " DOMAIN + if [[ -z "$DOMAIN" ]]; then + if ((attempt >= MAX_ATTEMPTS)); then + DOMAIN="${LOCAL_IP:-localhost}" + msg_warn "Using fallback: $DOMAIN" + break + fi + msg_warn "Domain cannot be empty! (Attempt $attempt/$MAX_ATTEMPTS)" + elif [[ "$DOMAIN" =~ ^([0-9]{1,3}\.){3}[0-9]{1,3}$ ]]; then + valid_ip=true + IFS='.' read -ra octets <<< "$DOMAIN" + for octet in "${octets[@]}"; do + if ((octet > 255)); then + valid_ip=false + break + fi + done + if $valid_ip; then + break + else + msg_warn "Invalid IP address!" + fi + elif [[ "$DOMAIN" =~ ^[a-zA-Z0-9]([a-zA-Z0-9-]{0,61}[a-zA-Z0-9])?(\.[a-zA-Z0-9]([a-zA-Z0-9-]{0,61}[a-zA-Z0-9])?)*\.[a-zA-Z]{2,}$ ]]; then + break + else + msg_warn "Invalid domain format!" + fi +done +msg_info "Setting Authelia up" +touch /etc/authelia/emails.txt +JWT_SECRET=$(openssl rand -hex 64) +SESSION_SECRET=$(openssl rand -hex 64) +STORAGE_KEY=$(openssl rand -hex 64) + +if [[ "$DOMAIN" =~ ^([0-9]{1,3}\.){3}[0-9]{1,3}$ ]]; then + AUTHELIA_URL="https://${DOMAIN}:9091" +else + AUTHELIA_URL="https://auth.${DOMAIN}" +fi +echo "$AUTHELIA_URL" > /etc/authelia/.authelia_url + +cat </etc/authelia/users.yml +users: + authelia: + disabled: false + displayname: "Authelia Admin" + password: "\$argon2id\$v=19\$m=65536,t=3,p=4\$ZBopMzXrzhHXPEZxRDVT2w\$SxWm96DwhOsZyn34DLocwQEIb4kCDsk632PuiMdZnig" + groups: [] +EOF +cat </etc/authelia/configuration.yml +authentication_backend: + file: + path: /etc/authelia/users.yml +access_control: + default_policy: one_factor +session: + secret: "${SESSION_SECRET}" + name: 'authelia_session' + same_site: 'lax' + inactivity: '5m' + expiration: '1h' + remember_me: '1M' + cookies: + - domain: "${DOMAIN}" + authelia_url: "${AUTHELIA_URL}" +storage: + encryption_key: "${STORAGE_KEY}" + local: + path: /etc/authelia/db.sqlite +identity_validation: + reset_password: + jwt_secret: "${JWT_SECRET}" + jwt_lifespan: '5 minutes' + jwt_algorithm: 'HS256' +notifier: + filesystem: + filename: /etc/authelia/emails.txt +EOF +touch /etc/authelia/emails.txt +chown -R authelia:authelia /etc/authelia +systemctl enable -q --now authelia +msg_ok "Authelia Setup completed" + +motd_ssh +customize +cleanup_lxc diff --git a/misc/build.func b/misc/build.func index ffdd4223a..051c5f4b8 100644 --- a/misc/build.func +++ b/misc/build.func @@ -3844,6 +3844,24 @@ EOF fix_gpu_gids + # Fix Debian 13 LXC template bug where / is owned by nobody:nogroup + # This causes systemd-tmpfiles to fail with "unsafe path transition" errors + # We need to fix this from the host before any package installation + if [[ "$var_os" == "debian" && "$var_version" == "13" ]]; then + # Stop container, fix ownership, restart + pct stop "$CTID" >/dev/null 2>&1 || true + sleep 1 + # Get the actual rootfs path from pct mount + local rootfs_path + rootfs_path=$(pct mount "$CTID" 2>/dev/null | grep -oP 'mounted at \K.*' || echo "") + if [[ -n "$rootfs_path" && -d "$rootfs_path" ]]; then + chown root:root "$rootfs_path" 2>/dev/null || true + fi + pct unmount "$CTID" >/dev/null 2>&1 || true + pct start "$CTID" >/dev/null 2>&1 + sleep 3 + fi + # Continue with standard container setup msg_info "Customizing LXC Container"