ginokent Blog
About RSS JA

gh-xz: A gh Extension for Managing PR/Issue Comments with Anchor Strings

Motivation

There are countless situations where you want to automatically post comments to PRs in CI/CD pipelines. It’s convenient when bots notify you via comments about test results, coverage reports, lint warnings, and more.

However, if you implement this without careful consideration, identical comments will multiply every time CI runs. On the other hand, writing logic to search for existing comments, retrieve their IDs, update if found, or create new ones if not—that’s tedious.

So I created a gh extension that manages comments by uniquely identifying them with “anchor strings.”

hakadoriya/gh-xz

Overview

gh-xz is a GitHub CLI (gh) extension that manages PR and Issue comments using anchor strings.

An anchor string is an HTML comment in the format <!-- anchor_string --> appended to the end of a comment. This string identifies the comment—if a comment with the same anchor already exists, it gets updated; otherwise, a new comment is created.

Installation

gh extension install https://github.com/hakadoriya/gh-xz

This makes the gh xz command available.

Usage

Post or Update a Comment

# Specify text directly
gh xz put-anchored-comment owner/repo 123 "my-anchor" "Test results: All passed"

# Read from a file
gh xz put-anchored-comment owner/repo 123 "my-anchor" @./report.md

# Read from stdin
cat ./report.md | gh xz put-anchored-comment owner/repo 123 "my-anchor" @-

On the first run, a new comment is created. On subsequent runs, the comment with the same anchor is updated.

Retrieve a Comment

gh xz get-anchored-comment owner/repo 123 "my-anchor"

This retrieves the body of the comment with the specified anchor.

Using with GitHub Actions

You can easily set this up in GitHub Actions using hakadoriya-actions/setup-gh-xz.

name: post-comment

on:
  pull_request:

jobs:
  comment:
    runs-on: ubuntu-latest
    permissions:
      contents: read
      pull-requests: write
    steps:
      - uses: hakadoriya-actions/setup-gh-xz@v0.0.1

      - name: Post coverage report
        env:
          GH_TOKEN: ${{ secrets.GITHUB_TOKEN }}
        run: |
          gh xz put-anchored-comment \
            ${{ github.repository }} \
            ${{ github.event.number }} \
            "coverage-report" \
            "Coverage: 87.5%"

Comments won’t multiply every time CI runs—they’ll always be updated with the latest results.

How It Works

Internally, it uses gh api to call the GitHub API and manipulate comments.

  1. Retrieve the list of comments for the target PR/Issue
  2. Search for a comment containing the anchor string
  3. If not found, POST to create a new comment; if found, PATCH to update it

The anchor string is automatically wrapped in <!-- -->, so users only need to specify a simple string.

The only dependency is the gh command, and it operates as a single Bash script.