これは何か

GitHub Issueに起票したものをスプレッドシートに転記するシステムを制作したため、制作方法を記事にします。

使用したサービスやAPI

  • Google スプレッドシート
  • Google Apps Script
  • GitHub Issue
  • issue取得API

機能

  • issue取得APIを利用してgithub issueに起票されているissueを取得し、スプレッドシートに転記
  • issue番号、タイトル、ラベル、マイルストーン、担当者、状態、issueURLを転記
  • スプレッドシートの関数を使用して状態がcloseになっているissueは、行全体を灰色にして完了していることが分かるようにする
  • トリガーを時間に設定し、1時間ごとにスプレッドシートの更新を行う

スプレッドシート

スプレッドシートには以下の項目を転記しています。

  • issue番号
  • issueタイトル
  • ラベル
  • マイルストーン
  • 担当者
  • 状態
  • 最終更新日時
  • issue URL

Google Apps Script

GASにコードを書き始める前にGithubでアクセストークンを発行しておく。
参照:個人用アクセストークンの作成

<br />//Github issue取得APIを利用してissueを取得する
function GetOpenIssues() {
var OWNER = 'リポジトリのオーナー名';
var REPO = 'リポジトリ名'

var url = 'https://api.github.com/repos/' + OWNER + '/' + REPO + '/issues?state=all&sort=created';
var accessToken = '発行したアクセストークン';
var headers = {
'Authorization': 'token '+ accessToken
};

var options = {
'method': 'GET',
'headers': headers,
};
var response = UrlFetchApp.fetch(url, options).getContentText();
var data = JSON.parse(response);
return data;
}

//転記を実行する
function UpdateGSheet(issueDataList) {
issueDataList = GetOpenIssues();
var sheetId = '転記したいスプレッドシートのID';
var sheetName = '転記したいシート名';
var ss = SpreadsheetApp.openById(sheetId).getSheetByName(sheetName);

var issueObjectList = []
var issueSize = Object.keys(issueDataList).length;
for(var index = 0;index < issueSize ;index++){
var d = issueDataList[index];
var issueObject = UpdateIssue(d);
issueObjectList.push(issueObject);
}
var issueInfoSize = Object.keys(issueObjectList[0]).length;

// シートをクリア
ClearBeforeSheetInfo(ss);

ss.getRange(2,1,issueSize,issueInfoSize).setValues(issueObjectList);
}

//シートに更新内容を転記する前にシートの中身を一度削除する
function ClearBeforeSheetInfo(sheet){
var range = sheet.getRange("A2:X100");
range.clear({contentsOnly: true});
}

//転記する内容の定義
function UpdateIssue(issueData){
var number = issueData['number'];
var title = issueData['title'];
var updated_at = new Date(issueData['updated_at']);
var jst_updated_at = Utilities.formatDate(updated_at, 'Asia/Tokyo', 'yyyy/MM/dd HH:mm:ss');
var state = issueData['state'];
if(issueData['assignee']){
var assign = issueData['assignee']['login']
} else {
assign = '指定なし'
}
if(issueData['milestone']){
var milestone = issueData['milestone']['title']
} else {
milestone = ''
}
var labelNames = "";
for (var i = 0; i < issueData['labels'].length; i++) {
//ラベルを全て取得してカンマ区切りで格納
labelNames += issueData['labels'][i]['name'] + ",";
}
//カンマが一つ余分なので、余分なカンマを削除
labelName = labelNames.slice(0, -1);

var issueList = []
issueList = [
number,
title,
labelName,
milestone,
assign,
state,
jst_updated_at,
issueData['url']
]
return issueList;
}