apfree-wifidog: improve structure and readability
authorDengfeng Liu <liudf0716@gmail.com>
Sat, 26 Oct 2024 12:47:06 +0000 (20:47 +0800)
committerTianling Shen <cnsztl@gmail.com>
Fri, 1 Nov 2024 08:53:41 +0000 (16:53 +0800)
- Refactored wifidogx.init to improve code structure and readability.
- Added local authentication support, allowing authentication without a server.

Signed-off-by: Dengfeng Liu <liudf0716@gmail.com>
net/apfree-wifidog/files/wifidogx.conf
net/apfree-wifidog/files/wifidogx.init

index 7026418648d7be216a74573a0ed562fb958a8216..0d0ce5baf40005a281d29e4f0e1b217183596a1f 100644 (file)
@@ -12,6 +12,7 @@ config wifidogx 'common'
        option apple_cna 0
        option enable_websocket 1
        option enable_dns_forward 1
+       option no_auth_server 0
 
 config group 'wechat'
         option g_type '3'
index 094bf491ef5485af7ae753bbda0a009e4ebe4a5f..39ed9ea47eab09fffb0c1695413b50968df6d753 100644 (file)
 # Copyright (C) 2018 Dengfeng Liu
 
 START=99
-
 USE_PROCD=1
 NAME=wifidogx
-PROG=/usr/bin/${NAME}
-CONFIGFILE=/tmp/wifidogx.conf
+PROG="/usr/bin/${NAME}"
+CONFIGFILE="/tmp/wifidogx.conf"
 
 handle_gateway() {
-       local section=$1
+       local section="$1"
        local gateway_name gateway_channel gateway_id
 
-       config_get gateway_name $section gateway_name
-       config_get gateway_channel $section gateway_channel
-       config_get gateway_id $section gateway_id
-       if [ -z "$gateway_name" ] || [ -z  "$gateway_channel" ]; then
-               echo "gateway_name is required for $section" >&2
+       config_get gateway_name "$section" gateway_name
+       config_get gateway_channel "$section" gateway_channel
+       config_get gateway_id "$section" gateway_id
+
+       if [ -z "$gateway_name" ] || [ -z "$gateway_channel" ]; then
+               echo "gateway_name and gateway_channel are required for $section" >&2
                return
        fi
-       # if gateway_id is not set, get it from the gateway_name
+
+       # Get gateway_id from gateway_name if not set
        if [ -z "$gateway_id" ]; then
-               gateway_id=$(ifconfig $gateway_name | grep HWaddr | awk '{print $5}' | tr 'a-z' 'A-Z')
-               [ -z "$gateway_id" ] && {
+               gateway_id=$(ifconfig "$gateway_name" | awk '/HWaddr/ {print toupper($5)}' | tr -d ':')
+               if [ -z "$gateway_id" ]; then
                        echo "Failed to get gateway_id for $gateway_name" >&2
                        return
-               }
-               gateway_id=$(echo $gateway_id | tr -d ':')
-               uci set wifidogx.$section.gateway_id=$gateway_id
+               fi
+               uci set wifidogx."$section".gateway_id="$gateway_id"
                uci commit wifidogx
        fi
 
-       echo "GatewaySetting { 
-       GatewayInterface $gateway_name
-       GatewayChannel $gateway_channel
-       GatewayID $gateway_id
-}" >> ${CONFIGFILE}
+       printf "GatewaySetting { 
+               GatewayInterface %s
+               GatewayChannel %s
+               GatewayID %s
+       }\n" "$gateway_name" "$gateway_channel" "$gateway_id" >> "$CONFIGFILE"
 }
 
