节点在线、应用在线、配置在线使用令牌查询
|
# 星尘发布自动开放防火墙端口
## 功能概述
从 v3.7 开始,星尘发布支持自动检测应用监听端口并开放防火墙规则,免去手动配置防火墙的繁琐步骤。
该功能在应用部署启动后自动执行,支持 Windows 和 Linux 多种防火墙系统。
## 功能特点
1. **自动检测**:自动识别系统防火墙类型和可用性
2. **智能提取**:从应用配置文件自动提取监听端口
3. **多平台支持**:支持 Windows 和主流 Linux 防火墙
4. **无侵入设计**:配置失败不影响应用正常部署
5. **详细日志**:完整记录检测和配置过程
## 支持的防火墙类型
### Windows 平台
- **Windows Firewall**(Windows 防火墙)
- 使用 `netsh advfirewall` 命令
- 自动创建入站规则
- 规则命名格式:`{应用名}-{端口}`
### Linux 平台
- **firewalld**(CentOS/RHEL/Fedora)
- 主流企业 Linux 发行版默认防火墙
- 永久开放端口,重启后保持
- 自动重载配置
- **ufw**(Ubuntu/Debian)
- Ubuntu 和 Debian 系列默认防火墙
- 简单易用的防火墙管理工具
- 自动处理重复规则
- **iptables**(通用)
- 传统 Linux 防火墙
- 兼容大多数 Linux 发行版
- 自动尝试保存规则
## 端口检测机制
系统会自动从以下配置文件中提取监听端口:
### 1. Nginx 配置文件
从 `*.conf` 或 `*.nginx` 文件中提取 `listen` 指令:
```nginx
server {
listen 80;
listen 443 ssl;
# 自动提取:80, 443
}
```
### 2. ASP.NET Core 配置
从 `appsettings*.json` 文件中提取端口:
**方式一:urls 配置**
```json
{
"urls": "http://localhost:5000;https://localhost:5001"
// 自动提取:5000, 5001
}
```
**方式二:Kestrel 配置**
```json
{
"Kestrel": {
"Endpoints": {
"Http": {
"Url": "http://localhost:5000"
},
"Https": {
"Url": "https://localhost:5001"
}
}
}
// 自动提取:5000, 5001
}
```
### 3. IIS 配置
从 `web.config` 文件中提取绑定端口:
```xml
<configuration>
<system.applicationHost>
<sites>
<site name="Default Web Site" id="1">
<bindings>
<binding protocol="http" bindingInformation="*:8080:" />
<binding protocol="https" bindingInformation="*:8443:" />
<!-- 自动提取:8080, 8443 -->
</bindings>
</site>
</sites>
</system.applicationHost>
</configuration>
```
## 部署日志示例
### Windows 平台
```
检测到防火墙类型:WindowsFirewall
检测到 2 个端口需要开放: 80, 443
已开放端口 80 (规则: MyWebApp-80)
已开放端口 443 (规则: MyWebApp-443)
```
### Linux (firewalld)
```
检测到防火墙类型:Firewalld
检测到 2 个端口需要开放: 5000, 5001
已开放端口 5000 (firewalld)
已开放端口 5001 (firewalld)
```
### Linux (ufw)
```
检测到防火墙类型:Ufw
检测到 1 个端口需要开放: 8080
已开放端口 8080 (ufw)
```
### 无防火墙或无权限
```
未检测到可用的防火墙或无权限访问,跳过端口开放
```
## 权限要求
### Windows 平台
- 需要**管理员权限**才能配置 Windows 防火墙
- StarAgent 服务应以管理员身份运行
- 如果权限不足,会跳过防火墙配置但不影响应用部署
### Linux 平台
- 需要 **root 权限**或具有 sudo 权限的用户
- 建议 StarAgent 以 root 用户运行
- 或配置 sudoers 允许 StarAgent 用户执行防火墙命令
#### 配置 sudoers(可选)
如果不想以 root 运行 StarAgent,可以配置 sudoers:
```bash
# 编辑 sudoers 文件
sudo visudo
# 添加以下行(根据实际防火墙类型选择)
staragent ALL=(ALL) NOPASSWD: /usr/bin/firewall-cmd
staragent ALL=(ALL) NOPASSWD: /usr/sbin/ufw
staragent ALL=(ALL) NOPASSWD: /usr/sbin/iptables
```
## 技术实现
### 防火墙检测流程
```
1. Windows 系统
└─ 执行 netsh advfirewall show currentprofile
└─ 成功 → WindowsFirewall
└─ 失败 → 无可用防火墙
2. Linux 系统
├─ 执行 firewall-cmd --state
│ └─ running → Firewalld
├─ 执行 ufw status
│ └─ active → Ufw
└─ 执行 iptables -L -n
└─ 成功 → Iptables
└─ 失败 → 无可用防火墙
```
### Windows 命令示例
```powershell
# 检测防火墙
netsh advfirewall show currentprofile
# 检查规则是否存在
netsh advfirewall firewall show rule name="MyApp-80"
# 添加入站规则
netsh advfirewall firewall add rule name="MyApp-80" dir=in action=allow protocol=TCP localport=80
```
### Linux firewalld 命令示例
```bash
# 检测防火墙状态
firewall-cmd --state
# 查询端口是否已开放
firewall-cmd --query-port=80/tcp
# 永久开放端口
firewall-cmd --permanent --add-port=80/tcp
# 重载配置
firewall-cmd --reload
```
### Linux ufw 命令示例
```bash
# 检测防火墙状态
ufw status
# 开放端口(自动处理重复)
ufw allow 80/tcp
```
### Linux iptables 命令示例
```bash
# 查看规则
iptables -L -n
# 检查规则是否存在
iptables -C INPUT -p tcp --dport 80 -j ACCEPT
# 添加规则
iptables -A INPUT -p tcp --dport 80 -j ACCEPT
# 保存规则(CentOS/RHEL)
service iptables save
# 保存规则(Ubuntu/Debian)
iptables-save > /etc/iptables/rules.v4
```
## 故障排查
### 防火墙未检测到
**症状**:日志显示"未检测到可用的防火墙"
**可能原因**:
1. 系统未安装防火墙服务
2. 防火墙服务未运行
3. StarAgent 无执行权限
**解决方法**:
```bash
# CentOS/RHEL - 安装并启动 firewalld
sudo yum install firewalld
sudo systemctl start firewalld
sudo systemctl enable firewalld
# Ubuntu/Debian - 启用 ufw
sudo ufw enable
```
### 端口开放失败
**症状**:日志显示"端口 XX 开放失败"
**可能原因**:
1. 权限不足
2. 防火墙服务异常
3. 端口号无效
**解决方法**:
1. 确认 StarAgent 有足够权限
2. 手动执行防火墙命令测试
3. 检查日志中的错误详情
### 端口未自动提取
**症状**:日志显示"未检测到需要开放的端口"
**可能原因**:
1. 配置文件格式不标准
2. 配置文件不在工作目录
3. 端口配置使用了变量
**解决方法**:
1. 检查配置文件是否存在于部署目录
2. 确认配置文件格式符合标准
3. 手动开放端口:
```bash
# Windows
netsh advfirewall firewall add rule name="MyApp-80" dir=in action=allow protocol=TCP localport=80
# Linux (firewalld)
sudo firewall-cmd --permanent --add-port=80/tcp
sudo firewall-cmd --reload
```
## 注意事项
1. **自动化程度**:仅支持从配置文件提取端口,动态端口(如随机端口)需要手动配置
2. **安全考虑**:
- 仅开放 TCP 入站规则
- 不修改现有防火墙规则
- 支持检查规则是否已存在,避免重复添加
3. **兼容性**:
- 需要系统已安装相应防火墙服务
- Windows 需要 Windows Firewall 服务运行
- Linux 至少需要一种防火墙(firewalld/ufw/iptables)
4. **性能影响**:
- 防火墙配置在应用启动后异步执行
- 配置失败不会阻塞或中断应用部署
- 每个端口配置耗时通常在 100ms 以内
## 后续规划
- [ ] 支持 UDP 协议端口开放
- [ ] 支持从启动参数提取端口
- [ ] 支持端口范围配置
- [ ] 支持自定义规则优先级
- [ ] 支持云平台安全组自动配置(阿里云、腾讯云等)
## 相关链接
- [星尘发布架构](/NewLife/Stardust/Blob/master/Doc/星尘发布架构.md)
- [StarAgent 远程部署](/NewLife/Stardust/Blob/master/Doc/StarAgent远程部署.md)
- [远程命令执行安全方案](/NewLife/Stardust/Blob/master/Doc/远程命令执行安全方案.md)
|