17
16

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?

More than 5 years have passed since last update.

以前は動いていたGoogleAppsScriptをコピペすると動かなかった件

Last updated at Posted at 2018-11-30

はじめに

Google Formを送信した際に、入力値を取得してSlackに通知するスクリプトを書いて使っていたのですが、いざ検証用のフォームで動いていたコードを本番用のフォームにコピーしたところうまく動きませんでした。

function onFormSubmit(e) {
  const itemResponse = e.response.getItemResponses();
  const answers = getAnswers(itemResponse);

  // Slackに通知
  sendToSlack(answers);
}
// 以下省略
TypeError: undefined のメソッド「getItemResponses」を呼び出せません。 at onFormSubmit

原因がわかるまで結構時間がかかったので、備忘録の意味も含めて記事にしておこうと思います。

結論

OAuthスコープに、利用するAPIを指定してトリガーを再設定すると解決しました。

原因

スクリプトに付与された権限が不足していたため、実行に失敗していました。
https://myaccount.google.com/permissions利用するプロジェクト名のアプリがないor付与されているアクセス権が不足していると、エラーとなります。
今回だと、Google Formsのデータ取得のAPI利用が許可されていなかったため、それを追加する必要があります。(以前は明示的に指定せずに必要な権限がリクエストされていたと思うのですが、仕様が変わったのでしょうか……?)

このアクセス権は、トリガーの設定時OAuthスコープにあるものの権限を承認ウィンドウを経て付与されます。

  • 1. プロジェクトのOAuthスコープが不足している
  • 2. トリガー設定時に付与される権限が不足したまま、サードパーティーアプリが作成される
  • 3. 発火時にエラー

という流れになっているので、**OAuthスコープを正しく設定し、トリガーを再設定することによって正しい権限を付与(追加)**すると解決します。

参考:
Authorization Scopes  |  Apps Script  |  Google Developers
Googleフォームのスクリプトの新しいトリガー設定画面でトリガー設定すると、イベントがうまく渡らなくなりました。

解決策

1. OAuthスコープの追加

OAuthスコープは、以下のどちらかで指定できます。

a. 明示的に使用するAPIがわかるコードを入力する
b. スコープを直接指定する

a. 明示的に使用するAPIがわかるコードを入力する

スクリプト内に、APIを使っていることがわかるコードがあると、そこから自動でOAuthスコープを取得してくれるようです。なので、コメントアウトしてGoogle FromsのAPIを書き込みます。

+ // FormApp.getActiveForm() 
+
function onFormSubmit(e) {
  省略
}
b. スコープを直接指定する

表示 > マニフェストファイルを表示appsscript.jsonを表示します。
image.png

oauthScopesに必要なAPIを指定して追加、保存する。

appsscript.json
{
  "timeZone": "Asia/Tokyo",
  "dependencies": {
  },
  "oauthScopes": [
-   "https://www.googleapis.com/auth/script.external_request"
+   "https://www.googleapis.com/auth/script.external_request",
+   "https://www.googleapis.com/auth/forms"
  ],
  "exceptionLogging": "STACKDRIVER"
}

トリガーの再設定

OAuthスコープを修正したら、エラーの出ていたトリガーを削除し、再度トリガーを設定すれば完了です。
認証のためポップアップが表示されるので、追加したAPIが表示されていることを確認して許可しましょう。
https://myaccount.google.com/permissions に、正しく権限が付与されたことを確認してフォームを送信すると、エラーが解消されていると思います。お疲れ様でした。

以下確認(蛇足)

まず適当なFormを作成します。
image.png

次にメニューからスクリプトエディタを選択します。
image.png

フォームの入力値をログに出力するコードを記載して保存します。

アンケートスクリプト
function onFormSubmit(e) {
  const itemResponse = e.response.getItemResponses();
  
  for (var i = 0; i < itemResponse.length; i++){    
    var formData = itemResponse[i];
    
    Logger.log({
      question: formData.getItem().getTitle(),
      answer: formData.getResponse()
    });
  }
}

保存アイコンの右の時計アイコンをクリックすると、以前はトリガー設定モーダルダイアログが表示される仕様でしたが、別タブでG Suite Developer Hubのトリガーページに飛ぶようになっています。
image.png

右下のトリガーを追加をクリックします。

image.png

トリガーを設定して保存します。

image.png

アンケートを開き、回答を送信し、
image.png

プロジェクトページを確認すると、エラーが発生しています(メールも来ます)。
image.png

プロジェクトOAuthスコープが不足してGoogle FormsのAPIが利用できなかったためのようなので、追加します。

上の解決策を参照
image.png

OAuthスコープを追加して再度アンケートに回答すると、メールで以下のエラーが来ます。
image.png

OAuthスコープを追加したことで先ほど追加したトリガーの権限では実行できなかったようです。今あるトリガーを削除して再度設定します。
ポップアップで承認ウィンドウが出るので、確認して許可を押すと、トリガーが追加されます。

image.png

権限が付与されたことを https://myaccount.google.com/permissions で確認しましょう。
image.png

再度アンケートに回答すると、エラー率が50%に下がり、正常に実行できたことがわかります。
image.png

17
16
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
17
16

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?