Tauri开发桌面端服务,配置指定防火墙端口

注意程序需要管理员权限,参考下面这个文章:

Tauri开发桌面端使程序拥有管理员权限,桌面图标有小盾牌

打开src-tauri目录下src下的main.rs文件,添加下面代码

rust 复制代码
// 新增:防火墙配置相关函数
use std::process::Command;
use std::io::{self, Write};

/// Windows防火墙配置函数
#[cfg(target_os = "windows")]
fn configure_windows_firewall() -> Result<(), Box<dyn std::error::Error>> {
    let app_name = "测试";
    let port = 5800;
    
    println!("开始检查Windows防火墙配置...");
    
    // 检查是否已存在规则
    let tcp_check_cmd = format!("netsh advfirewall firewall show rule name=\"{0} Port {1} TCP\"", app_name, port);
    let tcp_output = Command::new("cmd")
        .args(&["/C", &tcp_check_cmd])
        .output()?;
    
    let udp_check_cmd = format!("netsh advfirewall firewall show rule name=\"{0} Port {1} UDP\"", app_name, port);
    let udp_output = Command::new("cmd")
        .args(&["/C", &udp_check_cmd])
        .output()?;
    
    let tcp_exists = tcp_output.status.success();
    let udp_exists = udp_output.status.success();
    
    // 如果规则已存在,跳过配置
    if tcp_exists && udp_exists {
        println!("✅ Windows防火墙规则已存在,跳过配置");
        return Ok(());
    }
    
    println!("正在配置Windows防火墙规则...");
    
    let mut rules_created = 0;
    
    // 创建TCP入站规则(如果不存在)
    if !tcp_exists {
        let tcp_rule = format!(
            "netsh advfirewall firewall add rule name=\"{0} Port {1} TCP\" dir=in action=allow protocol=TCP localport={1} profile=private,public",
            app_name, port
        );
        
        let output = Command::new("cmd")
            .args(&["/C", &tcp_rule])
            .output()?;
        
        if output.status.success() {
            println!("✅ TCP防火墙规则创建成功");
            rules_created += 1;
        } else {
            let error_msg = String::from_utf8_lossy(&output.stderr);
            println!("⚠️  TCP防火墙规则创建失败: {}", error_msg);
            // 不立即返回错误,继续尝试UDP规则
        }
    }
    
    // 创建UDP入站规则(如果不存在)
    if !udp_exists {
        let udp_rule = format!(
            "netsh advfirewall firewall add rule name=\"{0} Port {1} UDP\" dir=in action=allow protocol=UDP localport={1} profile=private,public",
            app_name, port
        );
        
        let output = Command::new("cmd")
            .args(&["/C", &udp_rule])
            .output()?;
        
        if output.status.success() {
            println!("✅ UDP防火墙规则创建成功");
            rules_created += 1;
        } else {
            let error_msg = String::from_utf8_lossy(&output.stderr);
            println!("⚠️  UDP防火墙规则创建失败: {}", error_msg);
        }
    }
    
    if rules_created > 0 {
        println!("✅ Windows防火墙规则配置完成,创建了 {} 条规则", rules_created);
    } else {
        println!("ℹ️  无需创建新的防火墙规则");
    }
    
    Ok(())
}

/// macOS防火墙配置(通常不需要特殊配置)
#[cfg(target_os = "macos")]
fn configure_macos_firewall() -> Result<(), Box<dyn std::error::Error>> {
    println!("macOS系统:防火墙配置通常由系统自动处理");
    println!("应用首次运行时,系统会提示用户是否允许网络访问");
    Ok(())
}

/// Linux防火墙配置(提供用户指导)
#[cfg(target_os = "linux")]
fn configure_linux_firewall() -> Result<(), Box<dyn std::error::Error>> {
    let port = 5800;
    
    // 检测Linux发行版和防火墙工具
    if Command::new("which").arg("ufw").output().is_ok() {
        // Ubuntu/Debian使用ufw
        println!("检测到ufw防火墙,请手动执行以下命令:");
        println!("sudo ufw allow {}/tcp", port);
        println!("sudo ufw allow {}/udp", port);
    } else if Command::new("which").arg("firewall-cmd").output().is_ok() {
        // CentOS/RHEL使用firewalld
        println!("检测到firewalld防火墙,请手动执行以下命令:");
        println!("sudo firewall-cmd --permanent --add-port={}/tcp", port);
        println!("sudo firewall-cmd --permanent --add-port={}/udp", port);
        println!("sudo firewall-cmd --reload");
    } else if Command::new("which").arg("iptables").output().is_ok() {
        // 使用iptables
        println!("检测到iptables防火墙,请手动执行以下命令:");
        println!("sudo iptables -A INPUT -p tcp --dport {} -j ACCEPT", port);
        println!("sudo iptables -A INPUT -p udp --dport {} -j ACCEPT", port);
    } else {
        println!("Linux系统:防火墙配置因发行版而异");
        println!("请根据您的系统手动配置端口 {} 的防火墙规则", port);
    }
    
    Ok(())
}

