#!/bin/sh # OpenWrt HA Presence Tracker Installer set -e GITEA_RAW_URL="https://git.darkmode.duckdns.org/sirmrak/openwrt-ha-presence/raw/branch/main/files" CONFIG_FILE="/etc/config/openwrt_ha" STATES_DIR="/tmp/mqtt_ha_states" info() { echo "[INFO] $1"; } warn() { echo "[WARN] $1"; } error() { echo "[ERROR] $1"; } validate_mac() { echo "$1" | grep -qE "^([0-9A-Fa-f]{2}:){5}[0-9A-Fa-f]{2}$" } if [ "$(id -u)" -ne 0 ]; then error "Скрипт должен выполняться от имени root." exit 1 fi # === ПРОВЕРКА ПАКЕТОВ === info "Проверка необходимых пакетов..." if opkg list-installed | grep -q "^mosquitto-client-nossl " && opkg list-installed | grep -q "^hostapd-utils "; then info "Пакеты уже установлены. Пропускаем." else info "Установка зависимостей..." opkg update >/dev/null 2>&1 || warn "Не удалось обновить списки opkg." opkg install mosquitto-client-nossl hostapd-utils >/dev/null 2>&1 || warn "Не удалось установить пакеты." if ! opkg list-installed | grep -q "^mosquitto-client-nossl " || ! opkg list-installed | grep -q "^hostapd-utils "; then warn "Не удалось установить необходимые пакеты." printf "Продолжить всё равно? [y/N]: " read answer case "$answer" in [yY]*) ;; *) exit 1 ;; esac fi fi # === МЕНЮ ПРИ СУЩЕСТВУЮЩЕМ КОНФИГЕ === SKIP_CONFIG=false ADD_DEVICE_ONLY=false if [ -f "$CONFIG_FILE" ]; then echo "" echo "Обнаружена существующая конфигурация." echo "1) Обновить скрипты (настройки сохранятся)" echo "2) Добавить новое устройство" echo "3) Удалить интеграцию полностью" echo "4) Выход" printf "Выберите [1-4]: " read choice case "$choice" in 1) SKIP_CONFIG=true ;; 2) SKIP_CONFIG=true; ADD_DEVICE_ONLY=true ;; 3) info "Удаление..." crontab -l 2>/dev/null | grep -v "mqtt_ha_discovery.sh" | crontab - 2>/dev/null || true /etc/init.d/cron restart 2>/dev/null || true /etc/init.d/openwrt_presence stop 2>/dev/null || true /etc/init.d/openwrt_presence disable 2>/dev/null || true rm -f /etc/init.d/openwrt_presence /etc/hostapd.user /usr/bin/mqtt_ha_discovery.sh "$CONFIG_FILE" rm -rf "$STATES_DIR" info "Удаление завершено. Удалите сущности в Home Assistant вручную." exit 0 ;; *) exit 1 ;; esac fi # === ВВОД НАСТРОЕК MQTT (только при первой установке) === if [ "$SKIP_CONFIG" = "false" ]; then echo "" echo "=== Настройка MQTT брокера ===" echo "(Нажмите Enter для значения по умолчанию)" printf "IP или домен MQTT брокера [192.168.1.100]: " read MQTT_HOST; MQTT_HOST=${MQTT_HOST:-192.168.1.100} printf "Порт MQTT [1883]: " read MQTT_PORT; MQTT_PORT=${MQTT_PORT:-1883} printf "Логин MQTT [mqtt_user]: " read MQTT_USER; MQTT_USER=${MQTT_USER:-mqtt_user} printf "Пароль MQTT [mqtt_password]: " read MQTT_PASS; MQTT_PASS=${MQTT_PASS:-mqtt_password} printf "Базовый топик MQTT [openwrt]: " read BASE_TOPIC; BASE_TOPIC=${BASE_TOPIC:-openwrt} echo "" info "Проверка подключения к MQTT..." if mosquitto_pub -h "$MQTT_HOST" -p "$MQTT_PORT" -u "$MQTT_USER" -P "$MQTT_PASS" \ -t "${BASE_TOPIC}/test/install" -m "ping" -I "installer_$$" -r 2>/dev/null; then info "Подключение к MQTT успешно." else warn "Не удалось подключиться к MQTT брокеру." printf "Продолжить всё равно? [y/N]: " read answer case "$answer" in [yY]*) ;; *) exit 1 ;; esac fi # === СКАЧИВАНИЕ И ЗАПОЛНЕНИЕ КОНФИГА === info "Скачивание шаблона конфигурации..." wget --no-check-certificate -O "$CONFIG_FILE" "$GITEA_RAW_URL/openwrt_ha" >/dev/null 2>&1 || exit 1 # Заполняем секцию MQTT sed -i "/config mqtt 'main'/,/^$/ { s|option host '.*'|option host '${MQTT_HOST}'| s|option port '.*'|option port '${MQTT_PORT}'| s|option user '.*'|option user '${MQTT_USER}'| s|option pass '.*'|option pass '${MQTT_PASS}'| s|option base_topic '.*'|option base_topic '${BASE_TOPIC}'| }" "$CONFIG_FILE" info "Конфигурация создана: $CONFIG_FILE" fi # === ДОБАВЛЕНИЕ УСТРОЙСТВ === if [ "$SKIP_CONFIG" = "false" ] || [ "$ADD_DEVICE_ONLY" = "true" ]; then echo "" printf "Добавить устройство прямо сейчас? [Y/n]: " read answer case "$answer" in [nN]*) SKIP_DEVICES=true ;; *) SKIP_DEVICES=false ;; esac fi if [ "$SKIP_DEVICES" != "true" ]; then # Определяем номер следующего устройства DEVICE_COUNT=$(grep -c "^config device" "$CONFIG_FILE" 2>/dev/null || echo 0) DEVICE_COUNT=$((DEVICE_COUNT + 1)) while true; do echo "" echo "--- Устройство #$DEVICE_COUNT ---" printf "Имя устройства (например, 'Телефон'): " read DEVICE_NAME DEVICE_NAME=${DEVICE_NAME:-Устройство $DEVICE_COUNT} while true; do echo "Введите MAC-адрес(а) через пробел" echo "Пример: 14:e0:1d:c7:05:76 или 14:e0:1d:c7:05:76 aa:bb:cc:dd:ee:ff" printf "MAC-адрес(а): " read DEVICE_MACS if [ -z "$DEVICE_MACS" ]; then warn "Необходимо ввести хотя бы один MAC-адрес." continue fi ALL_VALID=true for mac in $DEVICE_MACS; do if ! validate_mac "$mac"; then warn "Неверный формат MAC: $mac" ALL_VALID=false break fi done [ "$ALL_VALID" = "true" ] && break done echo "Тип устройства:" echo "1) Трекер (люди, статусы home/not_home)" echo "2) Тревога/IoT (розетки, статусы online/offline)" printf "Выберите [1-2] [1]: " read DEVICE_TYPE_NUM DEVICE_TYPE_NUM=${DEVICE_TYPE_NUM:-1} if [ "$DEVICE_TYPE_NUM" = "2" ]; then DEVICE_TYPE="alarm" DEFAULT_DELAY="0" else DEVICE_TYPE="tracker" DEFAULT_DELAY="30" fi printf "Задержка перед отправкой 'отключен' (сек) [$DEFAULT_DELAY]: " read DEVICE_DELAY DEVICE_DELAY=${DEVICE_DELAY:-$DEFAULT_DELAY} # Дописываем секцию устройства в конец конфига cat >> "$CONFIG_FILE" << EOF config device 'device${DEVICE_COUNT}' option name '${DEVICE_NAME}' option macs '${DEVICE_MACS}' option type '${DEVICE_TYPE}' option delay '${DEVICE_DELAY}' EOF info "Устройство '$DEVICE_NAME' добавлено." printf "Добавить еще одно устройство? [Y/n]: " read answer case "$answer" in [nN]*) break ;; esac DEVICE_COUNT=$((DEVICE_COUNT + 1)) done fi # === СКАЧИВАНИЕ СКРИПТОВ === info "Загрузка файлов из репозитория..." if ! wget --spider --no-check-certificate "$GITEA_RAW_URL/hostapd.user" >/dev/null 2>&1; then error "Не удалось подключиться к репозиторию: $GITEA_RAW_URL" exit 1 fi wget --no-check-certificate -O /etc/hostapd.user "$GITEA_RAW_URL/hostapd.user" >/dev/null 2>&1 || exit 1 wget --no-check-certificate -O /usr/bin/mqtt_ha_discovery.sh "$GITEA_RAW_URL/mqtt_ha_discovery.sh" >/dev/null 2>&1 || exit 1 wget --no-check-certificate -O /etc/init.d/openwrt_presence "$GITEA_RAW_URL/openwrt_presence" >/dev/null 2>&1 || exit 1 chmod +x /etc/hostapd.user /usr/bin/mqtt_ha_discovery.sh /etc/init.d/openwrt_presence # === АВТОЗАПУСК === info "Настройка автозапуска..." /etc/init.d/openwrt_presence enable >/dev/null 2>&1 /etc/init.d/openwrt_presence restart >/dev/null 2>&1 sleep 2 if ! ps | grep -q "[h]ostapd_cli"; then warn "Служба запущена, но процесс hostapd_cli не найден." echo "Проверьте: logread | grep hostapd" echo "Возможно, ваши интерфейсы Wi-Fi называются не phy0-ap0/phy1-ap0 (проверьте: iw dev)" fi # === CRON === info "Настройка Cron..." if command -v crontab >/dev/null 2>&1; then if ! crontab -l 2>/dev/null | grep -q "mqtt_ha_discovery.sh"; then (crontab -l 2>/dev/null; echo "* * * * * /usr/bin/mqtt_ha_discovery.sh") | crontab - 2>/dev/null /etc/init.d/cron restart 2>/dev/null fi else warn "Cron не установлен. Установите: opkg install cron" fi # === ИНИЦИАЛИЗАЦИЯ === info "Первичная инициализация..." /usr/bin/mqtt_ha_discovery.sh >/dev/null 2>&1 || warn "Инициализация завершилась с ошибкой." echo "" echo "==================================================" info "Установка успешно завершена!" echo "==================================================" echo "Конфигурация: vi /etc/config/openwrt_ha" echo "Логи: logread | grep wifi_tracker" echo "" echo "Для проверки: выключите Wi-Fi на добавленном устройстве" echo "и проверьте лог через указанную задержку."