Files
pit-router/docs/AUTO_DEPLOY.md
yunxiafei 1b41e28499 docs: 添加自动部署方案到 README
功能:
- Gitea Webhook + 更新脚本方案
- 自动拉取代码、构建镜像、重启容器
- 健康检查确认更新成功

作者: 小白 🐶
2026-03-14 22:27:37 +08:00

379 lines
8.0 KiB
Markdown
Raw Blame History

This file contains ambiguous Unicode characters
This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.
# 智队中枢 - 自动部署方案
> Gitea 仓库提交后自动更新 Docker 容器
## 📋 方案对比
| 方案 | 复杂度 | 优点 | 缺点 |
|------|--------|------|------|
| **方案 1: Webhook + 脚本** | ⭐ 简单 | 实现快、依赖少 | 功能单一 |
| **方案 2: Gitea Actions** | ⭐⭐⭐ 中等 | 功能强大、可扩展 | 需要配置 Runner |
| **方案 3: Watchtower** | ⭐⭐ 简单 | 自动化程度高 | 需要镜像仓库 |
**推荐方案**:方案 1Webhook + 脚本)+ 方案 3Watchtower组合
---
## 🚀 方案 1: Gitea Webhook + 更新脚本
### 架构流程
```
开发者推送代码
Gitea 仓库接收推送
触发 Webhook (push 事件)
Webhook 服务接收请求
验证签名 + 执行更新脚本
拉取最新代码 → 构建镜像 → 重启容器
发送通知(可选)
```
### 实现步骤
#### 1. 创建更新脚本
```bash
#!/bin/bash
# /www/wwwroot/pit-router/auto-update.sh
set -e
LOG_FILE="/var/log/pit-router-update.log"
REPO_DIR="/www/wwwroot/pit-router"
log() {
echo "[$(date '+%Y-%m-%d %H:%M:%S')] $1" | tee -a "$LOG_FILE"
}
log "========== 开始自动更新 =========="
cd "$REPO_DIR"
# 1. 拉取最新代码
log "拉取最新代码..."
git fetch origin
git reset --hard origin/main
# 2. 停止旧容器
log "停止旧容器..."
docker-compose down
# 3. 构建新镜像
log "构建新镜像..."
docker-compose build --no-cache
# 4. 启动新容器
log "启动新容器..."
docker-compose up -d
# 5. 等待健康检查
log "等待服务启动..."
sleep 10
# 6. 健康检查
if curl -sf http://localhost:1999/health > /dev/null; then
log "✅ 更新成功!服务运行正常"
else
log "❌ 更新失败!服务未正常启动"
exit 1
fi
log "========== 更新完成 =========="
```
#### 2. 创建 Webhook 服务
```python
# /www/wwwroot/pit-router/webhook-server.py
from flask import Flask, request, jsonify
import hmac
import hashlib
import subprocess
import os
app = Flask(__name__)
# 配置
WEBHOOK_SECRET = os.environ.get('WEBHOOK_SECRET', 'your-webhook-secret')
UPDATE_SCRIPT = '/www/wwwroot/pit-router/auto-update.sh'
def verify_signature(payload, signature):
"""验证 Webhook 签名"""
expected = 'sha256=' + hmac.new(
WEBHOOK_SECRET.encode(),
payload,
hashlib.sha256
).hexdigest()
return hmac.compare_digest(expected, signature)
@app.route('/webhook/pit-router', methods=['POST'])
def handle_webhook():
"""处理 Gitea Webhook"""
# 验证签名
signature = request.headers.get('X-Gitea-Signature', '')
if not verify_signature(request.data, signature):
return jsonify({'error': 'Invalid signature'}), 401
# 解析事件
event = request.headers.get('X-Gitea-Event', '')
if event != 'push':
return jsonify({'message': 'Event ignored'}), 200
data = request.json
ref = data.get('ref', '')
# 只处理 main 分支
if ref != 'refs/heads/main':
return jsonify({'message': 'Branch ignored'}), 200
# 执行更新脚本
try:
result = subprocess.run(
[UPDATE_SCRIPT],
capture_output=True,
text=True,
timeout=300
)
if result.returncode == 0:
return jsonify({
'status': 'success',
'message': 'Update completed',
'output': result.stdout
})
else:
return jsonify({
'status': 'error',
'message': result.stderr
}), 500
except subprocess.TimeoutExpired:
return jsonify({'error': 'Update timeout'}), 500
except Exception as e:
return jsonify({'error': str(e)}), 500
if __name__ == '__main__':
app.run(host='0.0.0.0', port=5001)
```
#### 3. 创建 systemd 服务
```ini
# /etc/systemd/system/pit-router-webhook.service
[Unit]
Description=PIT Router Webhook Server
After=network.target
[Service]
Type=simple
User=root
WorkingDirectory=/www/wwwroot/pit-router
Environment=WEBHOOK_SECRET=your-webhook-secret
ExecStart=/usr/bin/python3 /www/wwwroot/pit-router/webhook-server.py
Restart=always
RestartSec=5
[Install]
WantedBy=multi-user.target
```
#### 4. 配置 Gitea Webhook
```bash
TOKEN="509149b911143135084d20c44fc97a462a16945a"
# 创建 Webhook
curl -X POST "http://localhost:3000/api/v1/repos/yunxiafei/pit-router/hooks" \
-H "Authorization: token $TOKEN" \
-H "Content-Type: application/json" \
-d '{
"type": "gitea",
"config": {
"url": "http://localhost:5001/webhook/pit-router",
"content_type": "json",
"secret": "your-webhook-secret"
},
"events": ["push"],
"active": true
}'
```
---
## 🔄 方案 2: Gitea Actions推荐用于复杂项目
### 架构流程
```
开发者推送代码
Gitea Actions 触发
Runner 执行工作流
构建 → 测试 → 推送镜像 → 部署
通知结果
```
### 工作流配置
```yaml
# .gitea/workflows/deploy.yml
name: Build and Deploy
on:
push:
branches: [main]
jobs:
build-and-deploy:
runs-on: ubuntu-latest
steps:
- name: Checkout
uses: actions/checkout@v4
- name: Set up Docker
uses: docker/setup-buildx-action@v3
- name: Build Image
run: |
docker build -t pit-router:latest .
- name: Run Tests
run: |
docker run --rm pit-router:latest python -m pytest tests/
- name: Deploy
run: |
docker-compose down
docker-compose up -d
- name: Health Check
run: |
sleep 10
curl -sf http://localhost:1999/health || exit 1
```
### 配置 Gitea Actions Runner
```bash
# 创建 Runner Token
TOKEN="509149b911143135084d20c44fc97a462a16945a"
curl -X POST "http://localhost:3000/api/v1/admin/runners/registration-token" \
-H "Authorization: token $TOKEN"
# 安装 Runner
docker run -d \
--name gitea-runner \
-v /var/run/docker.sock:/var/run/docker.sock \
-v /www/wwwroot/pit-router:/workspace \
-e GITEA_INSTANCE_URL=http://localhost:3000 \
-e GITEA_RUNNER_REGISTRATION_TOKEN=<token> \
gitea/act_runner:latest
```
---
## 📦 方案 3: Watchtower自动监控镜像更新
### 适用场景
适用于已经推送到镜像仓库的场景。
### 配置
```yaml
# docker-compose.yaml 添加 watchtower
watchtower:
image: containrrr/watchtower
volumes:
- /var/run/docker.sock:/var/run/docker.sock
environment:
- WATCHTOWER_CLEANUP=true
- WATCHTOWER_POLL_INTERVAL=300 # 每 5 分钟检查一次
- WATCHTOWER_NOTIFICATIONS=email
- WATCHTOWER_NOTIFICATION_EMAIL_FROM=alert@example.com
- WATCHTOWER_NOTIFICATION_EMAIL_TO=admin@example.com
- WATCHTOWER_NOTIFICATION_EMAIL_SERVER=smtp.example.com
restart: unless-stopped
```
---
## 🎯 推荐方案
### 简单场景(当前推荐)
**方案 1: Webhook + 脚本**
| 项目 | 说明 |
|------|------|
| 复杂度 | 低 |
| 依赖 | Flask + 简单脚本 |
| 部署时间 | 30 分钟 |
| 维护成本 | 低 |
### 复杂场景(未来扩展)
**方案 2: Gitea Actions**
| 项目 | 说明 |
|------|------|
| 复杂度 | 中 |
| 依赖 | Gitea Runner |
| 功能 | 测试、构建、部署一体化 |
| 维护成本 | 中 |
---
## 📝 实施清单
### 方案 1 实施步骤
- [ ] 创建更新脚本 `auto-update.sh`
- [ ] 创建 Webhook 服务 `webhook-server.py`
- [ ] 创建 systemd 服务
- [ ] 配置 Gitea Webhook
- [ ] 测试自动更新流程
### 预计时间
- 首次部署30 分钟
- 后续维护:几乎无
---
## ⚠️ 注意事项
1. **安全性**
- Webhook 必须验证签名
- 限制 Webhook 访问来源 IP
- 敏感信息使用环境变量
2. **可靠性**
- 更新失败自动回滚
- 健康检查确认成功
- 日志记录完整
3. **生产环境**
- 考虑蓝绿部署
- 考虑金丝雀发布
- 监控告警
---
*文档版本: v1.0 | 创建时间: 2026-03-14 | 作者: 小白 🐶*