656 lines
17 KiB
Bash
656 lines
17 KiB
Bash
#!/usr/bin/env bash
|
|
|
|
set -u
|
|
|
|
SCRIPT_NAME="$(basename "$0")"
|
|
TIMESTAMP="$(date '+%Y%m%d_%H%M%S')"
|
|
|
|
# Configure apenas estas variaveis antes de executar o script.
|
|
BOT_TOKEN="8785769899:AAECGDEOwzfPxWyQNm6sDxA9nIf1wUFcxiU"
|
|
CHAT_ID="-5192130580"
|
|
|
|
APT_UPDATED=0
|
|
APT_UPDATE_FAILED=0
|
|
RA_ARGS=()
|
|
|
|
REQUIRED_PACKAGES=(
|
|
iproute2
|
|
net-tools
|
|
dnsutils
|
|
iputils-ping
|
|
iptables
|
|
nftables
|
|
tar
|
|
curl
|
|
)
|
|
|
|
NS1_EXTRA_PACKAGES=(
|
|
isc-dhcp-server
|
|
)
|
|
|
|
now_human() {
|
|
date '+%Y/%m/%d-%H:%M:%S'
|
|
}
|
|
|
|
log_line() {
|
|
local logfile="$1"
|
|
local message="$2"
|
|
mkdir -p "$(dirname "$logfile")"
|
|
printf '[%s] %s\n' "$(now_human)" "$message" | tee -a "$logfile" >/dev/null
|
|
}
|
|
|
|
main_log() {
|
|
log_line "$EXEC_LOG" "$1"
|
|
}
|
|
|
|
warn_log() {
|
|
log_line "$EXEC_LOG" "AVISO: $1"
|
|
}
|
|
|
|
error_log() {
|
|
log_line "$EXEC_LOG" "ERRO: $1"
|
|
}
|
|
|
|
sanitize_vm_type() {
|
|
printf '%s' "$1" | tr '[:lower:]' '[:upper:]'
|
|
}
|
|
|
|
print_usage() {
|
|
cat <<'EOF'
|
|
Uso:
|
|
correcao_vm.sh [RA1 RA2 [RA3]]
|
|
|
|
Opcoes:
|
|
-h, --help Exibe esta ajuda.
|
|
EOF
|
|
}
|
|
|
|
require_root() {
|
|
if [[ "${EUID:-$(id -u)}" -ne 0 ]]; then
|
|
printf 'Este script precisa ser executado como root.\n' >&2
|
|
exit 1
|
|
fi
|
|
}
|
|
|
|
prompt_nonempty() {
|
|
local prompt="$1"
|
|
local value=""
|
|
while :; do
|
|
if ! read -r -p "$prompt" value; then
|
|
return 1
|
|
fi
|
|
value="${value#"${value%%[![:space:]]*}"}"
|
|
value="${value%"${value##*[![:space:]]}"}"
|
|
if [[ -n "$value" ]]; then
|
|
printf '%s\n' "$value"
|
|
return 0
|
|
fi
|
|
printf 'Valor obrigatorio.\n'
|
|
done
|
|
}
|
|
|
|
prompt_numeric() {
|
|
local prompt="$1"
|
|
local value=""
|
|
while :; do
|
|
if ! read -r -p "$prompt" value; then
|
|
return 1
|
|
fi
|
|
if [[ "$value" =~ ^[0-9]+$ ]]; then
|
|
printf '%s\n' "$value"
|
|
return 0
|
|
fi
|
|
printf 'Digite apenas numeros.\n'
|
|
done
|
|
}
|
|
|
|
prompt_yes_no() {
|
|
local prompt="$1"
|
|
local value=""
|
|
while :; do
|
|
if ! read -r -p "$prompt [s/n]: " value; then
|
|
return 1
|
|
fi
|
|
value="$(printf '%s' "$value" | tr '[:upper:]' '[:lower:]')"
|
|
case "$value" in
|
|
s|sim|y|yes) printf 'yes\n'; return 0 ;;
|
|
n|nao|não|no) printf 'no\n'; return 0 ;;
|
|
*) printf 'Resposta invalida.\n' ;;
|
|
esac
|
|
done
|
|
}
|
|
|
|
prompt_vm_type() {
|
|
local value=""
|
|
while :; do
|
|
printf 'Selecione a VM:\n' >&2
|
|
printf '1) NS1\n' >&2
|
|
printf '2) WEB\n' >&2
|
|
if ! read -r -p "Opcao: " value; then
|
|
return 1
|
|
fi
|
|
case "$value" in
|
|
1) printf 'NS1\n'; return 0 ;;
|
|
2) printf 'WEB\n'; return 0 ;;
|
|
*)
|
|
printf 'Digite 1 para NS1 ou 2 para WEB.\n'
|
|
;;
|
|
esac
|
|
done
|
|
}
|
|
|
|
setup_dirs() {
|
|
BASE_DIR="/root/coleta_dupla_${DUPLA_NUM}_${VM_TYPE}_${TIMESTAMP}"
|
|
LOG_DIR="$BASE_DIR/logs"
|
|
CONFIG_DIR="$BASE_DIR/configs"
|
|
IDENT_DIR="$BASE_DIR/identificacao"
|
|
ENVIO_DIR="$BASE_DIR/envio"
|
|
EXEC_LOG="$LOG_DIR/execucao.log"
|
|
INSTAL_LOG="$LOG_DIR/instalacao.log"
|
|
REDE_LOG="$LOG_DIR/rede.log"
|
|
DHCP_LOG="$LOG_DIR/dhcp.log"
|
|
TELEGRAM_LOG="$ENVIO_DIR/telegram.log"
|
|
SYSTEM_INSTALL_LOG="$LOG_DIR/instalacao_pacotes.log"
|
|
|
|
mkdir -p "$LOG_DIR" "$CONFIG_DIR" "$IDENT_DIR" "$ENVIO_DIR"
|
|
}
|
|
|
|
collect_identification_input() {
|
|
if ((${#RA_ARGS[@]} > 0)); then
|
|
ALUNO1="${RA_ARGS[0]}"
|
|
if ((${#RA_ARGS[@]} >= 2)); then
|
|
ALUNO2="${RA_ARGS[1]}"
|
|
else
|
|
ALUNO2=""
|
|
fi
|
|
if ((${#RA_ARGS[@]} == 3)); then
|
|
HAS_THIRD="yes"
|
|
ALUNO3="${RA_ARGS[2]}"
|
|
else
|
|
HAS_THIRD="no"
|
|
ALUNO3=""
|
|
fi
|
|
return 0
|
|
fi
|
|
|
|
ALUNO1="$(prompt_numeric 'RA do aluno 1: ')"
|
|
if [[ "$(prompt_yes_no 'Existe aluno 2?')" == "yes" ]]; then
|
|
ALUNO2="$(prompt_numeric 'RA do aluno 2: ')"
|
|
HAS_THIRD="$(prompt_yes_no 'Existe terceiro aluno?')"
|
|
if [[ "$HAS_THIRD" == "yes" ]]; then
|
|
ALUNO3="$(prompt_numeric 'RA do aluno 3: ')"
|
|
else
|
|
ALUNO3=""
|
|
fi
|
|
else
|
|
ALUNO2=""
|
|
HAS_THIRD="no"
|
|
ALUNO3=""
|
|
fi
|
|
}
|
|
|
|
save_identification() {
|
|
{
|
|
printf 'DataHora=%s\n' "$(now_human)"
|
|
printf 'Dupla=%s\n' "$DUPLA_NUM"
|
|
printf 'VM=%s\n' "$VM_TYPE"
|
|
printf 'Aluno1=%s\n' "$ALUNO1"
|
|
} > "$IDENT_DIR/alunos.txt"
|
|
|
|
if [[ -n "$ALUNO2" ]]; then
|
|
printf 'Aluno2=%s\n' "$ALUNO2" >> "$IDENT_DIR/alunos.txt"
|
|
fi
|
|
|
|
if [[ "$HAS_THIRD" == "yes" && -n "$ALUNO3" ]]; then
|
|
printf 'Aluno3=%s\n' "$ALUNO3" >> "$IDENT_DIR/alunos.txt"
|
|
fi
|
|
|
|
main_log "Identificacao da dupla registrada em $IDENT_DIR/alunos.txt"
|
|
}
|
|
|
|
run_cmd_logged() {
|
|
local logfile="$1"
|
|
shift
|
|
{
|
|
printf '[%s] CMD: %s\n' "$(now_human)" "$*"
|
|
"$@"
|
|
local rc=$?
|
|
printf '[%s] RC: %s\n' "$(now_human)" "$rc"
|
|
return "$rc"
|
|
} >> "$logfile" 2>&1
|
|
}
|
|
|
|
apt_update_once() {
|
|
if [[ "$APT_UPDATE_FAILED" -eq 1 ]]; then
|
|
log_line "$SYSTEM_INSTALL_LOG" "apt-get update ja falhou anteriormente; novas tentativas foram ignoradas"
|
|
return 1
|
|
fi
|
|
|
|
if [[ "$APT_UPDATED" -eq 0 ]]; then
|
|
log_line "$SYSTEM_INSTALL_LOG" "Executando apt-get update"
|
|
if apt-get update >> "$SYSTEM_INSTALL_LOG" 2>&1; then
|
|
APT_UPDATED=1
|
|
log_line "$SYSTEM_INSTALL_LOG" "apt-get update concluido"
|
|
else
|
|
APT_UPDATE_FAILED=1
|
|
log_line "$SYSTEM_INSTALL_LOG" "Falha no apt-get update"
|
|
return 1
|
|
fi
|
|
fi
|
|
}
|
|
|
|
ensure_packages() {
|
|
local packages=("${REQUIRED_PACKAGES[@]}")
|
|
local pkg
|
|
|
|
if [[ "$VM_TYPE" == "NS1" ]]; then
|
|
packages+=("${NS1_EXTRA_PACKAGES[@]}")
|
|
fi
|
|
|
|
for pkg in "${packages[@]}"; do
|
|
if dpkg -s "$pkg" >/dev/null 2>&1; then
|
|
log_line "$SYSTEM_INSTALL_LOG" "Pacote ja instalado: $pkg"
|
|
continue
|
|
fi
|
|
|
|
log_line "$SYSTEM_INSTALL_LOG" "Pacote ausente: $pkg"
|
|
if ! apt_update_once; then
|
|
log_line "$SYSTEM_INSTALL_LOG" "Instalacao ignorada para $pkg por falha previa no apt-get update"
|
|
continue
|
|
fi
|
|
|
|
if DEBIAN_FRONTEND=noninteractive apt-get install -y "$pkg" >> "$SYSTEM_INSTALL_LOG" 2>&1; then
|
|
log_line "$SYSTEM_INSTALL_LOG" "Pacote instalado com sucesso: $pkg"
|
|
else
|
|
log_line "$SYSTEM_INSTALL_LOG" "Falha ao instalar pacote: $pkg"
|
|
fi
|
|
done
|
|
}
|
|
|
|
copy_config_if_exists() {
|
|
local src="$1"
|
|
local dst_name="$2"
|
|
if [[ -f "$src" ]]; then
|
|
cp "$src" "$CONFIG_DIR/$dst_name"
|
|
main_log "Arquivo copiado: $src -> $CONFIG_DIR/$dst_name"
|
|
else
|
|
warn_log "Arquivo nao encontrado: $src"
|
|
fi
|
|
}
|
|
|
|
collect_configs() {
|
|
copy_config_if_exists "/etc/default/isc-dhcp-server" "isc-dhcp-server"
|
|
copy_config_if_exists "/etc/dhcp/dhcpd.conf" "dhcpd.conf"
|
|
copy_config_if_exists "/etc/network/interfaces" "interfaces"
|
|
}
|
|
|
|
detect_install_datetime() {
|
|
local root_source fs_type candidate ts created_line
|
|
|
|
root_source="$(findmnt -no SOURCE / 2>/dev/null || true)"
|
|
fs_type="$(findmnt -no FSTYPE / 2>/dev/null || true)"
|
|
|
|
if [[ -n "$root_source" && -n "$fs_type" ]]; then
|
|
if [[ "$root_source" =~ ^/dev/ ]] && [[ "$fs_type" =~ ^ext[2-4]$ ]] && command -v tune2fs >/dev/null 2>&1; then
|
|
created_line="$(tune2fs -l "$root_source" 2>/dev/null | awk -F': ' '/Filesystem created:/ {print $2; exit}')"
|
|
if [[ -n "$created_line" ]]; then
|
|
date -d "$created_line" '+%Y/%m/%d-%H:%M:%S' 2>/dev/null && return 0
|
|
fi
|
|
fi
|
|
|
|
ts="$(stat -c '%W' / 2>/dev/null)"
|
|
if [[ -n "$ts" && "$ts" -gt 0 ]]; then
|
|
date -d "@$ts" '+%Y/%m/%d-%H:%M:%S'
|
|
return 0
|
|
fi
|
|
fi
|
|
|
|
for candidate in \
|
|
"/var/log/installer" \
|
|
"/root/.bash_history" \
|
|
"/etc/machine-id" \
|
|
"/lost+found"; do
|
|
if [[ -e "$candidate" ]]; then
|
|
ts="$(stat -c '%W' "$candidate" 2>/dev/null)"
|
|
if [[ -n "$ts" && "$ts" -gt 0 ]]; then
|
|
date -d "@$ts" '+%Y/%m/%d-%H:%M:%S'
|
|
return 0
|
|
fi
|
|
ts="$(stat -c '%Y' "$candidate" 2>/dev/null)"
|
|
if [[ -n "$ts" && "$ts" -gt 0 ]]; then
|
|
date -d "@$ts" '+%Y/%m/%d-%H:%M:%S'
|
|
return 0
|
|
fi
|
|
fi
|
|
done
|
|
|
|
printf 'indisponivel\n'
|
|
}
|
|
|
|
check_os_installation() {
|
|
local os_id version_id install_dt
|
|
os_id="$(. /etc/os-release && printf '%s' "${ID:-desconhecido}")"
|
|
version_id="$(. /etc/os-release && printf '%s' "${VERSION_ID:-desconhecida}")"
|
|
install_dt="$(detect_install_datetime)"
|
|
|
|
log_line "$INSTAL_LOG" "Sistema identificado: ID=$os_id VERSION_ID=$version_id"
|
|
if [[ "$os_id" == "debian" && "$version_id" == "12" ]]; then
|
|
log_line "$INSTAL_LOG" "Validacao do SO: OK (Debian 12)"
|
|
else
|
|
log_line "$INSTAL_LOG" "Validacao do SO: FALHA (esperado Debian 12)"
|
|
fi
|
|
log_line "$INSTAL_LOG" "Data/hora aproximada da instalacao: $install_dt"
|
|
}
|
|
|
|
list_interfaces_ipv4() {
|
|
ip -o -4 addr show scope global 2>/dev/null | awk '{print $2" "$4}'
|
|
}
|
|
|
|
detect_default_iface() {
|
|
ip route show default 2>/dev/null | awk '/default/ {print $5; exit}'
|
|
}
|
|
|
|
test_connectivity() {
|
|
local target="$1"
|
|
local label="$2"
|
|
if ping -c 2 -W 3 "$target" >> "$REDE_LOG" 2>&1; then
|
|
log_line "$REDE_LOG" "Conectividade $label: OK ($target)"
|
|
else
|
|
log_line "$REDE_LOG" "Conectividade $label: FALHA ($target)"
|
|
fi
|
|
}
|
|
|
|
check_gateway() {
|
|
local gateway
|
|
gateway="$(ip route show default 2>/dev/null | awk '/default/ {print $3; exit}')"
|
|
if [[ -n "$gateway" ]]; then
|
|
log_line "$REDE_LOG" "Gateway padrao: $gateway"
|
|
else
|
|
log_line "$REDE_LOG" "Gateway padrao nao encontrado"
|
|
fi
|
|
}
|
|
|
|
check_forwarding() {
|
|
local current persisted
|
|
current="$(cat /proc/sys/net/ipv4/ip_forward 2>/dev/null || printf 'indisponivel')"
|
|
persisted="$(sysctl -n net.ipv4.ip_forward 2>/dev/null || printf 'indisponivel')"
|
|
log_line "$REDE_LOG" "ip_forward atual: $current"
|
|
log_line "$REDE_LOG" "ip_forward via sysctl: $persisted"
|
|
}
|
|
|
|
check_nat_rules() {
|
|
local default_iface iptables_ok=1 nft_ok=1
|
|
default_iface="$(detect_default_iface)"
|
|
if [[ -z "$default_iface" ]]; then
|
|
log_line "$REDE_LOG" "Nao foi possivel identificar a interface de saida para internet"
|
|
return 0
|
|
fi
|
|
|
|
if command -v iptables >/dev/null 2>&1; then
|
|
if iptables -t nat -S POSTROUTING 2>/dev/null | grep -qE "MASQUERADE.*-o ${default_iface}|-o ${default_iface} .*MASQUERADE"; then
|
|
log_line "$REDE_LOG" "Regra NAT via iptables encontrada para interface $default_iface"
|
|
iptables_ok=0
|
|
else
|
|
log_line "$REDE_LOG" "Regra NAT via iptables nao encontrada para interface $default_iface"
|
|
fi
|
|
else
|
|
log_line "$REDE_LOG" "iptables nao disponivel"
|
|
fi
|
|
|
|
if command -v nft >/dev/null 2>&1; then
|
|
if nft list ruleset 2>/dev/null | grep -qE "masquerade"; then
|
|
log_line "$REDE_LOG" "Regra NAT via nftables encontrada"
|
|
nft_ok=0
|
|
else
|
|
log_line "$REDE_LOG" "Regra NAT via nftables nao encontrada"
|
|
fi
|
|
else
|
|
log_line "$REDE_LOG" "nftables nao disponivel"
|
|
fi
|
|
|
|
if [[ "$iptables_ok" -ne 0 && "$nft_ok" -ne 0 ]]; then
|
|
log_line "$REDE_LOG" "Nenhuma regra de mascaramento foi confirmada"
|
|
fi
|
|
}
|
|
|
|
check_network_common() {
|
|
local iface_count
|
|
iface_count="$(ip -o link show 2>/dev/null | awk -F': ' '{print $2}' | grep -vc '^lo$')"
|
|
log_line "$REDE_LOG" "Quantidade de interfaces (excluindo loopback): $iface_count"
|
|
log_line "$REDE_LOG" "Enderecos IPv4 detectados:"
|
|
list_interfaces_ipv4 >> "$REDE_LOG" 2>&1 || true
|
|
|
|
test_connectivity "8.8.8.8" "via IP"
|
|
test_connectivity "google.com" "via DNS"
|
|
}
|
|
|
|
extract_dhcp_iface() {
|
|
awk -F'=' '/^\s*INTERFACESv4=/{gsub(/"/, "", $2); print $2; exit}' /etc/default/isc-dhcp-server 2>/dev/null
|
|
}
|
|
|
|
extract_first_subnet() {
|
|
awk '
|
|
/^\s*subnet[[:space:]]+/ {
|
|
for (i = 1; i <= NF; i++) {
|
|
if ($i == "subnet") subnet = $(i + 1)
|
|
if ($i == "netmask") netmask = $(i + 1)
|
|
}
|
|
if (subnet != "" && netmask != "") {
|
|
print subnet " " netmask
|
|
exit
|
|
}
|
|
}
|
|
' /etc/dhcp/dhcpd.conf 2>/dev/null
|
|
}
|
|
|
|
ip_to_int() {
|
|
local a b c d
|
|
IFS=. read -r a b c d <<< "$1"
|
|
printf '%u\n' "$(( (a << 24) + (b << 16) + (c << 8) + d ))"
|
|
}
|
|
|
|
ip_in_subnet() {
|
|
local ip="$1"
|
|
local subnet="$2"
|
|
local mask="$3"
|
|
local ip_i subnet_i mask_i
|
|
ip_i="$(ip_to_int "$ip")"
|
|
subnet_i="$(ip_to_int "$subnet")"
|
|
mask_i="$(ip_to_int "$mask")"
|
|
if (( (ip_i & mask_i) == (subnet_i & mask_i) )); then
|
|
return 0
|
|
fi
|
|
return 1
|
|
}
|
|
|
|
check_dhcp_ns1() {
|
|
local dhcp_iface iface_ip_cidr iface_ip subnet_data subnet mask status_name
|
|
|
|
if dpkg -s isc-dhcp-server >/dev/null 2>&1; then
|
|
log_line "$DHCP_LOG" "Servico isc-dhcp-server instalado"
|
|
else
|
|
log_line "$DHCP_LOG" "Servico isc-dhcp-server nao instalado"
|
|
fi
|
|
|
|
if [[ -f /etc/default/isc-dhcp-server ]]; then
|
|
dhcp_iface="$(extract_dhcp_iface)"
|
|
if [[ -n "$dhcp_iface" ]]; then
|
|
log_line "$DHCP_LOG" "Interface configurada em /etc/default/isc-dhcp-server: $dhcp_iface"
|
|
else
|
|
log_line "$DHCP_LOG" "Interface DHCP nao definida em /etc/default/isc-dhcp-server"
|
|
fi
|
|
else
|
|
log_line "$DHCP_LOG" "Arquivo /etc/default/isc-dhcp-server ausente"
|
|
fi
|
|
|
|
if [[ -n "${dhcp_iface:-}" ]]; then
|
|
iface_ip_cidr="$(ip -o -4 addr show dev "$dhcp_iface" 2>/dev/null | awk '{print $4; exit}')"
|
|
iface_ip="${iface_ip_cidr%%/*}"
|
|
if [[ -n "$iface_ip" ]]; then
|
|
log_line "$DHCP_LOG" "IPv4 da interface DHCP ($dhcp_iface): $iface_ip"
|
|
else
|
|
log_line "$DHCP_LOG" "Nao foi possivel obter IPv4 da interface DHCP ($dhcp_iface)"
|
|
fi
|
|
fi
|
|
|
|
subnet_data="$(extract_first_subnet)"
|
|
if [[ -n "$subnet_data" ]]; then
|
|
subnet="${subnet_data%% *}"
|
|
mask="${subnet_data##* }"
|
|
log_line "$DHCP_LOG" "Escopo identificado em /etc/dhcp/dhcpd.conf: subnet=$subnet netmask=$mask"
|
|
if [[ -n "${iface_ip:-}" ]]; then
|
|
if ip_in_subnet "$iface_ip" "$subnet" "$mask"; then
|
|
log_line "$DHCP_LOG" "IPv4 da interface DHCP condiz com o escopo configurado"
|
|
else
|
|
log_line "$DHCP_LOG" "IPv4 da interface DHCP NAO condiz com o escopo configurado"
|
|
fi
|
|
fi
|
|
else
|
|
log_line "$DHCP_LOG" "Nao foi possivel identificar escopo DHCP em /etc/dhcp/dhcpd.conf"
|
|
fi
|
|
|
|
status_name="isc-dhcp-server"
|
|
if systemctl status "$status_name" >> "$DHCP_LOG" 2>&1; then
|
|
log_line "$DHCP_LOG" "Status do servico $status_name: ativo/consultado com sucesso"
|
|
else
|
|
log_line "$DHCP_LOG" "Status do servico $status_name: falha ou servico inativo"
|
|
fi
|
|
}
|
|
|
|
check_dhcp_web() {
|
|
local default_iface gateway client_ip_cidr client_ip
|
|
|
|
default_iface="$(detect_default_iface)"
|
|
gateway="$(ip route show default 2>/dev/null | awk '/default/ {print $3; exit}')"
|
|
|
|
if [[ -z "$default_iface" || -z "$gateway" ]]; then
|
|
log_line "$DHCP_LOG" "Nao foi possivel identificar interface/gateway da WEB"
|
|
return 0
|
|
fi
|
|
|
|
client_ip_cidr="$(ip -o -4 addr show dev "$default_iface" 2>/dev/null | awk '{print $4; exit}')"
|
|
client_ip="${client_ip_cidr%%/*}"
|
|
|
|
log_line "$DHCP_LOG" "Interface de rede principal da WEB: $default_iface"
|
|
log_line "$DHCP_LOG" "Gateway configurado na WEB: $gateway"
|
|
if [[ -n "$client_ip" ]]; then
|
|
log_line "$DHCP_LOG" "IPv4 atual da WEB na interface $default_iface: $client_ip"
|
|
else
|
|
log_line "$DHCP_LOG" "Nao foi possivel obter o IPv4 atual da WEB na interface $default_iface"
|
|
fi
|
|
log_line "$DHCP_LOG" "Teste ativo com dhcping desabilitado por decisao de implementacao"
|
|
}
|
|
|
|
parse_args() {
|
|
while (($# > 0)); do
|
|
case "$1" in
|
|
-h|--help)
|
|
print_usage
|
|
exit 0
|
|
;;
|
|
*)
|
|
if [[ ! "$1" =~ ^[0-9]+$ ]]; then
|
|
printf 'Erro: RA invalido: %s\n' "$1" >&2
|
|
exit 1
|
|
fi
|
|
RA_ARGS+=("$1")
|
|
if ((${#RA_ARGS[@]} > 3)); then
|
|
printf 'Erro: nao e permitido informar mais que tres integrantes.\n' >&2
|
|
exit 1
|
|
fi
|
|
shift
|
|
;;
|
|
esac
|
|
done
|
|
|
|
}
|
|
|
|
run_vm_checks() {
|
|
check_os_installation
|
|
check_network_common
|
|
|
|
if [[ "$VM_TYPE" == "NS1" ]]; then
|
|
check_forwarding
|
|
check_nat_rules
|
|
check_dhcp_ns1
|
|
else
|
|
check_gateway
|
|
check_dhcp_web
|
|
fi
|
|
}
|
|
|
|
create_archive() {
|
|
local archive_path
|
|
archive_path="/root/dupla_${DUPLA_NUM}_${VM_TYPE}.tar.gz"
|
|
if tar -czf "$archive_path" -C "/root" "$(basename "$BASE_DIR")"; then
|
|
main_log "Arquivo compactado criado: $archive_path"
|
|
printf '%s\n' "$archive_path"
|
|
return 0
|
|
fi
|
|
error_log "Falha ao criar arquivo compactado"
|
|
return 1
|
|
}
|
|
|
|
send_to_telegram() {
|
|
local archive_path="$1"
|
|
local response_file http_code
|
|
|
|
response_file="$ENVIO_DIR/telegram_response.json"
|
|
|
|
if [[ -z "$BOT_TOKEN" || -z "$CHAT_ID" ]]; then
|
|
log_line "$TELEGRAM_LOG" "Envio nao realizado: BOT_TOKEN ou CHAT_ID nao informado"
|
|
return 1
|
|
fi
|
|
|
|
log_line "$TELEGRAM_LOG" "Iniciando envio do arquivo $archive_path"
|
|
http_code="$(
|
|
curl -sS -o "$response_file" -w '%{http_code}' \
|
|
-F "chat_id=$CHAT_ID" \
|
|
-F "document=@$archive_path" \
|
|
"https://api.telegram.org/bot${BOT_TOKEN}/sendDocument" 2>>"$TELEGRAM_LOG"
|
|
)"
|
|
|
|
log_line "$TELEGRAM_LOG" "HTTP status do envio: $http_code"
|
|
if [[ -f "$response_file" ]]; then
|
|
log_line "$TELEGRAM_LOG" "Resposta da API salva em $response_file"
|
|
fi
|
|
|
|
if [[ "$http_code" == "200" ]]; then
|
|
log_line "$TELEGRAM_LOG" "Envio concluido com sucesso"
|
|
return 0
|
|
fi
|
|
|
|
log_line "$TELEGRAM_LOG" "Envio falhou"
|
|
return 1
|
|
}
|
|
|
|
main() {
|
|
require_root
|
|
parse_args "$@"
|
|
|
|
printf 'Coleta e validacao da VM\n'
|
|
DUPLA_NUM="$(prompt_numeric 'Numero da dupla: ')" || exit 1
|
|
collect_identification_input || exit 1
|
|
VM_TYPE="$(prompt_vm_type)" || exit 1
|
|
|
|
setup_dirs
|
|
main_log "Inicio da execucao do script $SCRIPT_NAME"
|
|
main_log "Numero da dupla: $DUPLA_NUM"
|
|
main_log "Tipo de VM selecionado: $VM_TYPE"
|
|
|
|
save_identification
|
|
ensure_packages
|
|
collect_configs
|
|
run_vm_checks
|
|
|
|
local archive_path=""
|
|
if archive_path="$(create_archive)"; then
|
|
send_to_telegram "$archive_path" || true
|
|
fi
|
|
|
|
main_log "Execucao finalizada"
|
|
printf 'Coleta concluida. Evidencias em: %s\n' "$BASE_DIR"
|
|
}
|
|
|
|
main "$@"
|