Gerrit 常用 CLI 与 SSH 命令详解(核心篇)

Gerrit 3.14.4 SSH 命令面与 REST API 实战:gerrit version/ls-projects/create-project/query/review/set-reviewers/create-account/show-caches 全家桶实测回显,REST 评审闭环与 capabilities 权限自检,CI 门禁轮询脚本示例与 2.x→3.x 命令差异排障。

GerritGerrit版本控制2026/10/27

Gerrit 常用 CLI 与 SSH 命令详解(核心篇)

目标:系统梳理 Gerrit 的两大自动化接口——SSH 命令行(ssh -p 29418 <admin>@<gerrit> gerrit <command> 全家桶)与 REST API(curl 实测),覆盖项目、账户、群组、评审、查询、运维维护六类命令,并给出评审流水线自动化示例与排障实录。全部命令在 Gerrit 3.14.4 站点实测(2026-10-27),回显逐行照抄。

一、环境信息

  • Gerrit 版本:3.14.4(部署与站点结构见《Gerrit 3.14 Docker Compose 部署实战》)
  • 接入地址:SSH 命令端口 8148(Gerrit 内部标准端口 29418,示例宿主映射为 8148,下文命令统一写 8148);REST/Web 入口 http://localhost:8141
  • 管理账号:admin(HTTP 凭据 q1w2e3r4,SSH 公钥已注册,接入步骤见部署篇第十二节)
  • 实测项目:demo-project(含 Change 1(已合入)、Change 2)
  • 命令回显均为主机实测输出,REST 响应首行 )]}' 为 Gerrit 防跨站 JSON 劫持魔法前缀(解析 JSON 时剥离该行)

二、SSH 命令行接入

Gerrit 的 SSH 通道是双用途:Git 推拉协议 + 管理命令面。管理命令的通用形态:

ssh -i ~/.ssh/gerrit_demo -p 8148 admin@localhost gerrit <command> [options]

基础验证(三条实测):

ssh -i ~/.ssh/gerrit_demo -p 8148 admin@localhost gerrit version
ssh -i ~/.ssh/gerrit_demo -p 8148 admin@localhost gerrit ls-projects

实测回显:

gerrit version 3.14.4

All-Projects
All-Users
demo-project

💡 技术拓展:Gerrit 的 SSH 命令面与 Git 协议共用 29418 一个端口,客户端首次连接同样走 SSH host-key 握手(主机密钥在站点 etc/ssh_host_*),自动化脚本建议固定 -o StrictHostKeyChecking=yes 并预分发 known_hosts。管理命令权限由全局能力(capabilities)控制——admin 账号的 administrateServer: true 等能力清单可通过 REST 查(见 4.5)。

三、gerrit 命令族详解

3.1 项目管理:ls-projects / create-project

gerrit create-project demo-project    # 建项目(实测静默成功)
gerrit ls-projects                    # 列全部项目

ls-projects 常用过滤(官方命令文档):

gerrit ls-projects --description      # 含描述
gerrit ls-projects -p demo            # 限定树分支(前缀过滤)
gerrit ls-projects --all              # 含隐藏项目

3.2 变更查询:query(评审流水线的核心读命令)

ssh -i ~/.ssh/gerrit_demo -p 8148 admin@localhost "gerrit query 'project:demo-project status:open'"

实测回显(输出节选,实测首尾):

change 2 (Open)
  project: demo-project
  branch: master
  Change-Id: I2222222222222222222222222222222222222222
  subject: Add second line
  owner: admin
  email: admin@demo.com
  created: 2026-10-27 13:24:03.000000000
  updated: 2026-10-27 13:24:53.000000000
  submitted: --
  approvals:
  submit records:

1 change

查询语法即 Web UI 搜索框语法(status:open、is:merged、owner:、label:Code-Review=+2、project: 等可任意组合),管道接 -- 分隔符后可附加格式化字段:

gerrit query 'status:open' --format=JSON -- current_patch_set

--format=JSON 输出 JSONL(每行一个 Change 对象),是 CI 轮询拉取待验证 Change 的标准姿势(自动化示例见第五节)。

3.3 评审操作:review(打分/评论/合入)

3.x 的评审命令是 gerrit review,参数格式为 CHANGE,PATCHSET(实测:裸写 change 号报 is not a valid patch set,排障见第七节 7.2):

# 打 Code-Review +2 并留言
gerrit review --code-review +2 -m "LGTM via ssh" 2,1

# 合入
gerrit review --submit 2,1

