GitLab 如何使用与配置:从代码托管到自动化部署的实战指南
很多人第一次接触 GitLab,会把它理解成"代码仓库平台"。这当然没错,但如果你只把 GitLab 当成一个放代码的地方,那它真正有价值的部分,其实还没开始用。
GitLab 的强项,不只是托管代码,而是把代码、分支、权限、评审、CI/CD、Runner 和部署流程整合到了一套系统里。项目一旦进入多人协作、持续交付、自动化部署阶段,GitLab 的价值就会非常明显:流程更清晰,权限更可控,交付更稳定。
这篇文章会从 GitLab 的基本使用开始,一路讲到 Runner、CI/CD 和自动部署,适合用来做团队培训、项目文档或者内部知识库。
一、GitLab 是什么
GitLab 可以理解为一套完整的软件协作平台,常见能力包括:
- Git 仓库管理
- 成员与权限控制
- 分支管理
- Merge Request(合并请求)
- Issue 与看板管理
- CI/CD 自动化流程
- Runner 执行器管理
- 自动部署
简单来说:
- Git 负责版本控制
- GitLab 负责把版本控制和团队协作真正落地
二、GitLab 的核心概念
在开始使用之前,先理解几个最常见的概念。
1. Project
Project 就是项目仓库,是代码和流程的基本单位。
2. Repository
仓库本体,保存代码、提交历史、分支等。
3. Branch
分支,用于隔离不同阶段的开发工作。
常见分支设计:
master:生产分支develop:开发/测试分支feature/*:功能开发分支hotfix/*:紧急修复分支
4. Merge Request
用于代码合并和评审。团队开发中,建议所有代码都通过 Merge Request 合并,而不是直接推送到生产分支。
5. Runner
Runner 是 GitLab CI/CD 的执行器。没有 Runner,流水线只能创建,不能真正执行。
6. .gitlab-ci.yml
GitLab CI/CD 的核心配置文件,必须放在仓库根目录。
三、GitLab 的基本使用流程
一个标准的 GitLab 使用流程,一般是这样的:
1. 创建项目
在 GitLab 上新建一个 Project。创建后,你会得到一个仓库地址。
可以使用:
- HTTPS
- SSH
进行克隆。
2. 克隆仓库
bash
git clone <repository-url>
如果是长期使用,建议配置 SSH Key,这样会更方便。
3. 创建功能分支
不要直接在 master 上开发。推荐从主分支切出功能分支:
bash
git checkout -b feature/login-page
4. 提交代码
bash
git add .
git commit -m "feat: add login page"
git push origin feature/login-page
5. 发起 Merge Request
提交后,在 GitLab 页面发起 Merge Request,合并到目标分支。这个阶段通常会结合:
- 代码评审
- 自动测试
- 权限审核
- Pipeline 状态检查
这也是 GitLab 区别于"普通仓库"的关键地方。
四、GitLab 使用前必须配置的内容
很多团队 GitLab 用不好,不是因为不会提交代码,而是基础配置没做好。
1. 配置 SSH Key
如果你用 SSH 克隆仓库,需要先在本地生成密钥:
bash
ssh-keygen -t ed25519 -C "your_email@example.com"
然后把公钥内容复制到 GitLab 的:
User Settings -> SSH Keys
配置完成后,就可以用 SSH 地址拉代码了。
2. 配置分支保护(Protected Branch)
生产分支一定要保护,常见保护分支包括:
masterdevelop
保护后可以限制:
- 谁能 push
- 谁能 merge
- 是否必须通过 Merge Request
如果不做这一步,生产分支很容易被误操作直接覆盖。
3. 配置 CI/CD Variables
一些敏感信息和环境参数,不应该直接写进代码里,比如:
- 部署目录
- 密钥
- Token
- 服务地址
- 环境变量
应该统一放到:
Settings -> CI/CD -> Variables
这样更安全,也更方便环境切换。
4. 配置 Runner
GitLab 的 CI/CD 需要 Runner 来执行。Runner 可以部署在:
- Linux 服务器
- Windows 服务器
- Docker 容器
- Kubernetes 集群
如果项目本身依赖 Windows 环境,比如需要访问本地目录、Windows 服务或 PowerShell 脚本,那么使用 Windows + shell executor 通常是最直接的方案。
五、GitLab Runner 如何理解
Runner 可以理解为"执行流水线命令的机器"。
比如你在 .gitlab-ci.yml 里写了:
yaml
script:
- npm ci
- npm run build
真正执行这些命令的,不是 GitLab Web 页面,而是 Runner。
常见执行器类型
shelldockerdocker-windowskubernetes
Windows 场景下常见配置
toml
concurrent = 1
[[runners]]
name = "frontend_runner"
executor = "shell"
shell = "pwsh"
关键参数说明
concurrent
表示整个 Runner 进程同时最多能执行多少个 Job。
例如:
toml
concurrent = 1
表示任务是串行执行的。
executor = "shell"
表示直接调用操作系统 shell 执行命令。
shell = "pwsh"
表示用 PowerShell 7 执行脚本。
六、GitLab CI/CD 的基本结构
GitLab CI/CD 通过 .gitlab-ci.yml 定义流水线。
一个最基础的结构通常包含:
stagesjobscriptrulestagsvariables
例如:
yaml
stages:
- build
- deploy
表示先构建,再部署。
七、一个前端自动部署的例子
假设有一个前端项目,需求如下:
- 推送到
master分支时自动触发 - Runner 在 Windows 服务器上执行
- 自动运行前端打包
- 将
dist部署到:
text
C:\BackTest\frontend\dist
那么 .gitlab-ci.yml 可以这样写:
yaml
stages:
- deploy
variables:
DEPLOY_DIR: "C:\\BackTest\\frontend\\dist"
DEPLOY_BRANCH: "master"
deploy_frontend_prod:
stage: deploy
tags:
- frontend-deploy
rules:
- if: '$CI_COMMIT_BRANCH == $DEPLOY_BRANCH'
script:
- .\scripts\deploy-frontend.ps1
environment:
name: production
对应的 PowerShell 部署脚本:
powershell
$ErrorActionPreference = "Stop"
$projectRoot = if ($env:CI_PROJECT_DIR) { $env:CI_PROJECT_DIR } else { (Get-Location).Path }
$frontendDir = $projectRoot
$deployDir = if ($env:DEPLOY_DIR) { $env:DEPLOY_DIR } else { "C:\BackTest\frontend\dist" }
function Invoke-RobocopySafe {
param(
[Parameter(Mandatory = $true)][string]$Source,
[Parameter(Mandatory = $true)][string]$Destination
)
robocopy $Source $Destination /MIR /R:2 /W:2
if ($LASTEXITCODE -gt 7) {
throw "robocopy failed with exit code $LASTEXITCODE"
}
}
Set-Location $frontendDir
npm ci
npm run build
$distDir = Join-Path $frontendDir "dist"
if (!(Test-Path $deployDir)) {
New-Item -ItemType Directory -Force -Path $deployDir | Out-Null
}
Invoke-RobocopySafe -Source $distDir -Destination $deployDir
这种方式的好处很明显:
- CI 文件负责调度
- 脚本负责执行
- 部署逻辑更清晰
- 更适合后期维护
八、GitLab 中最常见的坑
1. 分支名写错
仓库实际使用的是 master,但 CI 配置里写成了 main。结果是代码提交了,Pipeline 却不触发。
2. .gitlab-ci.yml 放错位置
GitLab 只会识别仓库根目录 下的 .gitlab-ci.yml。如果你把它放到上层目录或者子目录,GitLab 不会读取。
3. Runner Tag 不匹配
Job 里写的是:
yaml
tags:
- frontend-deploy
但 Runner 根本没有这个 tag,最终任务就会一直处于 pending 状态。
需要记住:
- Runner 名字不是 tag
- GitLab 匹配 job 时靠的是 tag
4. Runner 没绑定项目
Runner 在线,不代表当前项目能用。还必须确认:
- 这个 Runner 已绑定当前项目
- 处于 active 状态
- 没有被 pause
5. 部署目录权限不足
即使脚本完全正确,只要 Runner 执行账户没有目录写权限,部署就会失败。
6. Token 泄露
Runner Token、Deploy Token、密钥等都属于敏感信息。如果泄露,建议尽快 rotate,不要长期继续使用。
九、GitLab 的最佳实践建议
如果你不想把 GitLab 只当成"高级网盘",建议至少做到下面几点:
1. 所有生产代码都走 Merge Request
不要直接往生产分支 push。
2. 保护生产分支
限制 push 和 merge 权限。
3. 使用 CI/CD Variables 管理环境配置
敏感信息不要硬编码。
4. 使用 Runner Tag 做环境隔离
例如:
frontend-deploybackend-deployprod-runnertest-runner
5. 把部署逻辑写进脚本
不要把复杂 PowerShell 或 Bash 全堆进 .gitlab-ci.yml。
6. 预留回滚能力
自动部署不是终点,能快速回滚才算成熟。
十、结语
GitLab 真正有价值的地方,不是"它能不能存代码",而是它能不能帮团队把交付流程标准化。
当你开始真正用上:
- 分支保护
- Merge Request
- Runner
- CI/CD
- 自动部署
GitLab 才会从一个代码托管工具,变成一个完整的软件交付平台。
如果是个人项目,它能帮你减少重复劳动。如果是团队项目,它能帮你把流程从"靠人记住"变成"靠系统约束"。
这两者之间的差距,往往决定了项目后期是否稳定、是否能持续交付。
附录:一个简单的 GitLab 使用清单
开发侧
- 配置 SSH Key
- 克隆仓库
- 创建功能分支
- 提交代码
- 发起 Merge Request
管理侧
- 配置成员权限
- 保护生产分支
- 配置 CI/CD Variables
- 配置 Runner
- 配置部署流程
自动化侧
- 创建
.gitlab-ci.yml - 配置部署脚本
- 绑定 Runner Tag
- 验证 Pipeline
- 增加回滚方案