/// 跨平台防火墙配置入口函数
fn configure_firewall_cross_platform() -> Result<(), Box<dyn std::error::Error>> {
    println!("开始配置防火墙规则...");
    
    #[cfg(target_os = "windows")]
    {
        configure_windows_firewall()?;
    }
    
    #[cfg(target_os = "macos")]
    {
        configure_macos_firewall()?;
    }
    
    #[cfg(target_os = "linux")]
    {
        configure_linux_firewall()?;
    }
    
    println!("防火墙配置完成");
    Ok(())
}

// 新增:导入regex库用于防火墙状态检查
use regex;
/// 检查防火墙状态
fn check_firewall_status() -> Result<(), Box<dyn std::error::Error>> {
    let port = 5800;
    
    #[cfg(target_os = "windows")]
    {
        let app_name = "测试";
        
        // 检查TCP规则
        let tcp_check_cmd = format!("netsh advfirewall firewall show rule name=\"{0} Port {1} TCP\"", app_name, port);
        let tcp_output = Command::new("cmd")
            .args(&["/C", &tcp_check_cmd])
            .output()?;
        
        // 检查UDP规则
        let udp_check_cmd = format!("netsh advfirewall firewall show rule name=\"{0} Port {1} UDP\"", app_name, port);
        let udp_output = Command::new("cmd")
            .args(&["/C", &udp_check_cmd])
            .output()?;
        
        let tcp_exists = tcp_output.status.success();
        let udp_exists = udp_output.status.success();
        
        // 更宽松的检查逻辑
        if tcp_exists && udp_exists {
            println!("✅ Windows防火墙规则检查:端口 {} 的TCP和UDP规则已配置", port);
            
            // 进一步检查规则状态
            let tcp_output_str = String::from_utf8_lossy(&tcp_output.stdout);
            let udp_output_str = String::from_utf8_lossy(&udp_output.stdout);
            
            // 修复:使用正则表达式处理不确定的空格数量
            let tcp_enabled = {
                let re = regex::Regex::new(r"已启用:\s*是").unwrap();
                re.is_match(&tcp_output_str) || tcp_output_str.contains("Enabled: Yes")
            };
            
            let udp_enabled = {
                let re = regex::Regex::new(r"已启用:\s*是").unwrap();
                re.is_match(&udp_output_str) || udp_output_str.contains("Enabled: Yes")
            };
            
            // 调试信息:输出实际的命令输出
            // println!("🔍 TCP规则检查输出: {}", tcp_output_str);
            // println!("🔍 UDP规则检查输出: {}", udp_output_str);
            
            if tcp_enabled && udp_enabled {
                println!("✅ 端口 {} 的TCP和UDP规则已启用", port);
            } else {
                println!("⚠️  端口 {} 的规则存在但可能未完全启用", port);
                println!("   TCP规则状态: {}", if tcp_enabled { "已启用" } else { "未启用" });
                println!("   UDP规则状态: {}", if udp_enabled { "已启用" } else { "未启用" });
            }
        } else if tcp_exists || udp_exists {
            println!("⚠️  端口 {} 的部分防火墙规则已配置", port);
            println!("   TCP规则: {}", if tcp_exists { "已配置" } else { "未配置" });
            println!("   UDP规则: {}", if udp_exists { "已配置" } else { "未配置" });
        } else {
            println!("❌ Windows防火墙规则检查:端口 {} 未配置防火墙规则", port);
            println!("💡 提示:这不会影响应用功能,但可能需要手动配置防火墙");
        }
    }
    
    #[cfg(not(target_os = "windows"))]
    {
        println!("ℹ️  防火墙状态检查:{} 系统通常不需要特殊配置", {
            #[cfg(target_os = "macos")] { "macOS" }
            #[cfg(target_os = "linux")] { "Linux" }
            #[cfg(not(any(target_os = "macos", target_os = "linux")))] { "当前" }
        });
    }
    
    Ok(())
}

然后在fn main()函数中添加下面代码:

rust 复制代码
fn main() {

    // 新增:自动配置防火墙
    match configure_firewall_cross_platform() {
        Ok(_) => println!("防火墙自动配置成功"),
        Err(e) => eprintln!("防火墙自动配置失败: {}", e),
    }

    // 检查防火墙状态
    if let Err(e) = check_firewall_status() {
        eprintln!("防火墙状态检查失败: {}", e);
    }

    // 其他代码......

}

切记执行:npm run tauri dev/build 时需要打开 "管理员:命令提示符"窗口中执行命令

相关推荐
DongLi012 天前
rustlings 学习笔记 -- exercises/05_vecs
rust
番茄灭世神3 天前
Rust学习笔记第2篇
rust·编程语言
shimly1234563 天前
(done) 速通 rustlings(20) 错误处理1 --- 不涉及Traits
rust
shimly1234563 天前
(done) 速通 rustlings(19) Option
rust
@atweiwei3 天前
rust所有权机制详解
开发语言·数据结构·后端·rust·内存·所有权
shimly1234563 天前
(done) 速通 rustlings(24) 错误处理2 --- 涉及Traits
rust
shimly1234563 天前
(done) 速通 rustlings(23) 特性 Traits
rust
shimly1234563 天前
(done) 速通 rustlings(17) 哈希表
rust
shimly1234563 天前
(done) 速通 rustlings(15) 字符串
rust
shimly1234563 天前
(done) 速通 rustlings(22) 泛型
rust