Google AppScriptでHTTP POSTを受け付ける方法は、ググればかなり出てきます。
2021年頃の仕様変更(参考URL1 2)によって console.log
や Logger.log
の出力はGoogle Cloudに紐づける必要があり、ちょっとした開発は面倒です。
ここでは、ともかくHTTP POSTのBodyをSpreadsheetに出力するだけの最小コードを用意しました。これにより e
の出力をとりあえず確認できるようになります。
動画内の当該URLは(もちろん)無効化されてます。
論よりコード
function doPost(e) {
const sheet = SpreadsheetApp.getActiveSpreadsheet().getSheets()[0];
sheet.getRange("1:1").insertCells(SpreadsheetApp.Dimension.ROWS);
sheet.getRange(1, 1).setValue((new Date).toLocaleString('ja-JP'));
sheet.getRange(1, 2).setValue(e);
sheet.getRange(1, 3).setValue(e.postData.contents);
const output = ContentService.createTextOutput(JSON.stringify({result:"Ok"}));
output.setMimeType(ContentService.MimeType.JSON);
return output;
}
上記コードに対してHTTP POSTすると、スプレッドシート内の一番左(=先頭)シートに対して、最新が1行目に来るように記録されます。
使い方
- 新規にGoogle Spreadsheetを作成
- Spreadsheetの [拡張機能] > [App Script]
-
myFunction
とコードを入れ替える - [デプロイ] > [新しいデプロイ]
- [種類の選択] > ウェブアプリ
- アクセスできるユーザー = 全員
- [デプロイ] >> [アクセスを承認] >> [許可]
これで URL が払い出されます。
あとは例えば
curl -v -L -H "Content-Type: application/json" -d '{"b":200}' https://script.google.com/macros/s/APP_ID.../exec
のようにHTTP POSTすればOKです。
スクリプトを編集したらデプロイをし直してURLを再発行し、新たなURLにアクセスするようにしてください。
認証/認可の仕組みはありません。よって、URLが漏洩すると誰でもPOSTできることになるため、URLの取り扱いは厳重に行ってください。
URLの無効化は、当該Spreadsheetをゴミ箱=>"完全に削除"で行えます。Sheetの中身やスクリプトのバックアップをお忘れなく。
実際の活用には...?
Google Apps ScriptのdoPostでJSONなパラメータのPOSTリクエストを受ける にも書かれているように JSON.parse(e.postData.contents)
とすれば、Objectとして取り扱えます。
あとは sheet.getRange(ROW, COL).setValue(VAL);
で記録していけるでしょう。
ちなみに contents
と getDataAsString()
は等価のようです。
getDataAsString()
の引数には解釈するcharsetが指定できるので、contentsを使ってエンコーディングが変だった場合に有効かもです。
e
の中身について
doPost(e)
もしくは doGet(e)
で渡された e
の中身は https://developers.google.com/apps-script/guides/web#request_parameters で解説されています。
ちなみに e.postData
は FileUpload 型となっているのですが、肝心の定義が見当たりません。
こちらの記事によるとBlobを継承しているとのこと。(だからgetDataAsString()
がある)
メソッド/プロパティ一覧を Object.keys(e.postData).toString()
で確認してみましたが contents
length
name
type
以外で Blob と異なる点は見当たりませんでした。
Blogとして扱うのが良さそうです。
Object.keys(e.postData).toString();
//=> toString,getName,getBytes,setName,getDataAsString,setDataFromString,isGoogleType,getAllBlobs,copyBlob,setContentTypeFromExtension,getContentType,setContentType,setBytes,getAs,contents,length,name,type
あとがき
年次イベント、無事終わってよかったよ。
EoT