GoogleフォームからGithubのissueを立てる(2022/03)
初めまして。Taroです。表題のようなことをしたのですが、調べても現在の仕様に合致したやり方が出てこなかったので、備忘録がてら残しておきます。
GASをちゃんと使うのは初めてだったので、GAS周りは初心者向けに手取り足取りで書きます。
全体の手順
- フォームとレポジトリを用意する
- GASを書く
- トークンを取得してスクリプトにコピペ
- トリガーの設定
- 完成!
- カスタマイズ
- ちょっと解説
1. フォームとレポジトリを用意する
特別なことはないので、やり方は省略します。用意してください。
2. GASを書く
フォームが提出されたときに実行する関数を定義します。
フォーム作成画面の右上からメニューを開き、「スクリプトエディタ」をクリック。
左の歯車をクリックして設定画面を開き、「appsscript.json」マニフェスト ファイルをエディタで表示する
にチェックを入れます。
エディタに戻ると、appsscript.json
が表示されています。oauthScopes
という項目に以下の2つを追加してください。
{
"oauthScopes": [
"https://www.googleapis.com/auth/forms",
"https://www.googleapis.com/auth/script.external_request"
],
}
コード.gs
に戻り、以下のように書きます。
const TOKEN = 'ここにトークンをコピペ'
const URL = 'https://api.github.com/repos/AccountName/RepositoryName/issues'
function onFormSubmit(e) {
const answers = e.response.getItemResponses().map(ir => ir.getResponse())
const options = {
"method": "post",
"headers" : {
"Authorization": "token " + TOKEN,
"accept": "application/vnd.github.v3+json"
},
"payload" : JSON.stringify({
"title": 'ここにissueタイトルを書く',
"body": 'ここにissue本文を書く',
}),
}
const res = UrlFetchApp.fetch(URL, options)
// Logger.log(res)
}
2行目のconst URL = ...
のところは、アカウント名とレポジトリ名をいい感じに書き換えてください。
answers
は配列型で、フォームに対する回答が格納されています。これを適当に操作して、issueのタイトルと本文を錬成してください。
3. トークンを取得する
GithubのSettings > Developer settings でトークンを取得します。権限は、repo
にチェックを入れればOK。作成時にしか見れないので、忘れずにコピーしてください(忘れた場合は再発行する羽目になります)。これを、GASの1行目に書き込みます。
4. トリガーの設定
フォーム提出時に、さっき作った関数を自動で実行してくれるようにします。
左端のタイマーアイコンをクリックして、トリガーの設定画面を開きます。右下のボタンでトリガーを追加し、
- 実行する関数を選択: onFormSubmit
- デプロイ時に実行: Head
- イベントのソースを選択: フォームから
- イベントの種類を選択: フォーム送信時
で設定します。エラー通知設定はよくわからんので適当。
5. 完成!
もしかしたら、これでフォームを提出するとエラーを吐くかもしれません。その場合は、エディタ画面で一度「実行」を押す必要があったかもしれないです。たぶん。
6. カスタマイズ
自動でラベルをつけたりassignしたりもできます。その辺は公式ドキュメントを見てください。
7. ちょっと解説
フォームの回答を取得するやつ
const answers = e.response.getItemResponses().map(ir => ir.getResponse())
e.response
はFormRespose
のインスタンスです(公式リファレンス)。
getItemResponses()
はItemRespose
の配列を返します。(公式リファレンス)。
ItemResponse
は質問一つ一つに相当する情報を持っていて、getItem()
で質問を取得したり、getResponse()
で回答を取得したりできます。
APIにPOSTするやつ
const res = UrlFetchApp.fetch(URL, options)
// Logger.log(res)
}
UrlFetchApp
は、http通信をしてくれるやつ(だと思っている)。どういう仕組みか知りませんが、async await
とかは要らず、同期関数みたいに扱えます。
Logger.log()
は、console.log()
みたいなやつです。
Discussion