Skip to content

Proto 统一仓库

本文git托管服务由GitHub提供,CI/CD能力由GitHub Actions提供。

随着RPC服务在微服务中使用,大量服务接口需要进行管理,便于不同服务进行对接。那接口应该如何管理呢?

proto文件是IDL,pb文件才是我们需要使用的工具。

我们通过一个大仓来管理所有proto文件,由CI/CD自动编译proto文件为对应代码,以供微服务模块直接使用代码。

proto-unified-process

创建GitHub Repo

test/protos

bash
mkdir -p test/protos
cd test/protos
mkdir -p .github/workflows protos
touch .github/workflows/gen_proto.yml generate.sh protos/.gitkeep

git init
echo '# protos' >> README.md
echo '.DS_Store' >> .gitignore
git add .
git commit -m "first commit"
git branch -M main
git remote add origin git@github.com:mingfutest/protos.git
git push -u origin main
# 首次push会出现GitHub Actions执行失败。忽略即可。

test/proto_gen_export

bash
mkdir -p test/proto_gen_export
cd test/proto_gen_export
mkdir -p .github

git init
touch .github/CODEOWNERS
echo '# proto_gen_export' >> README.md
echo '.DS_Store' >> .gitignore
git add .
git commit -m "first commit"
git branch -M main
git remote add origin git@github.com:mingfutest/proto_gen_export.git
git push -u origin main

生成PAT

test/protos中的Actions需要向test/proto_gen_export仓库中执行Push操作,因此需要生成PAT,作为Actions中的secrets.PROTO_GEN_PUSH_TOKEN

前往:https://github.com/settings/personal-access-tokens/new

注意选择正确的Resource owner。

Repository access选择Only select repositories,只需添加proto_gen_export仓库即可。

Permissions - ContentsAccess选择Read and write

随后在:https://github.com/mingfutest/protos/settings/secrets/actions/new

填入:名称PROTO_GEN_PUSH_TOKEN以及Token内容。

推送一个proto

bash
cd test/protos
cp echo.proto protos/
# 删去.gitkeep
rm -f protos/.gitkeep
git add .
git commit -m "add echo.proto"
git push -u origin main

可以查看test/protos的Actions运行情况,运行成功后在test/proto_gen_export可以看到已经提交了编译得到的文件。

控制 test/proto_gen_export 代码权限

理论上,test/proto_gen_export这个仓库的代码应全部由Actions自动生成,不应人为直接干预。为了尽可能收紧权限范围,可以使用.github/CODEOWNERS文件控制权限。

CODEOWNERS文件的使用可以参考关于代码所有者 - GitHub 文档

本文操作已在GitHub仓库中通过验证:

附录

文件.github/workflows/gen_proto.yml内容:

yaml
name: Gen Proto CI

#on:
#  workflow_dispatch:

on:
  push:
    branches: [ main ]
    paths:
      - 'protos/**'

env:
  PROTOC_VERSION: 27.2
  
jobs:
  build:
    runs-on: ubuntu-latest
    steps:
    - name: Install Protoc
      uses: arduino/setup-protoc@v3
      with:
        version: "${{ env.PROTOC_VERSION }}"
    - name: Setup Go
      uses: actions/setup-go@v5
      with:
        go-version: '^1.22.5'
    - name: Setup protoc-gen-go
      run: go install github.com/golang/protobuf/protoc-gen-go@v1.5.4
    - uses: actions/checkout@v4
      with:
        repository: 'test/proto_gen_export'
        path: 'proto_gen_export'
        token: ${{secrets.PROTO_GEN_PUSH_TOKEN}}
    - uses: actions/checkout@v4
      with:
        path: 'protos'
    - name: Gen Code
      run: chmod +x protos/generate.sh && ./protos/generate.sh

文件generate.sh内容:

bash
#!/bin/bash

mkdir -p proto_gen_export/go;
protoc --proto_path=$(pwd)/protos/protos --go_out=plugins=grpc:$(pwd)/proto_gen_export/go $(pwd)/protos/protos/*.proto && \
cd proto_gen_export && git config user.email "" && git config user.name "GitHub Actions" && git add . && git commit -m "Auto Update" && git push

文件echo.proto内容:

protobuf
syntax = "proto3";

option go_package = "./pb";

package pb;

service EchoServer {
  rpc Echo(EchoRequest) returns (EchoResponse) {}
}

message EchoRequest {
  string value = 1;
}

message EchoResponse {
  string value = 1;
}