kuoruan / luci-app-kcptun

LuCI support for kcptun
Apache License 2.0
316 stars 84 forks source link

希望启动多个kcp实例 做负载均衡 有解决办法吗 #56

Open JoveYu opened 4 years ago

JoveYu commented 4 years ago

希望启动多个kcp实例 做负载均衡 有解决办法吗

sqliuchang commented 4 years ago

自己复制修改init脚本,然后启用就行了

Ding-Kyoma commented 3 years ago

@sqliuchang 能分享一下你修改后的init脚本么,我简单的改了一下开头的KCPTUN=kcptun 、 CONFIG_FOLDER=/var/etc/$KCPTUN 以及相应的配置,结果还是不能用

sqliuchang commented 3 years ago
#!/bin/sh /etc/rc.common
#
# Copyright 2016-2019 Xingwang Liao <kuoruan@gmail.com>
#
# Licensed under the Apache License, Version 2.0 (the "License");
# you may not use this file except in compliance with the License.
# You may obtain a copy of the License at
#
#    http://www.apache.org/licenses/LICENSE-2.0
#
# Unless required by applicable law or agreed to in writing, software
# distributed under the License is distributed on an "AS IS" BASIS,
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
# See the License for the specific language governing permissions and
# limitations under the License.
#

START=99
USE_PROCD=1

KCP0=kcp0
CONFIG_FOLDER=/var/etc/$KCP0

if [ -r /usr/share/libubox/jshn.sh ]; then
    . /usr/share/libubox/jshn.sh
elif [ -r /lib/functions/jshn.sh ]; then
    . /lib/functions/jshn.sh
else
    logger -p daemon.err -t "$KCP0" \
        "Package required: jshn."
    exit 1
fi

_log() {
    local level="$1"
    local msg="$2"

    logger -p "daemon.${level}" -t "$KCP0" "$msg"
}

gen_client_config_file() {
    local config_file="$1"

    json_init
    json_add_string "remoteaddr" "${server_addr}:${server_port}"
    json_add_string "localaddr" "${listen_addr}:${listen_port}"

    add_configs() {
        local type="$1"; shift
        local k v

        for k in "$@"; do
            v="$(eval echo "\$$k")"

            if [ -n "$v" ]; then
                if [ "$type" = "string" ]; then
                    json_add_string "$k" "$v"
                elif [ "$type" = "int" ]; then
                    json_add_int "$k" "$v"
                elif [ "$type" = "boolean" ]; then
                    if [ "$v" = "true" ]; then
                        json_add_boolean "$k" "1"
                    else
                        json_add_boolean "$k" "0"
                    fi
                fi
            fi
        done
    }

    add_configs "string" key crypt mode
    add_configs "int" conn autoexpire mtu sndwnd rcvwnd datashard parityshard dscp \
        nodelay interval resend nc sockbuf smuxver smuxbuf streambuf keepalive scavengettl snmpperiod
    add_configs "boolean" nocomp acknodelay quiet tcp

    if [ -n "$log_file" ]; then
        json_add_string "log" "$log_file"
    fi

    json_close_object

    json_dump -i >"$config_file"
}

add_iptables_rule() {
    local port="$1"

    iptables-restore --noflush <<-EOF 2>/dev/null
        *nat
        :KCP0 -
        -A KCP0 -p tcp --dport $port -j ACCEPT
        -A INPUT -p tcp -j KCP0
        COMMIT
    EOF
}

clear_iptables_rule() {
    iptables-save --counters | grep -vi "KCP0" | iptables-restore --counters
}

validate_config_section() {
    uci_validate_section "$KCP0" general "$1" \
        'server:uciname' \
        'client_file:string' \
        'daemon_user:string:root' \
        'enable_logging:bool:0' \
        'log_folder:directory:/var/log/kcp0'
}

