LoginSignup
10
8

More than 5 years have passed since last update.

Github Appでレビュー済みPRに自動的にラベルを追加

Posted at

概要

GithubのPRがレビュー済みになった際にラベルを付けておくと、レビュー済みPRが見分けやすくて便利です。
今回その作業をGithub Appで自動化することにしました。
以下はその作業ログです。

Github Appの作成

作成するAppの仕様

今回作成するAppは
すべてのreviewerがApproveしたらreviewedラベルをPRに追加する
という仕様にします。

Probot

ProbotはGithub Appのframeworkです。
ドキュメントも充実していて、Github Appの作成を効率良く行えるので、今回はこれを使うことにしました。

Node.js

Probotを使うにはNode.jsが必要になります。
このページを参照して、動作に必要なバージョンをインストールしておきます。

雛形の作成

yarnとnpmを使う方法がドキュメントにはありますが、今回はnpmを使っていきます。

下記コマンドを実行すると、Probotが雛形を作ってくれます。

npx create-probot-app {app-name}

対話形式でApp nameなどを聞かれるので答えていきます。

Gihub repositoryへのpush

ここまでのソースをGithubのrepositoryへpushしておきます。

smee.io

ローカルでの開発時にもGithubのwebhookを受け取れるようにするため、
smee.ioを利用します。
Start a new channelボタンを押すと、Webhook Proxy URLが生成されるので、
このURLとローカルのappを結びつけて開発していきます。
Probotはsmee.ioと簡単に連携できるようになっています。

Github Appの作成

https://github.com/settings/apps/new
から新規Appを作成します。

Homepage URLにはgithub repositoryのURLを、
Webhook URLにはsmee.ioで生成したURLを、
Webhook secret (optional)にはひとまずdevelopmentをいれておきます。(あとで書き換えます)

PermissionsはGithub Appでアクセスできる権限を指定します。
今回作成するAppはPull Requestのreviewの内容をみて、labelを追加するので
Pull requestsRead-only,labelを操作するのはIssueのpermissionのようなので
IssueRead & Writeを設定します。
それ以外はデフォルトのままにしておきます。

Subscribe to eventsApproveされたことの通知を受けるためにPull request reviewを、それとPRのheadブランチ更新のタイミングでApproveが無効になることがあるので、それも検知するためにPull requestもsubscribeしておきます。

Where can this GitHub App be installed?
はAppの公開範囲をどこまでにするのかの設定ですが、一般に公開されて問題なければ
Any accountにしておきます。

設定が終わったらCreate Github Appボタンを押してAppを作成します。

private keyの生成

Appの作成後の画面で、Generate a private keyボタンがあるので、
ボタンを押してprivate keyを発行しておきます。
このkeyはAppの実行に必要になります。
発行すると自動的にkeyがダウンロードされるので、レポジトリ直下に移動しておきます。
(既に.gitignoreで*.pemが指定されているので、git管理外になります。)

.envの設定

.env.exampleをコピーして.envを作ります。

.env内のAPP_IDとWEBHOOK_PROXY_URLを設定します。
APP_IDはhttps://github.com/settings/apps/{app-name}ページ内に書かれているIDの値で、WEBHOOK_PROXY_URLにはsmee.ioのURLをいれておきます。

Appの起動

npm run devで起動できることを確認します。

webhookの取得

今回作成する AppはPRがApproveされたタイミングで、全てのreviewerがApproveしたかをチェックします。
そのため、reviewがsubmitされたタイミングの通知を監視します。

app.on('pull_request_review.submitted', async context => {
  app.log('submitted')
  }

Approve回数の取得

Approveされたreviewを取得するために、reviewのリストを取得します。

const params = context.issue()
const reviews = await context.github.pullRequests.getReviews(params)

context.githubocotokit/restのインスタンスで、これを使うと簡単にGithub APIにアクセスできます。

reviewのstatusがAPPROVEDになっているものがApproveされた際のreviewなので、この回数をカウントしておきます。

reviewerの取得

reviewerを直接取得するAPIは存在しないようなので、reviewerに指名されてまだ一度もreviewしていないuserを取得するgetReviewRequestsの数と、reviewしたすべてのuser数を組み合わせることでreviewerの総数とします。

PRを作成したuserもreviewはできるので、PRの作成者はカウントしないようにしておきます。
PRの作成者は

const params = context.issue()
const pull_request = await context.github.pullRequests.get(params)
const creator = pullRequest.data.user.login

として取得できます。

ラベルの追加

reviewerの数==Approveの数になったらラベルを追加します。
ラベル名はひとまずreviewedとしておきます。

ラベルの追加は

const labels = context.issue({ labels: ['reviewed'] })
context.github.issues.addLabels(labels)

で行います。
labelsの配列に複数ラベルを指定すれば、一度にまとめてラベルを追加することもできます。

ラベルの削除

Githubのレポジトリの設定でDismiss stale pull request approvals when new commits are pushedにチェックがついていると、reviewがApproveされたあと、再度該当branchにpushが走ると、そのタイミングでApproveが無効になります。

その際は再度Approveしてもらう必要があるので、ラベルも取り除いておきます。
PRの対象branch更新のeventは pull_request.synchronizeを監視することで取得できます。
この際にreviewer数 !== Approve数 になっていて、かつreviewedラベルがついていたらラベルの削除APIを投げておきます。

const rmLabel = context.issue({ name: 'reviewed' })
context.github.issues.removeLabel(rmLabel)

ラベル名の変更

ここまではラベルをreviewed固定にしていましたが、設定で変えられるようにしておきます。

このGithub Appをインストールしたレポジトリに.github/reviewed.ymlがあった場合、そこに書かれているラベルを使用し、なければデフォルトのreviewedラベルを使うようにします。

github/reviewed.yml
labelName: ok

probot-configを使うと簡単にymlにアクセスできるので、package.jsonに追加しておきます。

npm install -S probot-config

probot-configを使ってreviewed.ymlを取得します。

const getConfig = require('probot-config')

const defaultConfig = {
  labelName: 'reviewed'
}
const config = await getConfig(context, 'reviewed.yml') || defaultConfig
const label = config.labelName

deploy

Probotのdocumentにはdeploy先として、Glitch,Heroku,Nowが紹介されていますが、今回はNowを使用します。

https://probot.github.io/docs/deployment/#now
上記URLにdeployの手順が書いてありますが、この手順ではエラーが出てしまったので、
https://github.com/probot/probot/blob/master/docs/deployment.md#now
側の手順を実行します。

違いはprivate_keyをbase64エンコードしてNowに送っている箇所です。
なお、デプロイの度に生成されるURLが変わるみたいなので、毎回aliasを付け直す必要があるようです。

Webhook APIの書き換え

Nowでaliasを振ったAPIのURLでGithub AppのWebhook URLを変更します。
併せてWebhook secretも変更しておくと安全です。
Webhook secretを変更した際には、再度Nowのdeployが必要になります。

repository & app

今回作成したAppのレポジトリはこちらになります。
Appのリンクはこちらになります。

気に入って頂けたらInstallして使ってみてもらえると嬉しいです。

10
8
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
10
8