autoNAS / scripts / autonas-sync-systemd-ordering.sh
Newer Older
5bf8614 3 months ago History
128 lines | 3.361kb
Bogdan Timofte authored 3 months ago
1
#!/bin/bash
2

            
3
set -euo pipefail
4

            
5
CONFIG_FILE="${AUTONAS_CONFIG_FILE:-/etc/pve/autonas/disks.conf}"
6
STORAGE_CFG="${AUTONAS_STORAGE_CFG:-/etc/pve/storage.cfg}"
7
DROPIN_DIR="/etc/systemd/system/nfs-server.service.d"
8
DROPIN_FILE="${DROPIN_DIR}/50-autonas-self-hosted-proxmox.conf"
9

            
10
require_root() {
11
    if [[ "${EUID}" -ne 0 ]]; then
12
        echo "ERROR: this action must be run as root" >&2
13
        exit 1
14
    fi
15
}
16

            
17
collect_local_autonas_ips() {
18
    [[ -f "${CONFIG_FILE}" ]] || return 0
19

            
20
    local -A current_ip_map=()
21
    local current_ip=""
22
    while IFS= read -r current_ip; do
23
        [[ -n "${current_ip}" ]] && current_ip_map["${current_ip}"]=1
24
    done < <(ip -o -4 addr show up scope global | awk '{print $4}' | cut -d/ -f1 | sort -u)
25

            
26
    [[ "${#current_ip_map[@]}" -gt 0 ]] || return 0
27

            
28
    local cfg_ip=""
29
    while IFS=: read -r _ _ cfg_ip _ _ _; do
30
        [[ -z "${cfg_ip}" || "${cfg_ip}" == "LOCAL" || "${cfg_ip}" == "IMPORT" ]] && continue
31
        [[ -n "${current_ip_map[${cfg_ip}]:-}" ]] && echo "${cfg_ip}"
32
    done < <(grep -v '^[[:space:]]*#' "${CONFIG_FILE}" || true)
33
}
34

            
35
collect_self_hosted_mount_units() {
36
    [[ -f "${STORAGE_CFG}" ]] || return 0
37

            
38
    local -A local_ip_map=()
39
    local ip=""
40
    while IFS= read -r ip; do
41
        [[ -n "${ip}" ]] && local_ip_map["${ip}"]=1
42
    done < <(collect_local_autonas_ips)
43

            
44
    [[ "${#local_ip_map[@]}" -gt 0 ]] || return 0
45

            
46
    local -A mount_unit_map=()
47
    local server=""
48
    local path=""
49
    local type=""
50
    local line=""
51

            
52
    emit_candidate() {
53
        if [[ "${type}" == "nfs" && -n "${server}" && -n "${path}" && -n "${local_ip_map[${server}]:-}" ]]; then
54
            mount_unit_map["$(systemd-escape --path --suffix=mount "${path}")"]=1
55
        fi
56
    }
57

            
58
    while IFS= read -r line || [[ -n "${line}" ]]; do
59
        if [[ "${line}" =~ ^[[:space:]]*# ]]; then
60
            continue
61
        fi
62

            
63
        if [[ "${line}" =~ ^[[:space:]]*$ ]]; then
64
            emit_candidate
65
            type=""
66
            server=""
67
            path=""
68
            continue
69
        fi
70

            
71
        if [[ ! "${line}" =~ ^[[:space:]] ]]; then
72
            emit_candidate
73
            type="${line%%:*}"
74
            server=""
75
            path=""
76
            continue
77
        fi
78

            
79
        if [[ "${line}" =~ ^[[:space:]]*server[[:space:]]+(.+)$ ]]; then
80
            server="${BASH_REMATCH[1]}"
81
            continue
82
        fi
83

            
84
        if [[ "${line}" =~ ^[[:space:]]*path[[:space:]]+(.+)$ ]]; then
85
            path="${BASH_REMATCH[1]}"
86
            continue
87
        fi
88
    done < "${STORAGE_CFG}"
89

            
90
    emit_candidate
91

            
92
    printf '%s\n' "${!mount_unit_map[@]}" | sort
93
}
94

            
95
write_dropin() {
96
    local units=("$@")
97

            
98
    if [[ "${#units[@]}" -eq 0 ]]; then
99
        rm -f "${DROPIN_FILE}"
100
        rmdir "${DROPIN_DIR}" 2>/dev/null || true
101
        return 0
102
    fi
103

            
104
    mkdir -p "${DROPIN_DIR}"
105
    {
106
        echo "# Managed by AutoNAS."
107
        echo "# Keep self-hosted Proxmox NFS client mounts ordered before nfs-server shutdown."
108
        echo "[Unit]"
109
        printf 'Before='
110
        printf '%s ' "${units[@]}"
111
        printf '\n'
112
    } > "${DROPIN_FILE}"
113
}
114

            
115
main() {
116
    require_root
117

            
118
    local units=()
119
    local unit=""
120
    while IFS= read -r unit; do
121
        [[ -n "${unit}" ]] && units+=("${unit}")
122
    done < <(collect_self_hosted_mount_units)
123

            
124
    write_dropin "${units[@]}"
125
    systemctl daemon-reload
126
}
127

            
128
main "$@"