GitHub Actions自动化部署实战:把重复劳动交给机器人
每次改了代码还要手动SSH到服务器上git pull、重启服务、清缓存,这些重复操作是在浪费生命。GitHub Actions让你免费拥有CI/CD流水线,push代码后自动完成部署全流程。
1. 你的第一个GitHub Actions配置
在项目根目录创建.github/workflows/deploy.yml:
name: Deploy to Server
on:
push:
branches: [main]
jobs:
deploy:
runs-on: ubuntu-latest
steps:
- name: Deploy via SSH
uses: appleboy/ssh-action@v1
with:
host: ${{ secrets.SERVER_HOST }}
username: ${{ secrets.SERVER_USER }}
key: ${{ secrets.SSH_PRIVATE_KEY }}
script: |
cd /var/www/mysite
git pull origin main
composer install --no-dev
systemctl reload php8.2-fpm把服务器IP、用户名、SSH私钥存到仓库的Settings > Secrets中。推送代码到main分支后,Actions会自动SSH到服务器执行部署脚本。
2. 零停机部署策略
直接git pull然后reload可以工作,但会导致1-2秒的服务中断。对于生产环境,推荐零停机部署。
Symlink切换法:保持两个目录,如/var/www/mysite和/var/www/mysite-new。部署到new目录,然后ln -sfn mysite-new mysite切换符号链接,Nginx配置指向符号链接路径。配合opcache_reset()或fpm reload刷新PHP代码缓存。
Docker滚动更新:用Docker Compose部署时,docker compose up -d --no-deps --build web只重建web容器,其他容器保持运行。健康检查通过后再停旧容器。
3. 多环境管理
一个完善的CI/CD流水线应该覆盖多个环境:
name: CI/CD Pipeline
on:
push:
branches: [main, staging]
jobs:
test:
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v4
- run: composer install
- run: php artisan test
deploy-staging:
needs: test
if: github.ref == 'refs/heads/staging'
runs-on: ubuntu-latest
# ... deploy to staging
deploy-production:
needs: test
if: github.ref == 'refs/heads/main'
runs-on: ubuntu-latest
environment: production
# ... deploy to productionpush到staging分支自动部署到测试环境,合入main后手动审批再部署到生产环境。environment: production可以设置审批人规则。
4. 部署后的健康检查
部署完成不等于系统正常。加入健康检查步骤:
- name: Health Check
run: |
for i in {1..10}; do
STATUS=$(curl -s -o /dev/null -w "%{http_code}" https://mysite.com/health)
if [ "$STATUS" = "200" ]; then
echo "✅ Deployment verified"
exit 0
fi
echo "Waiting for app to be ready... ($i/10)"
sleep 5
done
echo "❌ Health check failed"
exit 1在应用中实现/health端点检查数据库连接、缓存可用性等关键依赖。不要只是返回200。成功部署的标准不是步骤不报错,而是健康检查通过。
5. 通知与回滚
部署完成后通过Webhook通知到企业微信或Telegram。失败时自动回滚:
# 在部署脚本中加入
CURRENT_SHA=$(git rev-parse HEAD)
# ... 部署操作 ...
if [ $? -ne 0 ]; then
git checkout $PREVIOUS_SHA # 回滚到上一个版本
systemctl reload php-fpm
curl -X POST $ALERT_WEBHOOK -d '{"text":"Deploy failed, rolled back"}'
fi或者在GitHub Actions中保存上一个成功的artifact,失败时重新部署该artifact。
把部署流程自动化后你会发现自己更敢于频繁发布。小而快的迭代比大而慢的发布更安全——因为每次变更范围小,出问题时更容易定位。