LibrePortal/scripts/cli/commands/webui/cli_webui_commands.sh
librelad 2d24a764a8 refactor(storage): route elevation tests and the WebUI tree through paths.sh
Two mechanical sweeps, no behaviour change on a single-root install.

The 14 `[[ "$p" == "$containers_dir"* ]]` prefix tests that decide
manager-vs-container-user elevation become pathIsContainerData, so a file
on a second storage root is no longer misclassified as manager-owned —
which would have written it with the wrong owner and failed later, far
from the cause. The 65 references to the WebUI's own tree become
webuiDir(), which is pinned to the primary root by design.

Two traps found while doing it:

run_privileged.sh is sourced directly by init.sh without paths.sh, so it
needs a fallback. Defining one named pathIsContainerData was wrong:
generate_function_manifest.sh indexes top-level definitions, and the
resulting autoload stub would have shadowed the real multi-root
implementation with the primary-only fallback — silently classifying
every file on a second disk as manager-owned, which is exactly the bug
this sweep exists to prevent. Renamed to _runCfgIsContainerPath, which
delegates when the real one is loaded.

setup_lock.sh built its path in a top-level assignment, so it was
evaluated at source time and needed the file flagged eager. Made it a
function instead: the path resolves on call, and the file drops off
LP_EAGER_FILES entirely.

Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
2026-08-24 04:04:19 +01:00

114 lines
4.0 KiB
Bash
Executable File

#!/bin/bash
# WebUI Commands Handler
# Handles all webui subcommands by calling core functions
cliHandleWebuiCommands()
{
local action="$initial_command2"
local config_type="$initial_command3"
local options="$initial_command4"
if [[ -z "$action" ]]; then
cliShowWebuiHelp
fi
case "$action" in
"generate")
if [[ -z "$config_type" ]]; then
isNotice "Generate option required. Use: backup [source] or config [options]"
cliShowWebuiHelp
elif [ "$config_type" = "backup" ]; then
webuiGenerateBackupLocations
webuiGenerateBackupDashboard
webuiGenerateBackupSnapshots "${options:-all}"
webuiGenerateBackupAppStatus
webuiGenerateBackupSchema
webuiGenerateBackupPasswords
elif [ "$config_type" = "system" ]; then
webuiSystemUpdate
elif [ "$config_type" = "config" ]; then
webuiGenerateSystemConfigs
elif [ "$config_type" = "all" ]; then
webuiLibrePortalUpdate
else
isNotice "Invalid generate option: $config_type. Use: backup, system, config, or all"
cliShowWebuiHelp
fi
;;
"service")
installLibrePortalWebUITaskService;
;;
"login")
case "$config_type" in
"show")
sourceScanFiles "libreportal_configs"
if [[ -z "$CFG_WEBUI_USERNAME" || -z "$CFG_WEBUI_PASSWORD" ]]; then
isError "WebUI credentials not found. Run 'libreportal webui login reset' to generate."
return 1
fi
webuiDisplayLogins "show"
;;
"reset"|"recover")
cliWebuiLoginReset
;;
*)
isNotice "Invalid login action: $config_type. Use: show, reset"
cliShowWebuiHelp
;;
esac
;;
"recover")
isNotice "'libreportal webui recover' is deprecated — use 'libreportal webui login reset'."
cliWebuiLoginReset
;;
*)
isNotice "Invalid webui action: $action"
cliShowWebuiHelp
;;
esac
}
cliWebuiLoginReset()
{
local auth_file="$(webuiDir)/frontend/.auth.json"
local webui_logins_file="$configs_dir/webui/webui_logins"
isNotice "Resetting WebUI credentials..."
# Restore placeholders so the scan re-randomizes them
if [ -f "$webui_logins_file" ]; then
runInstallOp sed -i -E 's/^(CFG_WEBUI_USERNAME=).*$/\1RANDOMIZEDUSERNAME1/' "$webui_logins_file"
runInstallOp sed -i -E 's/^(CFG_WEBUI_PASSWORD=).*$/\1RANDOMIZEDPASSWORD1/' "$webui_logins_file"
fi
# Remove auth file to force credential regeneration on next container start
if [ -f "$auth_file" ]; then
rm -f "$auth_file"
isSuccessful "Removed WebUI auth file."
fi
# Re-randomize credentials in webui_logins
scanFileForRandomPasswordKeysUsers "$webui_logins_file"
sourceScanFiles "libreportal_configs"
isSuccessful "WebUI credentials have been reset."
# Regenerate all WebUI config files
isNotice "Regenerating WebUI config files..."
webuiLibrePortalUpdate
# The credential rewrite above ran as the non-root manager, which resets
# webui_logins' group and drops the container-owner group the rootless WebUI
# reads it through. Restore it before restarting, or the container can't read
# its own login file and exits on boot.
reconcileWebuiDirOwnership
# Restart the libreportal container so it picks up the new credentials
isNotice "Restarting LibrePortal container..."
dockerComposeRestart libreportal
isSuccessful "LibrePortal container restarted."
# Display the new credentials
webuiDisplayLogins "reset"
}