自動化できないかなと思って少し調べたのでメモ
やりたいこと
- branchの作成
- ファイルの更新・コミット
- pull-reqの作成
NodeJSからGitHubを叩く
@octokit/restのライブラリを使う。
GitHubのREST APIのNode IF。
node-githubから移行されたとのこと。
ドキュメント
以下にAPIのドキュメントがある。
https://octokit.github.io/rest.js/
――が、実際はGitHub APIのラッパーなので、そちらと見比べながらやるのがいい。
debugモード
Set DEBUG=octokit:rest* for additional debug logs.
環境変数にセットすれば行けるらしい。
やってみる
初期化
import Octokit from '@octokit/rest'
const octokit = new Octokit()
Enterprise環境とかだと設定が必要だったりするけど、叩くのはEnterpriseじゃないので設定しない。
認証
プライベートリポジトリや一部APIを叩くには認証が必要。
ocktokitにはいくつか認証方法が提供されているけど、今回はAccessTokenが手元にある前提で行う。
AccessTokenは本家で発行する、またはOAuthして取ってくる必要がある。
※例えばこう koa+passportでGitHub認証
AccessTokenがあるなら authenticate
を叩くだけ。
octokit.authenticate({
type: 'token',
token: accessToken,
})
返り値などは特にない。
参考: https://github.com/octokit/rest.js#authentication
referenceの取得
つまりブランチ。作成したいブランチの元となるブランチの情報をとってくる。
const origin = await octokit.gitdata.getReference({
owner: 'rymizuki',
repo: 'example',
ref: 'heads/master',
})
あくまでここで扱うのはreferenceなので、heads/ブランチ名
になる。
参考: https://octokit.github.io/rest.js/#api-Gitdata-getReference
referenceの作成
取得したreferenseから新しくreferenseを切る。
const ref = await octokit.gitdata.createReference({
owner,
repo,
ref: 'refs/heads/test',
sha: origin.data.object.sha,
})
元ブランチのshaから派生させる。
ref
には「refs
から始まり/
を2つ以上含む」という制約がある。
なお、同名のreferenceを作成しようとするとエラーになる。
参考: https://octokit.github.io/rest.js/#api-Gitdata-createReference
ファイルの取得
今回の要求としては「すでに存在しているファイルを上書き更新」なので、ファイルを取得する。
const content = await octokit.repos.getContent({
owner,
repo,
ref: 'heads/test', // さっき作ったブランチの情報をとってくる
path: 'README.md', // ファイルパス
})
// とってきたデータをデコードする
const data = new Buffer(content.data.content, content.data.encoding).toString()
参考: https://octokit.github.io/rest.js/#api-Repos-getContent
ファイルの更新
コミットしてプッシュする。
以下のAPIを叩くことで、ファイルの送信、commitの作成をGitHub上で行うことができる。
const updateResult = await octokit.repos.updateFile({
owner,
repo,
branch: 'test', // これはreferenceではなくbranch
message: 'docs(README): なんやかんや', // コミットメッセージ
path: 'README.md',
content: new Buffer(`${ data }\n\n更新したよ`).toString('base64'), // base64にエンコードする
sha: content.data.sha,
})
参考: https://octokit.github.io/rest.js/#api-Repos-updateFile
PullRequestの作成
const pullreq = await octokit.pullRequests.create({
owner,
repo,
head: 'test', // マージしたいブランチ
base: 'master', // マージされたいブランチ
title: 'README.mdを更新した', // pull-reqのタイトル
body: 'ほにゃらら', // pull-reqの本文
})
参考: https://octokit.github.io/rest.js/#api-PullRequests-create
まとめ
- ブランチの作成からPullReqの作成までの流れを紹介しました
- authenticateはaccessToken使っとくのが一番わかり易い
- refarenceとheadとbranchの関係を理解して使おう
- GitHub APIはとっても多機能だけど、使いこなせると便利そうですね