feat: add Z.ai GLM Coding Plan as built-in provider #792
Workflow file for this run
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| name: Codex PR Review | |
| on: | |
| pull_request_target: | |
| types: [opened, reopened, ready_for_review, synchronize, labeled] | |
| concurrency: | |
| group: codex-pr-review-${{ github.event.pull_request.number }} | |
| cancel-in-progress: true | |
| permissions: | |
| contents: read | |
| jobs: | |
| pr-review: | |
| # Review all non-draft human PRs by default. The workflow restores the | |
| # trusted prompt from the base SHA before running the write-token bot. | |
| if: | | |
| github.event.pull_request.draft == false && | |
| !endsWith(github.actor, '[bot]') && | |
| !contains(github.event.pull_request.labels.*.name, 'bot-skip') && | |
| vars.CODEX_BOT_ENABLED == 'true' | |
| runs-on: ubuntu-latest | |
| permissions: | |
| contents: read | |
| pull-requests: write | |
| outputs: | |
| review_result: ${{ steps.run_codex.outputs.final-message }} | |
| steps: | |
| - name: Check bot review state | |
| id: check_bot | |
| uses: actions/github-script@f28e40c7f34bde8b3046d885e986cb6290c5673b # v7 | |
| with: | |
| script: | | |
| const marker = "*Open-CoDesign Bot*"; | |
| const allowedLogins = (process.env.BOT_LOGINS || "github-actions[bot]") | |
| .split(",").map((v) => v.trim()).filter(Boolean); | |
| const currentHeadSha = context.payload.pull_request.head.sha; | |
| const reviews = await github.paginate( | |
| github.rest.pulls.listReviews, | |
| { | |
| owner: context.repo.owner, | |
| repo: context.repo.repo, | |
| pull_number: context.payload.pull_request.number, | |
| per_page: 100 | |
| } | |
| ); | |
| const botReviews = reviews | |
| .filter((r) => { | |
| if (!(r?.body || "").includes(marker)) return false; | |
| const u = r.user; | |
| if (!u || u.type !== "Bot") return false; | |
| return allowedLogins.includes(u.login); | |
| }) | |
| .sort((a, b) => { | |
| const at = new Date(a.submitted_at || a.created_at || 0).getTime(); | |
| const bt = new Date(b.submitted_at || b.created_at || 0).getTime(); | |
| if (bt !== at) return bt - at; | |
| return (b.id || 0) - (a.id || 0); | |
| }); | |
| const latest = botReviews[0]; | |
| const hasReviewForCurrentHead = botReviews.some((r) => r.commit_id === currentHeadSha); | |
| const isFollowUp = Boolean(latest?.commit_id && latest.commit_id !== currentHeadSha); | |
| core.setOutput("current_head_sha", currentHeadSha); | |
| core.setOutput("has_review_for_current_head", hasReviewForCurrentHead ? "true" : "false"); | |
| core.setOutput("latest_bot_review_id", latest ? String(latest.id) : ""); | |
| core.setOutput("latest_bot_review_commit", latest?.commit_id || ""); | |
| core.setOutput("is_follow_up_review", isFollowUp ? "true" : "false"); | |
| env: | |
| BOT_LOGINS: ${{ vars.BOT_LOGINS }} | |
| - name: Checkout repository | |
| if: steps.check_bot.outputs.has_review_for_current_head != 'true' | |
| uses: actions/checkout@34e114876b0b11c390a56381ad16ebd13914f8d5 # v4 | |
| with: | |
| ref: ${{ github.event.pull_request.base.sha }} | |
| fetch-depth: 0 | |
| - name: Pre-fetch base and head refs | |
| if: steps.check_bot.outputs.has_review_for_current_head != 'true' | |
| run: | | |
| git fetch --no-tags origin \ | |
| ${{ github.event.pull_request.base.ref }} \ | |
| +refs/pull/${{ github.event.pull_request.number }}/head:refs/remotes/pull/${{ github.event.pull_request.number }}/head | |
| - name: Restore trusted review prompt | |
| if: steps.check_bot.outputs.has_review_for_current_head != 'true' | |
| run: | | |
| # This workflow runs under pull_request_target so it can post reviews. | |
| # The checked-out merge ref is untrusted contributor content; never | |
| # let a PR modify the prompt that receives write-token access. | |
| git show "${{ github.event.pull_request.base.sha }}:.github/prompts/codex-pr-review.md" \ | |
| > .github/prompts/codex-pr-review.md | |
| - name: Resolve review provider config | |
| if: steps.check_bot.outputs.has_review_for_current_head != 'true' | |
| id: review_config | |
| shell: bash | |
| env: | |
| DEFAULT_API_KEY: ${{ secrets.OPENAI_API_KEY }} | |
| DEFAULT_BASE_URL: ${{ secrets.OPENAI_BASE_URL }} | |
| DEFAULT_MODEL: ${{ vars.OPENAI_MODEL }} | |
| DEFAULT_EFFORT: ${{ vars.OPENAI_EFFORT }} | |
| REVIEW_API_KEY: ${{ secrets.REVIEW_OPENAI_API_KEY }} | |
| REVIEW_BASE_URL: ${{ secrets.REVIEW_OPENAI_BASE_URL }} | |
| REVIEW_MODEL: ${{ vars.REVIEW_OPENAI_MODEL }} | |
| REVIEW_EFFORT: ${{ vars.REVIEW_OPENAI_EFFORT }} | |
| run: | | |
| api_key="$REVIEW_API_KEY" | |
| [ -n "$api_key" ] || api_key="$DEFAULT_API_KEY" | |
| base_url="$REVIEW_BASE_URL" | |
| [ -n "$base_url" ] || base_url="$DEFAULT_BASE_URL" | |
| model="$REVIEW_MODEL" | |
| [ -n "$model" ] || model="$DEFAULT_MODEL" | |
| [ -n "$model" ] || model='gpt-5.4' | |
| effort="$REVIEW_EFFORT" | |
| [ -n "$effort" ] || effort="$DEFAULT_EFFORT" | |
| [ -n "$effort" ] || effort='high' | |
| is_deepseek='false' | |
| case "$base_url" in | |
| *api.deepseek.com*) | |
| is_deepseek='true' | |
| ;; | |
| esac | |
| { | |
| echo "api_key=$api_key" | |
| echo "base_url=$base_url" | |
| echo "model=$model" | |
| echo "effort=$effort" | |
| echo "is_deepseek=$is_deepseek" | |
| } >> "$GITHUB_OUTPUT" | |
| - name: Set up Node.js for DeepSeek review | |
| if: steps.check_bot.outputs.has_review_for_current_head != 'true' && steps.review_config.outputs.is_deepseek == 'true' | |
| uses: actions/setup-node@49933ea5288caeca8642d1e84afbd3f7d6820020 # v4.4.0 | |
| with: | |
| node-version: "20" | |
| - name: Run DeepSeek for PR Review | |
| if: steps.check_bot.outputs.has_review_for_current_head != 'true' && steps.review_config.outputs.is_deepseek == 'true' | |
| env: | |
| GH_TOKEN: ${{ github.token }} | |
| GITHUB_TOKEN: ${{ github.token }} | |
| CURRENT_HEAD_SHA: ${{ steps.check_bot.outputs.current_head_sha }} | |
| LATEST_BOT_REVIEW_ID: ${{ steps.check_bot.outputs.latest_bot_review_id }} | |
| LATEST_BOT_REVIEW_COMMIT: ${{ steps.check_bot.outputs.latest_bot_review_commit }} | |
| IS_FOLLOW_UP_REVIEW: ${{ steps.check_bot.outputs.is_follow_up_review }} | |
| DEEPSEEK_API_KEY: ${{ steps.review_config.outputs.api_key }} | |
| DEEPSEEK_BASE_URL: ${{ steps.review_config.outputs.base_url }} | |
| DEEPSEEK_MODEL: ${{ steps.review_config.outputs.model }} | |
| DEEPSEEK_EFFORT: ${{ steps.review_config.outputs.effort }} | |
| run: node .github/scripts/deepseek-pr-review.mjs | |
| - name: Run Codex for PR Review | |
| id: run_codex | |
| if: steps.check_bot.outputs.has_review_for_current_head != 'true' && steps.review_config.outputs.is_deepseek != 'true' | |
| uses: openai/codex-action@e0fdf01220eb9a88167c4898839d273e3f2609d1 # v1 | |
| env: | |
| GH_TOKEN: ${{ github.token }} | |
| GITHUB_TOKEN: ${{ github.token }} | |
| CURRENT_HEAD_SHA: ${{ steps.check_bot.outputs.current_head_sha }} | |
| LATEST_BOT_REVIEW_ID: ${{ steps.check_bot.outputs.latest_bot_review_id }} | |
| LATEST_BOT_REVIEW_COMMIT: ${{ steps.check_bot.outputs.latest_bot_review_commit }} | |
| IS_FOLLOW_UP_REVIEW: ${{ steps.check_bot.outputs.is_follow_up_review }} | |
| with: | |
| openai-api-key: ${{ steps.review_config.outputs.api_key }} | |
| responses-api-endpoint: ${{ steps.review_config.outputs.base_url }} | |
| model: ${{ steps.review_config.outputs.model }} | |
| effort: ${{ steps.review_config.outputs.effort }} | |
| sandbox: danger-full-access | |
| safety-strategy: drop-sudo | |
| prompt-file: .github/prompts/codex-pr-review.md | |
| allow-bots: true | |
| allow-users: '*' |