实测:两条命令均静默成功,效果经 REST 复核——/changes/2/detail 显示 "labels":{"Code-Review":{"approved":{"name":"Gerrit Admin",...}}},/changes/2 显示 "status":"MERGED"。

常用变体:

gerrit review --abandon 3,1          # 废弃 Change
gerrit review --restore 3,1          # 恢复废弃
gerrit review --verified +1 4,1      # 打 Verified 分(装了对应标签的项目)

3.4 评审人管理:set-reviewers

gerrit set-reviewers -a admin 2 --project demo-project    # 添加评审人(实测静默成功)
gerrit set-reviewers -r <group> 3 --project demo-project  # 按组添加
gerrit set-reviewers -d <user> 3 --project demo-project   # -d 移除

3.5 账户与群组管理:create-account / set-account / ls-groups

# 建服务账户并归入 Service Users 组(实测静默成功)
gerrit create-account reviewbot --group "Service Users" --full-name "Review Bot"

# 改账户属性(实测静默成功)
gerrit set-account admin --full-name "Gerrit Admin"

# 列群组
gerrit ls-groups

实测回显:

Administrators
Anonymous Users
Change Owner
Non-Interactive Users
Registered Users
Service Users

SSH 公钥的增删走 REST(/accounts/<user>/sshkeys,见 4.3),SSH 命令面不直接管理密钥。

3.6 运维维护:show-caches / flush-caches / 判定命令集

ssh -i ~/.ssh/gerrit_demo -p 8148 admin@localhost 'gerrit show-caches --width 80'

实测回显(输出节选,实测首尾):

Gerrit Code Review        3.14.4                    now    13:25:08   UTC
                                                 uptime     3 min 16 sec

  Name                          |Entries              |  AvgGet |Hit Ratio|
                                |   Mem   Disk   Space|         |Mem  Disk|
--------------------------------+---------------------+---------+---------+
  adv_bases                     |                     |         |         |
  change_notes                  |     6               |   5.0ms | 91%     |
  changeid_project              |     2               |         | 87%     |
  default_preferences           |                     |         |         |
  external_ids_map              |     2               |         | 97%     |
  groups                        |                     |   4.7ms |  0%     |

配套命令:

gerrit flush-caches --cache groups   # 定向清缓存(改群组后立即生效的补救)
gerrit flush-caches --all            # 全清(谨慎,热缓存全冷)

命令集版本差异(重要):2.x 时代的 gerrit approve、gerrit set-review、gerrit ls-users 在 3.14 实测均为 not found(排障实录 7.1),3.x 的替代命令分别是 gerrit review、gerrit review、REST /accounts/ 查询。

四、REST API 实测(curl 全流程)

REST 是评审流水线集成的主通道(Web UI 与 CI 都走它)。认证:读/写均可用 HTTP Basic(账户 http password),本节统一 -u admin:q1w2e3r4。

4.1 服务与项目

curl -s -u admin:q1w2e3r4 http://localhost:8141/config/server/version
curl -s -u admin:q1w2e3r4 'http://localhost:8141/a/projects/?d'

实测回显(projects 输出节选):

)]}'
"3.14.4"

)]}'
{"All-Projects":{"id":"All-Projects","description":"Access inherited by all other projects.","state":"ACTIVE","web_links":[{"name":"browse","url":"/plugins/gitiles/All-Projects"}]},"All-Users":{"id":"All-Users","description":"Individual user settings and preferences.","state":"ACTIVE","web_links":[{"name":"browse","url":"/plugins/gitiles/All-Users"}]},"demo-project":{"id":"demo-project","state":"ACTIVE","web_links":[{"name":"browse","url":"/plugins/gitiles/demo-project"}]}}

4.2 账户与凭据

# 当前身份
curl -s -u admin:q1w2e3r4 http://localhost:8141/a/accounts/self
# 账户详情
curl -s -u admin:q1w2e3r4 http://localhost:8141/a/accounts/admin/detail
# 设置 HTTP 凭据
curl -s -u admin:q1w2e3r4 -X PUT -H 'Content-Type: application/json' \
  -d '{"http_password":"q1w2e3r4"}' \
  'http://localhost:8141/a/accounts/self/password.http'

实测回显(detail 节选):

)]}'
{"registered_on":"2026-10-27 13:16:06.000000000","_account_id":1000000,"name":"admin","secondary_emails":[],"username":"admin","avatars":[...]}

4.3 SSH 公钥注册(REST 承载)

