Help us understand the problem. What is going on with this article?

Google Apps Script + OAuthライブラリで、freee APIの操作を行う

この記事は、Web API アドベントカレンダーの6日目の記事です。

Google Apps Script を利用して、freee API の操作を行いたいというニーズをよく聞きます。
いろいろなハウトゥ記事が公開されていますが、「OAuth2.0」の認可操作が一つの壁になっているようです。

今回は、Googleが配布しているOAuth2.0ライブラリ「apps-script-oauth2」を利用して、freee API の操作を行うまでをまとめてみました。

行うこと

  • Googleスプレッドシート + Google Apps Script で、freee API の認可・情報取得を行う。
  • OAuth2.0 の処理は、「apps-script-oauth2」を使う
  • スプレッドシートのメニューに「認可」「ログアウト」の操作メニューを追加する。
  • 「認可」をクリックすると、OAuth処理が始まる。成功したあともう一度「認可」を押すと、認可ユーザーの情報が表示される
  • 「ログアウト」をクリックすると、freeeアプリからログアウト処理される

流れ

  • freee アプリの作成
  • Googleスプレッドシートの準備とapps-script-oauth2のインストール
  • コード作成
  • 実際の動作

freee アプリの作成

契約しているfreeeアカウントを利用して始めます。

freeeアカウントがない場合は「freee API スタートガイド」 を見ながらテスト用の事業所を作ると良いでしょう。

freee API を操作するためには、最初に「freeeアプリ」を作る必要があります。
作成の手順は、公式サイトの「チュートリアル」に詳しくまとまっています。

freee API チュートリアル

このチュートリアル見ながら進めれば、迷うことはないでしょう。順番としては

の流れでアプリを作成します。

image.png

アプリ名、説明、利用規約のチェックを行い、新規作成

image.png

アプリを下書き保存しておきます。

「コールバックURL」
「Client ID」
「Client Secret」

は、後の設定で利用します。

Googleスプレッドシートの準備とapps-script-oauth2のインストール

次に、Googleスプレッドシートの準備をします。

apps-script-oauth2 とは何か

apps-script-oauth2 は、Google Apps Script用の OAuth2.0処理ライブラリです。Googleが管理するGitHubの 「Google Workspace」 内で配布されています。

Google Workspace は、Google APIのためのサンプルコード集です。オープンソースライセンスを採用しており、誰でも自由に利用ができます。

Googleが管理しているライブライということで、安心して使える印象がありますね(サンプル+OSSなのでノーサポートではありますが)。

apps-script-oauth2 のインストール

GSuiteから新しいGoogle スプレッドシートを作成し、「ツール」→「スクリプトエディタ」を選んで、GASのエディタを開きます。

エディタ画面が開いたら、「リソース」→「ライブラリ」を選び、apps-script-oauth2 のインストール準備をします。

「Add a library」欄に、apps-script-oauth2のスクリプトIDを入力して追加します。IDは一意に決まっており

1B7FSrk5Zi6L1rSxxTDgDEUsPzlukDsi4KGuTMorsTQHhGBzBkMun4iDF

を入力。最新バージョンを選んで保存します。

image.png

保存ができたら、インストールは完了です。

freeeアプリの コールバックURLを設定する

次に、先ほど作成したfreee アプリのコールバックURLを修正します。
OAuth2.0認可処理後の遷移先を設定します。

apps-script-oauth2を使った場合、コールバックURLは必ず

https://script.google.com/macros/d/{SCRIPT ID}/usercallback

になります。「script ID」は、エディタ画面の「ファイル」→「プロジェクトのプロパティ」→「スクリプトID」で確認できます。

コールバックURLのSCRIPT IDを書き換え、freeeアプリの「コールバックURL」に入力し、下書き保存します。

image.png

コード作成

Google Apps Script のコードを記述します。 apps-script-oauth2のReadmeに書かれているコードを流用し、freeeアプリに合わせて書き換えました。

const driveService = getDriveService ();

function getDriveService () {
  return OAuth2.createService ('freeeAPI')
    .setAuthorizationBaseUrl (
      'https://accounts.secure.freee.co.jp/public_api/authorize'
    )
    .setTokenUrl ('https://accounts.secure.freee.co.jp/public_api/token')
    .setClientId (
      'freeeアプリのClient ID の値を入れる'
    )
    .setClientSecret (
      'freeeアプリのClient Secret の値を入れる'
    )
    .setCallbackFunction ('authCallback')
    .setPropertyStore (PropertiesService.getUserProperties ());
}

function onOpen () {
  SpreadsheetApp.getUi ()
    .createMenu ('freee API連携')
    .addItem ('認可処理', 'showAuth')
    .addItem ('ログアウト', 'logout')
    .addToUi ();
}

function createModelessDialog (html, title) {
  const htmlOutput = HtmlService.createHtmlOutput (html)
    .setWidth (360)
    .setHeight (120);
  SpreadsheetApp.getUi ().showModelessDialog (htmlOutput, title);
}

function showAuth () {
  if (!driveService.hasAccess ()) {
    const authorizationUrl = driveService.getAuthorizationUrl ();
    const template = HtmlService.createTemplate (
      '<a href="<?= authorizationUrl ?>" target="_blank">Authorize</a>. ' +
        'freee APIの認可をします。'
    );
    template.authorizationUrl = authorizationUrl;
    const page = template.evaluate ();
    const title = 'freeeアプリの認可処理';

    createModelessDialog (page, title);
  } else {
    showUser ();
  }
}

function authCallback (request) {
  const isAuthorized = driveService.handleCallback (request);
  if (isAuthorized) {
    return HtmlService.createHtmlOutput ('Success! You can close this tab.');
  } else {
    return HtmlService.createHtmlOutput ('Denied. You can close this tab');
  }
}

function showUser () {
  const response = UrlFetchApp.fetch (
    'https://api.freee.co.jp/api/1/users/me',
    {
      headers: {
        Authorization: 'Bearer ' + driveService.getAccessToken (),
      },
    }
  );

  const myJson = JSON.parse (response);

  Browser.msgBox ('OAuth認可済みです。\\n認可されたユーザー名:' + myJson.user.display_name);
}

function logout () {
  driveService.reset ();
  const mes = 'freeeアプリからログアウトしました。';
  const logoutTitle = 'ログアウト終了';

  createModelessDialog (mes, logoutTitle);
}

実際の挙動

スプレッドシートのメニューに「認可」「ログアウト」の操作メニューが追加されています。

image.png

  • 「認可処理」をクリックすると、OAuth処理が始まリます。

image.png

image.png

成功したあともう一度「認可」を押すと、認可ユーザーの情報が表示されます。

image.png

「ログアウト」をクリックすると、freeeアプリからログアウト処理されます。

image.png

TakeshiNickOsanai
Developer Relation Manager, Sales Engineer/PreSales, User Community Supporter, CMS Engineer, AWS Certified Solutions Architect
Why not register and get more from Qiita?
  1. We will deliver articles that match you
    By following users and tags, you can catch up information on technical fields that you are interested in as a whole
  2. you can read useful information later efficiently
    By "stocking" the articles you like, you can search right away