From 2acab94dcdb1b049ac42074f1f0f727ffa2bfd85 Mon Sep 17 00:00:00 2001 From: Heavybullets8 Date: Fri, 13 Oct 2023 05:00:39 +0000 Subject: [PATCH] Lifecycle - Unmount apps upon start (#133) [Features] - Starting an app with HeavyScript will now unmount the app if it's mounted. - CNPG database dumps no longer stop deployments by default, allowing for continuous operation. [Refactor] - The CNPG dump process has been refined to keep deployments running. - Opt-in to stop deployments during the dump using the `stop_before_dump` option in the `config.ini` file. - Your config files should have automatically updated to have this new section. --- .default.config.ini | 7 +++- functions/app/start_app.sh | 5 +-- .../backup_restore/database/cnpg_dump.sh | 38 ++++++++++++++----- utils/check_filtered_apps.sh | 5 +++ utils/generate_config.sh | 20 +++------- utils/resources.sh | 2 +- utils/start_app.sh | 18 +++++++-- 7 files changed, 62 insertions(+), 33 deletions(-) diff --git a/.default.config.ini b/.default.config.ini index 119a907d..23f706c2 100644 --- a/.default.config.ini +++ b/.default.config.ini @@ -64,4 +64,9 @@ enabled=true ## String options ## # File path for database dump folder -dump_folder="./database_dumps" \ No newline at end of file +dump_folder="./database_dumps" + +# Apps listed here will have their deployments shut down prior to their CNPG Database dump +# This is usually uneccesary, and unless otherwise recommended, leave blank +# Example: stop_before_dump=nextcloud,appname,appname +stop_before_dump="" \ No newline at end of file diff --git a/functions/app/start_app.sh b/functions/app/start_app.sh index 2bef6f8b..3f702c2f 100644 --- a/functions/app/start_app.sh +++ b/functions/app/start_app.sh @@ -30,7 +30,7 @@ start_app_prompt() { exit fi - if [[ $replica_count == "null" ]]; then + if [[ $replica_count == "null" && $(check_filtered_apps "$app_name") != *"${app_name},official"* ]]; then echo -e "${blue}$app_name${red} cannot be started${reset}" echo -e "${yellow}Replica count is null${reset}" echo -e "${yellow}Looks like you found an application HS cannot handle${reset}" @@ -41,9 +41,8 @@ start_app_prompt() { echo -e "Starting ${blue}$app_name${reset}..." # Check if all cli commands were successful - if start_app "$app_name" "$replica_count"; then + if start_app "$app_name"; then echo -e "${blue}$app_name ${green}Started${reset}" - echo -e "${green}Replica count set to ${blue}$replica_count${reset}\n" else echo -e "${red}Failed to start ${blue}$app_name${reset}\n" fi diff --git a/functions/backup_restore/database/cnpg_dump.sh b/functions/backup_restore/database/cnpg_dump.sh index 3e121c84..8edfbda7 100644 --- a/functions/backup_restore/database/cnpg_dump.sh +++ b/functions/backup_restore/database/cnpg_dump.sh @@ -189,9 +189,17 @@ backup_cnpg_databases() { local retention=$1 local timestamp=$2 local dump_folder=$3 + local stop_before_dump=() mapfile -t app_status_lines < <(db_dump_get_app_status) + + # Get the stop_before_dump value from config.ini + temp="${DATABASES__databases__stop_before_dump:-}" + # Split comma-separated values into an array + IFS=',' read -ra stop_before_dump <<< "$temp" + unset temp + if [[ ${#app_status_lines[@]} -eq 0 ]]; then return fi @@ -199,8 +207,13 @@ backup_cnpg_databases() { echo_backup+=("--CNPG Database Backups--") for app in "${app_status_lines[@]}"; do + scale_deployments_bool=false IFS=',' read -r app_name app_status <<< "$app" + if printf '%s\0' "${stop_before_dump[@]}" | grep -iFxqz "${app_name}"; then + scale_deployments_bool=true + fi + # Start the app if it is stopped if [[ $app_status == "STOPPED" ]]; then start_app "$app_name" 1 @@ -214,13 +227,15 @@ backup_cnpg_databases() { original_replicas["$key"]=$value done - # Scale down all deployments in the app to 0 - for deployment in "${!original_replicas[@]}"; do - if [[ ${original_replicas[$deployment]} -ne 0 ]] && ! scale_deployments "$app_name" 300 0 "$deployment" > /dev/null 2>&1; then - echo_backup+=("Failed to scale down $app_name's $deployment deployment.") - return - fi - done + if [[ $scale_deployments_bool == true ]]; then + # Scale down all deployments in the app to 0 + for deployment in "${!original_replicas[@]}"; do + if [[ ${original_replicas[$deployment]} -ne 0 ]] && ! scale_deployments "$app_name" 300 0 "$deployment" > /dev/null 2>&1; then + echo_backup+=("Failed to scale down $app_name's $deployment deployment.") + return + fi + done + fi # Dump the database if ! dump_database "$app_name" "$dump_folder"; then @@ -228,11 +243,16 @@ backup_cnpg_databases() { return fi - # Scale up all deployments in the app to their original replica counts, or stop the app if it was stopped + # Stop the app if it was stopped if [[ $app_status == "STOPPED" ]]; then wait_for_redeploy_jobs "$app_name" stop_app "direct" "$app_name" - else + break + fi + + + if [[ $scale_deployments_bool == true ]]; then + # Scale up all deployments in the app to their original replica counts for deployment in "${!original_replicas[@]}"; do if [[ ${original_replicas[$deployment]} -ne 0 ]] && ! scale_deployments "$app_name" 300 "${original_replicas[$deployment]}" "$deployment" > /dev/null 2>&1; then echo_backup+=("Failed to scale up $app_name's $deployment deployment.") diff --git a/utils/check_filtered_apps.sh b/utils/check_filtered_apps.sh index b4fb0b78..56111064 100644 --- a/utils/check_filtered_apps.sh +++ b/utils/check_filtered_apps.sh @@ -12,6 +12,11 @@ check_filtered_apps() { else empty end, + if .catalog == "TRUENAS" then + .name + ",official" + else + empty + end, if .config.cnpg.main.enabled == true then .name + ",cnpg" else diff --git a/utils/generate_config.sh b/utils/generate_config.sh index dfb94f10..49ebc113 100644 --- a/utils/generate_config.sh +++ b/utils/generate_config.sh @@ -13,21 +13,11 @@ generate_config_ini() { add_database_options() { config_file="config.ini" - # Check if the [databases] section exists - if ! grep -q "^\[databases\]" "$config_file"; then - # Add the [databases] section to the config file - echo -e "\n[databases]" >> "$config_file" + # Check if the stop_before_dump option exists + if ! grep -q "^stop_before_dump=" "$config_file"; then + # Add the stop_before_dump option with a default value and description + awk -i inplace -v stop_before_dump_option="\n# Apps listed here will have their deployments shut down prior to their CNPG Database dump\n# This is usually unnecessary, and unless otherwise recommended, leave blank\n# Example: stop_before_dump=nextcloud,appname,appname\nstop_before_dump=\"\"\n" '/^dump_folder=.*/ { print; print stop_before_dump_option; next }1' "$config_file" fi +} - # Check if the enabled option exists - if ! grep -q "^enabled=" "$config_file"; then - # Add the enabled option with a default value and description - awk -i inplace -v enable_option="## true/false options ##\n# Enable or disable database dumps\nenabled=true\n" '/^\[databases\]/ { print; print enable_option; next }1' "$config_file" - fi - # Check if the dump_folder option exists - if ! grep -q "^dump_folder=" "$config_file"; then - # Add the dump_folder option with a default value and description - awk -i inplace -v dump_folder_option="\n## String options ##\n# File path for database dump folder\ndump_folder=\"./database_dumps\"" '/^enabled=true/ { print; print dump_folder_option; next }1' "$config_file" - fi -} diff --git a/utils/resources.sh b/utils/resources.sh index 644097de..784e8333 100644 --- a/utils/resources.sh +++ b/utils/resources.sh @@ -4,7 +4,7 @@ pull_replicas() { local app_name app_name="$1" - midclt call chart.release.get_instance "$app_name" | jq '.config.controller.replicas // .config.workload.main.replicas // .pod_status.desired' + midclt call chart.release.get_instance "$app_name" | jq '.config.controller.replicas // .config.workload.main.replicas' } restart_app(){ diff --git a/utils/start_app.sh b/utils/start_app.sh index 51eef606..b566af83 100644 --- a/utils/start_app.sh +++ b/utils/start_app.sh @@ -49,11 +49,21 @@ get_running_job_id(){ '.[] | select( .time_finished == null and .state == "RUNNING" and (.progress.description | test("Waiting for pods to be scaled to [0-9]+ replica\\(s\\)$")) and (.arguments[0] == $app_name and .method == "chart.release.scale") ) | .id' } +check_mounted(){ + local app_name=$1 + + if [[ -d /mnt/mounted_pvc/"$app_name" ]]; then + unmount_app_func "$app_name" > /dev/null 2>&1 + fi +} + start_app(){ local app_name=$1 - local replica_count=${2:-$(pull_replicas "$app_name")} local job_id + #check if app is currently mounted + check_mounted "$app_name" + # Check if app is a cnpg instance, or an operator instance output=$(check_filtered_apps "$app_name") if [[ $output == *"${app_name},stopAll-on"* ]]; then @@ -61,15 +71,15 @@ start_app(){ return 1 fi abort_job "$app_name" - job_id=$(midclt call chart.release.scale "$app_name" '{"replica_count": '"$replica_count"'}') || return 1 + job_id=$(midclt call chart.release.redeploy_internal "$app_name") || return 1 wait_for_redeploy_methods "$app_name" midclt call core.job_abort "$job_id" > /dev/null 2>&1 elif [[ $output == *"${app_name},stopAll-off"* ]]; then - job_id=$(midclt call chart.release.scale "$app_name" '{"replica_count": '"$replica_count"'}') || return 1 + job_id=$(midclt call chart.release.redeploy_internal "$app_name") || return 1 wait_for_redeploy_methods "$app_name" midclt call core.job_abort "$job_id" > /dev/null 2>&1 else - if ! cli -c 'app chart_release scale release_name='\""$app_name"\"\ 'scale_options={"replica_count": '"$replica_count}" > /dev/null 2>&1; then + if ! cli -c 'app chart_release redeploy release_name='\""$app_name"\" > /dev/null 2>&1; then return 1 fi fi