LibrePortal/scripts/source/files/generate_arrays.sh
librelad 7aed9102c4 fix(tools): keep the user on the Tools tab and show the result there
Running any tool jumped to the Tasks tab and left the user stranded there. That
is right for an install — long, log-heavy, worth watching — and wrong for a
tool, which is a short admin action whose answer is one line. Worse, half of
these are only meaningful back on Tools: List Users opens a modal over that tab,
and Create User Account returns a generated password that was being buried in a
log the user then had to go read.

Tools now stay put. On completion the tool's own outcome lines — the
isSuccessful/isError/isNotice output, ANSI stripped and framework boilerplate
filtered — are shown in a small result modal, with a View log button for
anything needing the full detail. list_users is left alone because the existing
account-list modal is already a better result view.

Also stops generate_arrays.sh walking scripts/dev. That directory is
`export-ignore`d, so it exists in a working clone but never in a shipped
install; generating a files_dev.sh entry from it wrote a reference into
files_source.sh that no install could satisfy, and the loader treats a missing
array file as a broken installation — every libreportal command stopped with
"files_dev.sh is missing from your LibrePortal Installation". Excluded alongside
unused/, system/ and release/. Regenerating also picked up scripts/validation,
which had never had an array file.

And Matrix's account listing prints its aligned line from python rather than
re-splitting the marker line in bash: TAB is IFS whitespace, so an empty display
name collapsed into the previous delimiter and shifted every later column.

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

156 lines
6.2 KiB
Bash
Executable File