-prepare_wifidog_conf() {
+add_white_list_entries() {
+       local list_type="$1"
+       local uci_field="$2"
+       local target_variable="$3"
+
+       list_type=$(uci get wifidogx.common."$list_type")
+       for group in $list_type; do
+               group_list=$(uci get wifidogx."$group"."$uci_field")
+               if [ -n "$group_list" ]; then
+                       eval "$target_variable=\"\${$target_variable} \$group_list\""
+               fi
+       done
+}
+
+prepare_common_settings() {
+       printf "CheckInterval %s\nClientTimeout %s\nJsFilter %s\nWiredPassed %s\nBypassAppleCNA %s\nEnableDNSForward %s\n" \
+               "$check_interval" "$client_timeout" "$js_filter" "$wired_passed" "$apple_cna" "$enable_dns_forward" >> "$CONFIGFILE"
 
-       [ -f ${CONFIGFILE} ] && rm -f ${CONFIGFILE}
+       [ -n "$trusted_domains" ] && printf "TrustedDomains %s\n" "$(echo "$trusted_domains" | tr ' ' ',')" >> "$CONFIGFILE"
+       [ -n "$trusted_macs" ] && printf "TrustedMACList %s\n" "$(echo "$trusted_macs" | tr ' ' ',')" >> "$CONFIGFILE"
+       [ -n "$trusted_wildcard_domains" ] && printf "TrustedPanDomains %s\n" "$(echo "$trusted_wildcard_domains" | tr ' ' ',')" >> "$CONFIGFILE"
+}
+
+prepare_auth_server_settings() {
+       case "$auth_server_mode" in
+       cloud)
+               printf "DeviceID %s\nAuthServer {\n\tHostname %s\n\tHTTPPort %s\n\tPath %s\n}\n" \
+                       "$device_id" "$auth_server_hostname" "$auth_server_port" "$auth_server_path" >> "$CONFIGFILE"
+        
+               case "$long_conn_mode" in
+               ws|wss)
+                       ws_hostname="${ws_server_hostname:-$auth_server_hostname}"
+                       ws_port="${ws_server_port:-$auth_server_port}"
+                       ws_ssl=$([ "$long_conn_mode" = "wss" ] && echo 1 || echo 0)
+                       printf "WebSocket {\n\tWSServer %s\n\tWSServerPort %s\n\tWSServerPath %s\n\tWSServerSSL %s\n}\n" \
+                               "$ws_hostname" "$ws_port" "$ws_server_path" "$ws_ssl" >> "$CONFIGFILE"
+                       ;;
+               mqtt)
+                       mqtt_hostname="${mqtt_server_hostname:-$auth_server_hostname}"
+                       mqtt_port="${mqtt_server_port:-1883}"
+                       printf "MQTT {\n\tMQTTHost %s\n\tMQTTPort %s\n\tMQTTUsername %s\n\tMQTTPassword %s\n}\n" \
+                               "$mqtt_hostname" "$mqtt_port" "${mqtt_username:-}" "${mqtt_password:-}" >> "$CONFIGFILE"
+                       ;;
+               esac
+                       ;;
+       local)
+               [ -n "$auth_server_offline_file" ] && printf "AuthServerOfflineFile %s\n" "$auth_server_offline_file" >> "$CONFIGFILE"
+               [ -n "$local_portal" ] && printf "LocalPortal %s\n" "$local_portal" >> "$CONFIGFILE"
+               ;;
+       esac
+}
 