curl -s -u admin:q1w2e3r4 -X POST -H 'Content-Type: text/plain' \
  --data-binary @~/.ssh/gerrit_demo.pub \
  'http://localhost:8141/a/accounts/self/sshkeys'

实测回显(201 Created):

)]}'
{"seq":1,"ssh_public_key":"ssh-ed25519 AAAAC3NzaC1lZDI1NTE5AAAAIAeP...","algorithm":"ssh-ed25519","comment":"admin@demo","valid":true}

4.4 变更查询与评审闭环

# 查询(Web 搜索语法直通 REST)
curl -s -u admin:q1w2e3r4 'http://localhost:8141/a/changes/?q=status:merged&n=1'

实测回显(节选):

)]}'
[{"id":"demo-project~2","triplet_id":"demo-project~master~I2222222222222222222222222222222222222222","project":"demo-project","branch":"master","full_branch":"refs/heads/master","hashtags":[],"change_id":"I2222222222222222222222222222222222222222","subject":"Add second line","status":"MERGED",...,"submitted":"2026-10-27 13:24:53.000000000","submitter":{"_account_id":1000000},"insertions":1,"deletions":0,...,"_number":2,...}]

评审闭环三步(实测):

# 1. 打 Code-Review +2(POST,写 review 用 PUT 会 405 Method Not Allowed)
curl -s -u admin:q1w2e3r4 -X POST -H 'Content-Type: application/json' \
  -d '{"labels":{"Code-Review":2},"message":"LGTM"}' \
  'http://localhost:8141/a/changes/1/revisions/current/review'
# 2. 提交合入
curl -s -u admin:q1w2e3r4 -X POST -H 'Content-Type: application/json' -d '{}' \
  'http://localhost:8141/a/changes/1/submit' | grep -oE '"status":"[A-Z]+"'
# 3. 复核状态
curl -s -u admin:q1w2e3r4 http://localhost:8141/a/changes/1 | grep -oE '"status":"[A-Z]+"'

第 2/3 步实测回显:


"status":"MERGED"

"status":"MERGED"

Change 的 REST 定位符三种形态实测均有效:数字(/changes/1,最常用)、project~change_id(/changes/demo-project~1)、三段式 project~branch~change_id(/changes/demo-project~master~1)。改动 Change 主体后注意 revisions/current 语义会随新 patchset 漂移。

4.5 能力清单(权限自检)

curl -s -u admin:q1w2e3r4 http://localhost:8141/a/accounts/self/capabilities

实测回显(节选):

)]}'
{"readAs":true,"viewAllAccounts":true,"replication-startReplication":true,"viewAccess":true,"delete-project-deleteOwnProject":true,"delete-project-deleteProject":true,"maintainServer":true,"viewQueue":true,"flushCaches":true,"runGC":true,"createAccount":true,"createGroup":true,"administrateServer":true,"emailReviewers":true,"createProject":true,"streamEvents":true,"viewPlugins":true,"deleteGroup":true,"killTask":true,"modifyAccount":true,"viewCaches":true,"viewConnections":true,"viewSecondaryEmails":true,"queryLimit":{"min":0,"max":500}}

服务账户授权时按需裁剪(CI 机器人只需 createProject/streamEvents/queryLimit 等少量能力)。

五、评审流水线自动化示例

组合 query + review 实现最小 CI 门禁轮询(shell 形态,生产可换成 Jenkins/Zuul 的 Gerrit 插件驱动):

#!/usr/bin/env bash
# gerrit-ci-poll.sh:轮询 open 变更,跑校验后回写 Verified 分
GERRIT_HOST=localhost; GERRIT_PORT=8148; GERRIT_USER=reviewbot

ssh -i /etc/gerrit-ci/id_ed25519 -p $GERRIT_PORT $GERRIT_USER@$GERRIT_HOST \
  "gerrit query --format=JSON 'status:open project:demo-project verified:-1..+1'" \
| python3 -c 'import sys,json;[print(json.loads(l)["number"]) for l in sys.stdin if l.startswith("{")]'
| while read change; do
    git fetch "ssh://$GERRIT_USER@$GERRIT_HOST:$GERRIT_PORT/demo-project" "$change" || continue
    if make lint && make test; then
      ssh -i /etc/gerrit-ci/id_ed25519 -p $GERRIT_PORT $GERRIT_USER@$GERRIT_HOST \
        "gerrit review --verified +1 -m 'CI passed' $change,current"
    else
      ssh -i /etc/gerrit-ci/id_ed25519 -p $GERRIT_PORT $GERRIT_USER@$GERRIT_HOST \
        "gerrit review --verified -1 -m 'CI failed' $change,current"
    fi
  done

