From c05f847f1b2ef304ae37fd4f29fd0a3d7b4ca13f Mon Sep 17 00:00:00 2001 From: qaq <1937228092@qq.com> Date: Wed, 25 Jun 2025 12:05:59 +0800 Subject: [PATCH] =?UTF-8?q?=E6=94=AF=E6=8C=81ipv6?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- panel_install.sh | 516 ++++++++++++++++++----------------------------- 1 file changed, 195 insertions(+), 321 deletions(-) diff --git a/panel_install.sh b/panel_install.sh index 13a229b..627c987 100755 --- a/panel_install.sh +++ b/panel_install.sh @@ -27,326 +27,191 @@ check_docker() { echo "检测到 Docker 命令:$DOCKER_CMD" } -# 检查Docker IPv6支持的多种方法 -check_docker_ipv6_support() { - echo "🔍 验证Docker IPv6支持..." - - # 方法1: 检查daemon.json配置文件 - if [ -f "/etc/docker/daemon.json" ]; then - if grep -q '"ipv6".*true' /etc/docker/daemon.json 2>/dev/null; then - echo "✅ daemon.json配置检查通过" - return 0 - fi - fi - - # 方法2: 尝试创建IPv6测试网络 - echo "🧪 尝试创建IPv6测试网络..." - if docker network create --ipv6 --subnet=2001:db8:test::/64 ipv6-test-net 2>/dev/null; then - echo "✅ IPv6网络创建成功" - # 清理测试网络 - docker network rm ipv6-test-net >/dev/null 2>&1 - return 0 - fi - - # 方法3: 检查docker info的详细输出 - if docker info 2>/dev/null | grep -i ipv6 | grep -q true; then - echo "✅ docker info IPv6检查通过" - return 0 - fi - - # 方法4: 检查Docker版本和配置 - DOCKER_VERSION=$(docker version --format '{{.Server.Version}}' 2>/dev/null) - if [ -n "$DOCKER_VERSION" ]; then - echo "ℹ️ Docker版本: $DOCKER_VERSION" - # 对于新版本Docker,配置可能需要更多时间生效 - echo "⏳ 等待Docker配置生效..." - sleep 5 - - # 再次尝试网络创建 - if docker network create --ipv6 --subnet=2001:db8:test2::/64 ipv6-test-net2 2>/dev/null; then - echo "✅ 延迟检查IPv6网络创建成功" - docker network rm ipv6-test-net2 >/dev/null 2>&1 - return 0 - fi - fi - - echo "⚠️ IPv6支持验证失败,但配置可能已生效" - echo "ℹ️ 建议手动验证: docker network create --ipv6 --subnet=2001:db8:test::/64 test-net" - return 1 -} - -# 检查IPv6支持 +# 检测系统是否支持 IPv6 check_ipv6_support() { - echo "🔍 检查IPv6支持..." + echo "🔍 检测 IPv6 支持..." - # 检查内核是否支持IPv6 - if [ ! -f /proc/net/if_inet6 ]; then - echo "⚠️ 警告:系统内核不支持IPv6" + # 检查是否有 IPv6 地址(排除 link-local 地址) + if ip -6 addr show | grep -v "scope link" | grep -q "inet6"; then + echo "✅ 检测到系统支持 IPv6" + return 0 + elif ifconfig 2>/dev/null | grep -v "fe80:" | grep -q "inet6"; then + echo "✅ 检测到系统支持 IPv6" + return 0 + else + echo "⚠️ 未检测到 IPv6 支持" return 1 fi - - # 检查Docker是否支持IPv6 - if ! check_docker_ipv6_support; then - echo "⚠️ Docker守护进程未启用IPv6支持,正在自动配置..." - - # 自动配置Docker daemon.json - configure_docker_ipv6 - - # 重新检查 - if ! check_docker_ipv6_support; then - echo "❌ Docker IPv6配置失败,请手动检查" - return 1 - fi - fi - - echo "✅ IPv6支持检查通过" - return 0 } -# 配置Docker IPv6支持 +# 配置 Docker 启用 IPv6 configure_docker_ipv6() { - echo "🔧 正在配置Docker IPv6支持..." + echo "🔧 配置 Docker IPv6 支持..." - DAEMON_JSON_PATH="/etc/docker/daemon.json" + # 检查操作系统类型 + OS_TYPE=$(uname -s) - # 检查是否有写入权限 - if [ ! -w "/etc/docker" ] && [ ! -w "$DAEMON_JSON_PATH" ]; then - echo "⚠️ 需要管理员权限来配置Docker" - echo "🔐 正在请求sudo权限..." + if [[ "$OS_TYPE" == "Darwin" ]]; then + # macOS 上 Docker Desktop 已默认支持 IPv6 + echo "✅ macOS Docker Desktop 默认支持 IPv6" + return 0 fi - # 备份现有配置 - if [ -f "$DAEMON_JSON_PATH" ]; then - sudo cp "$DAEMON_JSON_PATH" "$DAEMON_JSON_PATH.backup.$(date +%Y%m%d_%H%M%S)" 2>/dev/null || { - echo "❌ 无法备份daemon.json文件,请检查权限" - return 1 - } - echo "✅ 已备份现有daemon.json配置" + # Docker daemon 配置文件路径 + DOCKER_CONFIG="/etc/docker/daemon.json" + + # 检查是否需要 sudo + if [[ $EUID -ne 0 ]]; then + SUDO_CMD="sudo" + else + SUDO_CMD="" fi - # 创建或更新daemon.json - if [ -f "$DAEMON_JSON_PATH" ]; then - # 文件存在,检查是否已配置IPv6 - if grep -q '"ipv6".*true' "$DAEMON_JSON_PATH" 2>/dev/null; then - echo "ℹ️ daemon.json已配置IPv6支持" + # 检查 Docker 配置文件 + if [ -f "$DOCKER_CONFIG" ]; then + # 检查是否已经配置了 IPv6 + if grep -q '"ipv6"' "$DOCKER_CONFIG"; then + echo "✅ Docker 已配置 IPv6 支持" else - echo "🔧 更新现有daemon.json配置..." - # 尝试多种方式更新JSON - JSON_UPDATED=false + echo "📝 更新 Docker 配置以启用 IPv6..." + # 备份原配置 + $SUDO_CMD cp "$DOCKER_CONFIG" "${DOCKER_CONFIG}.backup" - # 方法1: 使用jq + # 使用 jq 或 sed 添加 IPv6 配置 if command -v jq &> /dev/null; then - if sudo jq '. + {"ipv6": true, "fixed-cidr-v6": "2001:db8:1::/64"}' "$DAEMON_JSON_PATH" > /tmp/daemon.json.tmp 2>/dev/null && \ - sudo mv /tmp/daemon.json.tmp "$DAEMON_JSON_PATH" 2>/dev/null; then - JSON_UPDATED=true - echo "✅ 使用jq更新JSON配置" - fi - fi - - # 方法2: 使用Python3 - if [ "$JSON_UPDATED" = false ] && command -v python3 &> /dev/null; then - if sudo python3 -c " -import json -try: - with open('$DAEMON_JSON_PATH', 'r') as f: - config = json.load(f) -except: - config = {} -config['ipv6'] = True -config['fixed-cidr-v6'] = '2001:db8:1::/64' -with open('$DAEMON_JSON_PATH', 'w') as f: - json.dump(config, f, indent=2) -print('JSON updated successfully') -" 2>/dev/null; then - JSON_UPDATED=true - echo "✅ 使用Python3更新JSON配置" - fi - fi - - # 方法3: 手动创建新文件(简单覆盖) - if [ "$JSON_UPDATED" = false ]; then - echo "⚠️ 无法解析现有JSON,将创建新的配置文件" - read -p "这将覆盖现有的daemon.json配置,是否继续?(y/N): " confirm - if [[ "$confirm" == "y" || "$confirm" == "Y" ]]; then - sudo tee "$DAEMON_JSON_PATH" > /dev/null </dev/null || { - echo "❌ 无法创建/etc/docker目录" - return 1 - } - sudo tee "$DAEMON_JSON_PATH" > /dev/null < /dev/null; then - if sudo systemctl restart docker 2>/dev/null; then - echo "⏳ 等待Docker服务启动..." - sleep 5 - if sudo systemctl is-active docker &> /dev/null; then - echo "✅ Docker服务重启成功" + $SUDO_CMD jq '. + {"ipv6": true, "fixed-cidr-v6": "fd00::/80"}' "$DOCKER_CONFIG" > /tmp/daemon.json && $SUDO_CMD mv /tmp/daemon.json "$DOCKER_CONFIG" else - echo "❌ Docker服务启动失败" - sudo systemctl status docker --no-pager -l - return 1 + # 如果没有 jq,使用 sed + $SUDO_CMD sed -i 's/^{$/{\n "ipv6": true,\n "fixed-cidr-v6": "fd00::\/80",/' "$DOCKER_CONFIG" + fi + + echo "🔄 重启 Docker 服务..." + if command -v systemctl &> /dev/null; then + $SUDO_CMD systemctl restart docker + elif command -v service &> /dev/null; then + $SUDO_CMD service docker restart + else + echo "⚠️ 请手动重启 Docker 服务" fi - else - echo "❌ 无法重启Docker服务" - return 1 - fi - elif command -v service &> /dev/null; then - if sudo service docker restart 2>/dev/null; then sleep 5 - echo "✅ Docker服务重启完成" - else - echo "❌ 无法重启Docker服务" - return 1 fi else - echo "⚠️ 无法自动重启Docker服务,请手动重启:" - echo " sudo systemctl restart docker" - echo " 或者: sudo service docker restart" - return 1 + # 创建新的配置文件 + echo "📝 创建 Docker 配置文件..." + $SUDO_CMD mkdir -p /etc/docker + echo '{ + "ipv6": true, + "fixed-cidr-v6": "fd00::/80" +}' | $SUDO_CMD tee "$DOCKER_CONFIG" > /dev/null + + echo "🔄 重启 Docker 服务..." + if command -v systemctl &> /dev/null; then + $SUDO_CMD systemctl restart docker + elif command -v service &> /dev/null; then + $SUDO_CMD service docker restart + else + echo "⚠️ 请手动重启 Docker 服务" + fi + sleep 5 fi - - return 0 } -# 配置IPv6网络 -configure_ipv6_network() { - if [[ "$ENABLE_IPV6" == "true" ]]; then - echo "🌐 配置IPv6网络..." - - # 检查IPv6支持 - if ! check_ipv6_support; then - echo "❌ IPv6支持检查失败" - echo "" - echo "📋 您有以下选择:" - echo "1. 继续安装(仅使用IPv4网络)" - echo "2. 取消安装,手动配置IPv6后重试" - echo "" - read -p "请选择 (1/2): " ipv6_choice - - case $ipv6_choice in - 1) - echo "ℹ️ 继续安装,将使用IPv4网络" - ENABLE_IPV6=false - echo "✅ 网络配置完成(仅IPv4)" - echo "ℹ️ IPv4子网: 172.20.0.0/16" - return 0 - ;; - 2) - echo "❌ 安装已取消" - echo "ℹ️ 请参考以下步骤手动配置IPv6:" - echo " 1. 确保系统内核支持IPv6" - echo " 2. 编辑 /etc/docker/daemon.json 添加:" - echo ' {"ipv6": true, "fixed-cidr-v6": "2001:db8:1::/64"}' - echo " 3. 重启Docker服务: sudo systemctl restart docker" - echo " 4. 重新运行此安装脚本" - echo "ℹ️ 脚本会自动选择不冲突的IPv6子网" - exit 1 - ;; - *) - echo "❌ 无效选择,安装已取消" - exit 1 - ;; - esac - fi - - # 创建支持IPv6的docker-compose.yml配置 - echo "🔧 正在创建IPv6网络配置..." - - # 检查文件是否已包含IPv6配置 - if grep -q "enable_ipv6: true" docker-compose.yml && (grep -q "2001:db8:1::/64" docker-compose.yml || grep -q "2001:db8:2::/64" docker-compose.yml); then - EXISTING_IPV6_SUBNET=$(grep -o "2001:db8:[0-9]::/64" docker-compose.yml) - echo "✅ IPv6配置已存在" - echo "✅ IPv6网络配置完成" - echo "ℹ️ IPv6子网: $EXISTING_IPV6_SUBNET" - echo "ℹ️ IPv4子网: 172.20.0.0/16" - else - # 安全地添加IPv6配置,只修改networks部分 - echo "⚙️ 正在添加IPv6网络支持..." - - # 检测daemon.json中的IPv6子网,选择不冲突的子网 - IPV6_SUBNET="2001:db8:2::/64" # 默认使用2号子网 - if [ -f "/etc/docker/daemon.json" ]; then - if grep -q "2001:db8:2::/64" /etc/docker/daemon.json 2>/dev/null; then - IPV6_SUBNET="2001:db8:3::/64" # 如果2号被占用,使用3号 - fi - fi - echo "ℹ️ 将使用IPv6子网: $IPV6_SUBNET" - - # 创建临时文件来安全修改 - cp docker-compose.yml docker-compose.yml.backup - - # 使用awk来精确修改networks部分 - awk -v ipv6_subnet="$IPV6_SUBNET" ' - /^networks:/ { in_networks = 1 } - /^[a-zA-Z]/ && !/^networks:/ && in_networks { in_networks = 0 } - /^ gost-network:/ && in_networks { in_gost_network = 1 } - /^ [a-zA-Z]/ && !/^ gost-network:/ && in_gost_network { in_gost_network = 0 } - /^ driver: bridge$/ && in_gost_network && !ipv6_added { - print $0 - print " enable_ipv6: true" - ipv6_added = 1 - next - } - /^ - subnet: 172\.20\.0\.0\/16$/ && in_gost_network && !subnet_added { - print $0 - print " - subnet: " ipv6_subnet - subnet_added = 1 - next - } - { print } - ' docker-compose.yml.backup > docker-compose.yml - - # 验证修改是否成功 - if grep -q "enable_ipv6: true" docker-compose.yml && grep -q "$IPV6_SUBNET" docker-compose.yml; then - echo "✅ IPv6网络配置添加成功" - rm -f docker-compose.yml.backup - echo "✅ IPv6网络配置完成" - echo "ℹ️ IPv6子网: $IPV6_SUBNET" - echo "ℹ️ IPv4子网: 172.20.0.0/16" - else - echo "❌ IPv6网络配置添加失败" - echo "🔍 请检查docker-compose.yml文件" - if [ -f docker-compose.yml.backup ]; then - echo "📁 备份文件: docker-compose.yml.backup" - fi - fi - fi - else - echo "ℹ️ 跳过IPv6网络配置,仅使用IPv4网络" - echo "✅ 网络配置完成(仅IPv4)" - echo "ℹ️ IPv4子网: 172.20.0.0/16" - fi +# 更新 docker-compose.yml 以支持 IPv6 +update_compose_for_ipv6() { + echo "🔧 更新 docker-compose.yml 配置 IPv6..." + + # 创建支持 IPv6 的 docker-compose.yml + cat > docker-compose.yml.ipv6 <<'EOF' +services: + mysql: + image: mysql:5.7 + container_name: gost-mysql + restart: unless-stopped + environment: + MYSQL_ROOT_PASSWORD: ${DB_PASSWORD} + MYSQL_DATABASE: ${DB_NAME} + MYSQL_USER: ${DB_USER} + MYSQL_PASSWORD: ${DB_PASSWORD} + TZ: Asia/Shanghai + volumes: + - mysql_data:/var/lib/mysql + - ./gost.sql:/docker-entrypoint-initdb.d/init.sql:ro + command: > + --default-authentication-plugin=mysql_native_password + --character-set-server=utf8mb4 + --collation-server=utf8mb4_unicode_ci + --max_connections=1000 + --innodb_buffer_pool_size=256M + networks: + - gost-network + healthcheck: + test: ["CMD", "mysqladmin", "ping", "-h", "localhost"] + timeout: 10s + retries: 10 + + backend: + image: bqlpfy/springboot-backend:latest + container_name: springboot-backend + restart: unless-stopped + environment: + DB_HOST: mysql + DB_NAME: ${DB_NAME} + DB_USER: ${DB_USER} + DB_PASSWORD: ${DB_PASSWORD} + JWT_SECRET: ${JWT_SECRET} + LOG_DIR: /app/logs + SERVER_ADDR: ${SERVER_HOST} + JAVA_OPTS: "-Xms256m -Xmx512m -Dfile.encoding=UTF-8 -Duser.timezone=Asia/Shanghai" + ports: + - "${BACKEND_PORT}:6365" + - "[::]:${BACKEND_PORT}:6365" + volumes: + - backend_logs:/app/logs + depends_on: + mysql: + condition: service_healthy + networks: + - gost-network + healthcheck: + test: ["CMD", "sh", "-c", "wget --no-verbose --tries=1 --spider http://localhost:6365/flow/test || exit 1"] + interval: 30s + timeout: 10s + retries: 5 + start_period: 90s + + frontend: + image: bqlpfy/vue-frontend:latest + container_name: vue-frontend + restart: unless-stopped + ports: + - "${FRONTEND_PORT}:80" + - "[::]:${FRONTEND_PORT}:80" + depends_on: + backend: + condition: service_healthy + networks: + - gost-network + + +volumes: + mysql_data: + driver: local + backend_logs: + driver: local + + +networks: + gost-network: + driver: bridge + enable_ipv6: true + ipam: + config: + - subnet: 172.20.0.0/16 + - subnet: fd00:dead:beef::/48 +EOF + + mv docker-compose.yml.ipv6 docker-compose.yml + echo "✅ docker-compose.yml 已更新为支持 IPv6" } # 显示菜单 @@ -386,25 +251,6 @@ get_config_params() { read -p "后端端口(默认 6365): " BACKEND_PORT BACKEND_PORT=${BACKEND_PORT:-6365} - # 询问是否开启IPv6支持 - echo "" - echo "🌐 IPv6 支持配置" - echo "开启IPv6可以让容器支持IPv6网络连接" - echo "ℹ️ 注意事项:" - echo " - 需要系统内核支持IPv6" - echo " - 需要Docker守护进程启用IPv6支持" - echo " - 如果Docker未启用IPv6,请先配置Docker后再安装" - echo "" - read -p "是否开启IPv6支持?(y/N): " ENABLE_IPV6 - if [[ "$ENABLE_IPV6" == "y" || "$ENABLE_IPV6" == "Y" ]]; then - ENABLE_IPV6=true - echo "✅ 已选择开启IPv6支持" - echo "ℹ️ 将根据系统配置自动选择合适的IPv6子网" - else - ENABLE_IPV6=false - echo "ℹ️ 未开启IPv6支持,使用IPv4网络" - fi - DB_NAME=$(generate_random) DB_USER=$(generate_random) DB_PASSWORD=$(generate_random) @@ -423,8 +269,12 @@ install_panel() { curl -L -o gost.sql "$GOST_SQL_URL" echo "✅ 下载完成" - # 配置IPv6网络 - configure_ipv6_network + # 自动检测并配置 IPv6 支持 + if check_ipv6_support; then + echo "🚀 系统支持 IPv6,自动启用 IPv6 配置..." + configure_docker_ipv6 + update_compose_for_ipv6 + fi cat > .env <