-       uci_validate_section ${NAME} ${NAME} common \
+prepare_external_interface() {
+       [ -z "$external_interface" ] && echo "No ExternalInterface " >&2 && return
+       local external_interface_name
+       external_interface_name=$(uci get network."$external_interface".device)
+       [ -z "$external_interface_name" ] && echo "Failed to get device name for $external_interface" >&2 && return
+  
+       printf "ExternalInterface %s\n" "$external_interface_name" >> "$CONFIGFILE"
+}
+
+prepare_wifidog_conf() {
+       [ -f "$CONFIGFILE" ] && rm -f "$CONFIGFILE"
+       local long_conn_mode_value='"ws", "wss", "mqtt", "none"'
+       local auth_server_mode_value='"cloud", "local"'
+    
+       uci_validate_section "$NAME" "$NAME" common \
                'enabled:bool:0' \
+               "auth_server_mode:or($auth_server_mode_value)" \
                'log_level:integer:7' \
                'device_id:string' \
                'auth_server_hostname:string' \
@@ -60,88 +123,42 @@ prepare_wifidog_conf() {
                'mac_white_list:list(string)' \
                'wildcard_white_list:list(string)' \
                'enable_dns_forward:bool:1' \
-               'enable_websocket:bool:1' \
-               'js_filter:bool:1' 
-
-       if [ ! -z "$app_white_list" ]; then
-               # iterate app_white_list and find the corresponding domain according to the item
-               for group in $app_white_list; do
-                       group_domain_list=$(uci get wifidogx.$group.domain_name)
-                       # if the domain list is not empty, add it to trusted_domains
-                       if [ ! -z "$group_domain_list" ]; then
-                               trusted_domains="$trusted_domains $group_domain_list"
-                       fi
-               done
-       fi
-
-       if [ ! -z "$mac_white_list" ]; then
-               # iterate mac_white_list and find the corresponding mac according to the item
-               for group in $mac_white_list; do
-                       group_mac_list=$(uci get wifidogx.$group.mac_address)
-                       # if the mac list is not empty, add it to trusted_macs
-                       if [ ! -z "$group_mac_list" ]; then
-                               trusted_macs="$trusted_macs $group_mac_list"
-                       fi
-               done
-       fi
-
-       if [ ! -z "$wildcard_white_list" ]; then
-               # iterate wildcard_white_list and find the corresponding domain according to the item
-               for group in $wildcard_white_list; do
-                       group_wildcard_list=$(uci get wifidogx.$group.wildcard_domain)
-                       if [ ! -z "$group_wildcard_list" ]; then
-                               trusted_wildcard_domains="$trusted_wildcard_domains $group_wildcard_list"
-                       fi
-               done
-       fi
-
-       # set above variables to config file
-       echo "DeviceID $device_id" > ${CONFIGFILE}
-       echo "AuthServer {
-       Hostname $auth_server_hostname
-       HTTPPort $auth_server_port
-       Path $auth_server_path
-}" >> ${CONFIGFILE}
-       echo "CheckInterval $check_interval" >> ${CONFIGFILE}
-       echo "ClientTimeout $client_timeout" >> ${CONFIGFILE}
-       echo "JsFilter $js_filter" >> ${CONFIGFILE}
-       echo "WiredPassed $wired_passed" >> ${CONFIGFILE}
-       echo "BypassAppleCNA $apple_cna" >> ${CONFIGFILE}
-       echo "EnableDNSForward $enable_dns_forward" >> ${CONFIGFILE}
-       echo "EnableWS $enable_websocket" >> ${CONFIGFILE}
-       # if has trusted_domains, parse the list to a string with ',' as separator and add it to config file
-       if [ ! -z "$trusted_domains" ]; then
-               trusted_domains=$(echo $trusted_domains | tr ' ' ',')
-               echo "TrustedDomains $trusted_domains" >> ${CONFIGFILE}
-       fi
-       # if has trusted_macs, add it to config file
-       if [ ! -z "$trusted_macs" ]; then
-               trusted_macs=$(echo $trusted_macs | tr ' ' ',')
-               echo "TrustedMACList $trusted_macs" >> ${CONFIGFILE}
-       fi
-       # if has trusted_wildcard_domains, add it to config file
-       if [ ! -z "$trusted_wildcard_domains" ]; then
-               trusted_wildcard_domains=$(echo $trusted_wildcard_domains | tr ' ' ',')
-               echo "TrustedPanDomains $trusted_wildcard_domains" >> ${CONFIGFILE}
-       fi
-
+               "long_conn_mode:or($long_conn_mode_value)" \
+               'ws_server_hostname:string' \
+               'ws_server_port:port:80' \
+               'ws_server_path:string:/ws/wifidogx' \
+               'mqtt_server_hostname:string' \
+               'mqtt_server_port:port:1883' \
+               'mqtt_username:string' \
+               'mqtt_password:string' \
+               'js_filter:bool:1' \
+               'auth_server_offline_file:string' \
+               'local_portal:string' \
+               'external_interface:string'
+
+       [ -n "$app_white_list" ] && add_white_list_entries "app_white_list" "domain_name" "trusted_domains"
+       [ -n "$mac_white_list" ] && add_white_list_entries "mac_white_list" "mac_address" "trusted_macs"
+       [ -n "$wildcard_white_list" ] && add_white_list_entries "wildcard_white_list" "wildcard_domain" "trusted_wildcard_domains"
+
+       prepare_external_interface
+       prepare_auth_server_settings
        config_foreach handle_gateway gateway
+       prepare_common_settings
 }
 
 start_service() {
-       config_load $NAME
+       config_load "$NAME"
 
        prepare_wifidog_conf
 
-       [ "$enabled" -eq 0 ] && {
+       if [ "$enabled" -eq 0 ]; then
                echo "wifidogx is disabled, exit..." >&2
                return
-       }
+       fi
 
        procd_open_instance
-       # -f: run in foreground
-       procd_set_param command $PROG -c $CONFIGFILE -s -f -d $log_level
-       procd_set_param respawn # respawn automatically if something died
+       procd_set_param command "$PROG" -c "$CONFIGFILE" -s -f -d "$log_level"
+       procd_set_param respawn
        procd_set_param file /etc/config/wifidogx
        procd_close_instance
 }
@@ -151,11 +168,12 @@ status_service() {
 }
 
 reload_service() {
-       stop 
+       stop
        start
 }
 
 service_triggers() {
-       procd_add_reload_trigger "${NAME}"
-       procd_add_interface_trigger "interface.*.up" "wan" /etc/init.d/wifidogx restart
+       procd_add_reload_trigger "wifidogx" "firewall"
+       procd_add_interface_trigger "interface.*.up" "wan" /etc/init.d/wifidogx reload
+       procd_add_interface_trigger "interface.*.up" "wan6" /etc/init.d/wifidogx reload
 }