diff --git a/.github/workflows/hermetic_library_generation.yaml b/.github/workflows/hermetic_library_generation.yaml index fb0e1bc65669..cc71f46f214b 100644 --- a/.github/workflows/hermetic_library_generation.yaml +++ b/.github/workflows/hermetic_library_generation.yaml @@ -15,21 +15,17 @@ # downstream client libraries before they are released. name: Hermetic library generation upon generation config change through pull requests on: - workflow_dispatch: pull_request: - paths: - - "generation_config.yaml" jobs: library_generation: runs-on: ubuntu-latest env: - library_generation_image_tag: 2.39.0 + library_generation_image_tag: 2.40.0 steps: - uses: actions/checkout@v4 with: fetch-depth: 0 - token: ${{ secrets.CLOUD_JAVA_BOT_TOKEN }} - name: Generate changed libraries shell: bash run: | @@ -37,8 +33,16 @@ jobs: [ -z "$(git config user.email)" ] && git config --global user.email "cloud-java-bot@google.com" [ -z "$(git config user.name)" ] && git config --global user.name "cloud-java-bot" bash generation/hermetic_library_generation.sh \ - --target_branch ${{ github.base_ref }} \ - --current_branch ${{ github.head_ref }} \ + --base_ref "${base_ref}" \ + --base_repo "${base_repo}" \ + --head_ref "${head_ref}" \ + --head_repo_url "${head_repo_url}" \ + --head_repo_name "${head_repo_name}" \ --image_tag "${library_generation_image_tag}" env: + base_ref: ${{ github.event.pull_request.base.ref }} + base_repo: ${{ github.repository }} + head_ref: ${{ github.event.pull_request.head.ref }} + head_repo_url: ${{ github.event.pull_request.head.repo.html_url }} + head_repo_name: ${{ github.event.pull_request.head.repo.full_name }} GH_TOKEN: ${{ secrets.CLOUD_JAVA_BOT_TOKEN }} diff --git a/generation/hermetic_library_generation.sh b/generation/hermetic_library_generation.sh index b37b898c7364..d556cc576b45 100755 --- a/generation/hermetic_library_generation.sh +++ b/generation/hermetic_library_generation.sh @@ -1,4 +1,5 @@ #!/bin/bash +set -euo pipefail # This script should be run at the root of the repository. # This script is used to, when a pull request changes the generation # configuration (generation_config.yaml by default): @@ -12,28 +13,46 @@ # 4. Commit the changes to the pull request, if any. # 5. Edit the PR body with generated pull request description, if applicable. +# Note that the pull request may come from a forked repository, e.g., renovate +# pull request. Special handling is needed in this case. + # The following commands need to be installed before running the script: # 1. git # 2. gh # 3. docker # The parameters of this script is: -# 1. target_branch, the branch into which the pull request is merged. -# 2. current_branch, the branch with which the pull request is associated. -# 3. image_tag, the tag of gcr.io/cloud-devrel-public-resources/java-library-generation. -# 3. [optional] generation_config, the path to the generation configuration, +# 1. base_ref, the branch into which the pull request is merged. +# 2. base_repo, the repository into which the pull request is merged. +# 3. head_ref, the branch with which the pull request is associated. +# 4. head_repo_url, the url of the repository with which the pull request is associated. +# 5. head_repo_name, the name of the repository with which the pull request is associated. +# 6. image_tag, the tag of gcr.io/cloud-devrel-public-resources/java-library-generation. +# 7. [optional] generation_config, the path to the generation configuration, # the default value is generation_config.yaml in the repository root. while [[ $# -gt 0 ]]; do key="$1" case "${key}" in - --target_branch) - target_branch="$2" + --base_ref) + base_ref="$2" shift ;; - --current_branch) - current_branch="$2" + --base_repo) + base_repo="$2" + shift + ;; + --head_ref) + head_ref="$2" shift ;; + --head_repo_url) + head_repo_url="$2" + shift + ;; + --head_repo_name) + head_repo_name="$2" + shift + ;; --image_tag) image_tag="$2" shift @@ -50,13 +69,28 @@ esac shift done -if [ -z "${target_branch}" ]; then - echo "missing required argument --target_branch" +if [ -z "${base_ref}" ]; then + echo "missing required argument --base_ref" + exit 1 +fi + +if [ -z "${base_repo}" ]; then + echo "missing required argument --base_repo" + exit 1 +fi + +if [ -z "${head_ref}" ]; then + echo "missing required argument --head_ref" exit 1 fi -if [ -z "${current_branch}" ]; then - echo "missing required argument --current_branch" +if [ -z "${head_repo_url}" ]; then + echo "missing required argument --head_repo_url" + exit 1 +fi + +if [ -z "${head_repo_name}" ]; then + echo "missing required argument --head_repo_name" exit 1 fi @@ -70,14 +104,21 @@ if [ -z "${generation_config}" ]; then echo "Use default generation config: ${generation_config}" fi -volume_name="repo" -workspace_name="/workspace/repo" -repo_volumes="${volume_name}:${workspace_name}" +fork="forked-repo" +workspace_name="/workspace" baseline_generation_config="baseline_generation_config.yaml" message="chore: generate libraries at $(date)" -git checkout "${target_branch}" -git checkout "${current_branch}" +git checkout "${base_ref}" +if [[ "${head_repo_name}" == "${base_repo}" ]]; then + git checkout "${head_ref}" +else + echo "The pull request comes from a forked repository: ${head_repo_url}" + git remote add "${fork}" "${head_repo_url}" + git fetch "${fork}" + git checkout -b "${head_ref}" "${fork}/${head_ref}" + git branch --set-upstream-to="${fork}/${head_ref}" +fi # if the last commit doesn't contain changes to generation configuration, # do not generate again as the result will be the same. contains_config_change=$(git diff-tree --no-commit-id --name-only HEAD~1..HEAD -r | grep "${generation_config}") @@ -86,31 +127,16 @@ if [[ "${contains_config_change}" == "" ]]; then exit 0 fi # copy generation configuration from target branch to current branch. -git show "${target_branch}":"${generation_config}" > "${baseline_generation_config}" +git show "${base_ref}":"${generation_config}" > "${baseline_generation_config}" config_diff=$(diff "${generation_config}" "${baseline_generation_config}") - -# bind docker volume to include the repository in docker running environment. -if [[ $(docker volume inspect ${volume_name}) != '[]' ]]; then - docker volume rm ${volume_name} -fi -docker volume create \ - --name ${volume_name} \ - --opt "type=none" \ - --opt "device=$(pwd)" \ - --opt "o=bind" # run hermetic code generation docker image. docker run \ --rm \ - -v "${repo_volumes}" \ - -v /tmp:/tmp \ - -v /var/run/docker.sock:/var/run/docker.sock \ - -e "RUNNING_IN_DOCKER=true" \ - -e "REPO_BINDING_VOLUMES=-v ${repo_volumes}" \ + -u "$(id -u):$(id -g)" \ + -v "$(pwd):${workspace_name}" \ gcr.io/cloud-devrel-public-resources/java-library-generation:"${image_tag}" \ - python /src/cli/entry_point.py generate \ --baseline-generation-config-path="${workspace_name}/${baseline_generation_config}" \ - --current-generation-config-path="${workspace_name}/${generation_config}" \ - --repository-path="${workspace_name}" + --current-generation-config-path="${workspace_name}/${generation_config}" # commit the change to the pull request. git add java-* pom.xml gapic-libraries-bom/pom.xml versions.txt changed_files=$(git diff --cached --name-only) @@ -126,6 +152,6 @@ git commit -m "${message}" git push # set pr body if pr_description.txt is generated. if [[ -f "pr_description.txt" ]]; then - pr_num=$(gh pr list -s open -H "${current_branch}" -q . --json number | jq ".[] | .number") + pr_num=$(gh pr list -s open -H "${head_ref}" -q . --json number | jq ".[] | .number") gh pr edit "${pr_num}" --body "$(cat pr_description.txt)" fi