validate_server_section() {
    uci_validate_section "$KCP0" servers "$1" \
        'server_addr:host' \
        'server_port:port:29900' \
        'listen_addr:host:0.0.0.0' \
        'listen_port:port:12948' \
        'key:string' \
        'crypt:string:aes' \
        'mode:or("normal","fast","fast2","fast3","manual"):fast' \
        'conn:min(1)' \
        'autoexpire:uinteger' \
        'scavengettl:min(-1)' \
        'mtu:range(64,9200)' \
        'sndwnd:min(1)' \
        'rcvwnd:min(1)' \
        'datashard:uinteger' \
        'parityshard:uinteger' \
        'dscp:uinteger' \
        'nocomp:or("true", "false")' \
        'quiet:or("true", "false")' \
        'tcp:or("true", "false")' \
        'nodelay:bool' \
        'interval:uinteger' \
        'resend:range(0,2)' \
        'nc:bool' \
        'acknodelay:or("true", "false")' \
        'sockbuf:uinteger' \
        'smuxver:or("1", "2")' \
        'smuxbuf:uinteger' \
        'streambuf:uinteger' \
        'keepalive:uinteger' \
        'snmpperiod:min(1)'
}

validate_client_file() {
    local file="$1"

    if [ ! -f "$file" ]; then
        return 1
    fi

    test -x "$file" || chmod 755 "$file"

    ( $file -v 2>/dev/null | grep -q "kcp" )
}

start_kcptun_instance() {
    local section="$1"

    if ! validate_config_section "$section" ; then
        _log "err" "Config validate failed."
        return 1
    fi

    if [ -z "$server" ] || [ "$server" = "nil" ]; then
        _log "info" "No server selected, Client will stop."
        return 0
    elif ! validate_server_section "$server"; then
        _log "err" "Server config validation failed."
        return 1
    elif [ -z "$server_addr" ] || [ -z "$listen_port" ]; then
        _log "err" "Server config validation failed."
        return 1
    fi

    if [ -z "$client_file" ]; then
        _log "err" "Please set client file path, or use auto download."
        return 1;
    elif ! validate_client_file "$client_file"; then
        _log "err" "Client file validation failed."
        return 1
    fi

    is_ipv6_address() {
        echo "$1" | grep -q ":"
    }

    is_ipv6_address "$server_addr" && server_addr="[${server_addr}]"
    is_ipv6_address "$listen_addr" && listen_addr="[${listen_addr}]"

    test -d "$CONFIG_FOLDER" || mkdir -p "$CONFIG_FOLDER"

    log_file=""
    if [ "x$enable_logging" = "x1" ]; then
        mkdir -p "$log_folder"
        chown -R "$daemon_user" "$log_folder"
        log_file="${log_folder}/client.${section}.log"
    fi

    local config_file="${CONFIG_FOLDER}/client.${section}.json"

    if ! ( gen_client_config_file "$config_file" ); then
        _log "err" "Can't create config file".
        return 1
    fi

    procd_open_instance
    procd_set_param command "$client_file"
    procd_append_param command -c "$config_file"
    procd_set_param respawn
    procd_set_param user "$daemon_user"
    procd_set_param file "$config_file"
    procd_close_instance
}

service_triggers() {
    procd_add_reload_trigger "$KCP0"
}

start_service() {
    sleep 1

    config_load "$KCP0"
    config_foreach start_kcptun_instance "general"
}

我这个是老版本的脚本没有更新,而且去除了开放端口的部分,你们对照着原版看我改了什么可以自己修改 需要三开四开的就把KCP0 kcp0改成KCP1 kcp1就行了

Ding-Kyoma commented 3 years ago

@sqliuchang 你的模板跟(1.5.2-1)很接近,应该是同一版

另外创建了 /var/etc/kcp0/client.general.json,给init加了x权限 不过用了你的模板还是开不起来 image

是不是还有什么步骤遗漏的?

sqliuchang commented 3 years ago

kcp0.zip @GTGraphics3 应该是你config文件没配置好吧,你在luci下配置好kcptun之后,停止kcptun,然后复制这个配置文件/etc/config/kcptun到/etc/config/kcp0,然后启用kcp0试一下。还是不行的话可以用sh -x来调试。

Ding-Kyoma commented 3 years ago

@sqliuchang 非常感谢,在配置过/etc/config/kcp0后多开成功了!