#!/bin/bash
# Generate arrays script - automatically creates files_*.sh arrays
# This script scans the scripts folder and generates array files for each subfolder
#
# Usage: ./generate_arrays.sh run
#
# SAFETY: This script only runs when executed directly with 'run' parameter
# It will NOT run when sourced (which happens during LibrePortal startup)
# Only run if executed directly (not sourced) AND run parameter is provided
if [[ "${BASH_SOURCE[0]}" == "${0}" && "$1" == "run" ]]; then
SCRIPT_DIR="$(cd "$(dirname "${BASH_SOURCE[0]}")" && pwd)"
ARRAYS_DIR="$SCRIPT_DIR/arrays"
SCRIPTS_DIR="$(dirname "$(dirname "$SCRIPT_DIR")")"
# Standalone runner — duplicate the framework's tiny output helpers inline so
# the script keeps its zero-dependency property but still matches the look of
# the rest of the install pipeline.
RED='\033[0;31m'; GREEN='\033[0;32m'; YELLOW='\033[0;33m'; NC='\033[0m'
isSuccessful() { echo -e "${GREEN}✓ Success${NC} $1"; }
isNotice() { echo -e "${YELLOW}! Notice${NC} $1"; }
isHeader() {
local title="$1"
local width=52
local inner=$((width - 2))
local total_pad=$((inner - ${#title}))
(( total_pad < 0 )) && total_pad=0
local left_pad=$((total_pad / 2))
local right_pad=$((total_pad - left_pad))
local hbar
hbar=$(printf '═%.0s' $(seq 1 "$inner"))
printf '\n╔%s╗\n' "$hbar"
printf '║%*s%s%*s║\n' "$left_pad" '' "$title" "$right_pad" ''
printf '╚%s╝\n\n' "$hbar"
}
hbar=$(printf '═%.0s' $(seq 1 50))
printf '\n╔%s╗\n' "$hbar"
printf '║%6s%s%8s║\n' '' '╦ ┬┌┐ ┬─┐┌─┐ ╭─╮ ╔═╗┌─┐┬─┐┌┬┐┌─┐┬' ''
printf '║%6s%s%8s║\n' '' '║ │├┴┐├┬┘├┤ │◉│ ╠═╝│ │├┬┘ │ ├─┤│' ''
printf '║%6s%s%6s║\n' '' '╩═╝┴└─┘┴└─└─┘ ╨─╨ ╩ └─┘┴└─ ┴ ┴ ┴┴─┘' ''
printf '╚%s╝\n\n' "$hbar"
isHeader "Regenerating Array Files"
isNotice "Scanning scripts/ for subfolder arrays..."
# Create arrays directory if it doesn't exist
mkdir -p "$ARRAYS_DIR"
# Prune arrays whose source folder no longer exists, so a removed area (e.g.
# scripts/ssh/) doesn't linger in the sourced set as a stale files_*.sh.
for existing in "$ARRAYS_DIR"/files_*.sh; do
[ -f "$existing" ] || continue
pruned_name=$(basename "$existing"); pruned_name=${pruned_name#files_}; pruned_name=${pruned_name%.sh}
if [ ! -d "$SCRIPTS_DIR/$pruned_name" ]; then
rm -f "$existing"
isNotice "Pruned stale files_${pruned_name}.sh (no scripts/$pruned_name/)"
fi
done
# Get all directories in scripts folder
for folder in "$SCRIPTS_DIR"/*; do
if [ -d "$folder" ]; then
folder_name=$(basename "$folder")
# Skip folders that aren't sourced function libraries: the dead-code
# graveyard; system/ (standalone root-owned helpers invoked via sudo);
# release/ (build tooling — make_release.sh runs at build time, never
# sourced); and dev/ (maintainer-only tools such as lp-shot).
#
# dev/ matters more than it looks. It is `export-ignore`d in
# .gitattributes, so it exists in a working clone but never in a shipped
# install. Generating a files_dev.sh entry from it writes a reference
# into files_source.sh that no install can satisfy — and the loader
# treats a missing array file as a broken installation, so every
# libreportal command then stops with "It seems that files_dev.sh is
# missing from your LibrePortal Installation".
if [ "$folder_name" = "unused" ] || [ "$folder_name" = "system" ] \
|| [ "$folder_name" = "release" ] || [ "$folder_name" = "dev" ]; then
isNotice "Skipping $folder_name/"
continue
fi
array_file="$ARRAYS_DIR/files_${folder_name}.sh"
# Start the array file
cat > "$array_file" << EOF
#!/bin/bash
# This file is auto-generated by generate_arrays.sh
# Do not edit manually - run './scripts/source/files/generate_arrays.sh run' to regenerate
${folder_name}_scripts=(
EOF
# Find all .sh files in the folder and subdirectories
find "$folder" -name "*.sh" -type f | sort | while read -r file; do
# Get relative path from scripts directory
rel_path=$(realpath --relative-to="$SCRIPTS_DIR" "$file")
# Skip specific files for source folder
if [ "$folder_name" = "source" ]; then
case "$rel_path" in
"source/files/app_files.sh"|"source/files/cli_files.sh"| \
"source/loading/check_files.sh"|"source/loading/initilize_files.sh"| \
"source/loading/scan_files.sh"|"source/load_sources.sh"| \
"source/paths.sh"| \
"source/files/generate_arrays.sh")
continue
;;
esac
fi
# Skip specific files for webui folder
if [ "$folder_name" = "webui" ]; then
case "$rel_path" in
"webui/data/generators/webui_test_generate.sh")
continue
;;
esac
fi
# peer/peer_shell.sh is the SSH forced-command dispatcher — it's
# deployed standalone to ~/.local/bin/peer-shell and executed by
# sshd, never sourced as a library. Sourcing it would run its
# top-level _die() on the empty SSH_ORIGINAL_COMMAND and crash
# the parent shell.
if [ "$folder_name" = "peer" ]; then
case "$rel_path" in
"peer/peer_shell.sh")
continue
;;
esac
fi
# Escape quotes and add to array
echo " \"$rel_path\"" >> "$array_file"
done
# Close the array
cat >> "$array_file" << EOF
)
EOF
isSuccessful "Generated files_${folder_name}.sh"
fi
done
isHeader "Generation Complete"
isSuccessful "$(find "$ARRAYS_DIR" -name "files_*.sh" | wc -l) array files written to $ARRAYS_DIR"
echo ""
fi