要点:

  1. git fetch <gerrit> <change号> 可直接拉取任意 Change 的当前 patchset(Gerrit 对 Change 引用的原生支持,评审即代码);
  2. 服务账户建户与归组见 3.5(create-account reviewbot --group "Service Users");
  3. 更正式的门禁用 Submit Requirements 声明(配置篇 3.11 体系):「Verified +1 必须存在且 Code-Review +2 两人(其一非提交者)」。

六、常用命令速查表

场景SSH 命令 / REST备注
版本确认gerrit version值如 gerrit version 3.14.4
列/建项目gerrit ls-projects / gerrit create-project <n>建项目静默成功
查变更gerrit query '<表达式>' [--format=JSON]语法同 Web 搜索框
打分/留言gerrit review --code-review +2 -m "..." <c>,<p>change,patchset 格式
合入/废弃gerrit review --submit <c>,<p> / --abandon同上格式
评审人gerrit set-reviewers -a <u> <c> --project <p>-d 移除
建服务账户gerrit create-account <n> --group "<g>"归 Service Users 组
改账户gerrit set-account <n> --full-name "<f>"静默成功
群组清单gerrit ls-groups含系统组
缓存观测/清理gerrit show-caches / gerrit flush-caches--width 80 控表宽
REST 版本GET /config/server/version剥 )]}' 前缀
REST 查询GET /a/changes/?q=<expr>JSON 数组
REST 打分POST /a/changes/<c>/revisions/current/review必须是 POST
REST 合入POST /a/changes/<c>/submit返回 MERGED

七、排障实录

7.1 2.x 老命令 3.x 报 not found

现象(实测):

ssh -p 8148 admin@localhost gerrit approve --code-review +2 2
# ssh: remote command failed: exit status 1(命令不存在)

结论:gerrit approve / gerrit set-review / gerrit ls-users 在 3.x 已移除;替代分别是 gerrit review(打分/合入/废弃)、gerrit review、REST GET /accounts/?q=(查用户)。网上大量旧资料仍教 2.x 命令,照抄即报错。

7.2 review 命令报 is not a valid patch set

现象(实测):

gerrit review --code-review +2 2
# fatal: 2 is not a valid patch set

根因:3.x 的 review 参数是 CHANGE,PATCHSET 逗号组合。解决:写 gerrit review --code-review +2 2,1(实测成功,REST 复核 approved 生效)。

7.3 REST 打分端点 405 Method Not Allowed

现象:PUT /a/changes/1/revisions/current/review 返回 405。结论:review 动作只支持 POST。解决:改用 POST(回显见 4.4),提交合入 /submit 同为 POST。

7.4 Change 已合入后同 Change-Id 重推被拒

现象(实测回显,部署篇同步沉淀):

 ! [remote rejected] HEAD -> refs/for/master (change http://localhost:8141/c/demo-project/+/1 closed)

根因:closed(MERGED/ABANDONED)状态不能追加 patchset。解决:git commit --amend 换新 Change-Id(或新提交)后重推产生新 Change。

现象:用登录页 cookie 做写操作报 Authentication required。根因:cookie 会话的写请求必须带 X-Gerrit-Auth: <XSRF_TOKEN> 头(浏览器自动处理,curl 要手工加);而 Basic(http password)认证的写请求不需要。解决:自动化一律走 Basic + http password(4.2 设置凭据),避免 cookie/XSRF 组合。

八、参考链接

  1. SSH 命令总览:https://gerrit-review.googlesource.com/Documentation/cmd-index.html
  2. gerrit query:https://gerrit-review.googlesource.com/Documentation/cmd-query.html
  3. gerrit review:https://gerrit-review.googlesource.com/Documentation/cmd-review.html
  4. REST API 总览:https://gerrit-review.googlesource.com/Documentation/rest-api.html
  5. REST changes API:https://gerrit-review.googlesource.com/Documentation/rest-api-changes.html
  6. 用户搜索语法:https://gerrit-review.googlesource.com/Documentation/user-search.html
  7. 站内《Gerrit 3.14 Docker Compose 部署实战》:https://www.quzuo.net/document/ypUmjOG83Lt8
  8. 站内《Gerrit 配置参数详解》:https://www.quzuo.net/document/uzY1P2tFxQvE
  9. 站内《Gerrit 介绍与选型指南》:https://www.quzuo.net/document/jBzSHXoP3n0J