FirebaseのFunctionsでスクレイピングするときの注意事項
先日、毎月書いた記事一覧を取得するSlackアプリでZennの記事が取得できなくなるという事象が発生しました。
原因はZennの記事一覧取得API(非公式)に403でアクセスできなくなっていたためでしたが、
もともと非公式のAPIを使わせていただいていたものだったので、これは仕方ないと、スクレイピングで記事を取得するように修正をすることに。
その際、FirebaseのFunctions上でPlaywrightを動かすのにちょっと工夫が必要だったのでそれをここに残しておきます。
2021/06/08追記
Zennの開発者、catnoseさんよりコメントをいただきまして
ちなみにAPIをアクセス禁止にしたわけではなく、
https://api.zenn.dev/*がhttps://zenn.dev/api/*に変わった感じです!
とのことでした。
また、Kawamata Ryoさんより、メモリの変更はコードで設定することもできるとの情報をいただきました!以下のようにFunctionsのオプションとしてmemory
を指定することでもメモリ変更が可能なようです。
const runtimeOpts = {
timeoutSeconds: 300,
memory: '1GB'
}
exports.myStorageFunction = functions
.runWith(runtimeOpts)
.storage
.object()
.onFinalize((object) = > {
// do some complicated things that take a lot of memory and time
});
なお、詳細は公式を確認していただきたいのですが、指定できるmemory
の値は以下を指定できるみたいです。
- 128MB
- 256MB
- 512MB
- 1GB
- 2GB
- 4GB
- 8GB
環境
- macOS Big Sur 11.3.1
- Flutter 2.2.0
ポイント
- playwright-aws-lambdaを使う
- デフォルトのメモリ容量256MBだと足りないのでメモリを増やす必要がある
playwright-aws-lambdaを使う
最初、通常のPlaywrightをインストールして使っていたのですが、以下のようにchromiumを起動できず。
2021-06-01T13:43:21.934Z ? firestore-onCreate: browserType.launch: Failed to launch chromium because executable doesn't exist at /root/.cache/ms-playwright/chromium-878941/chrome-linux/chrome
2021-06-01T13:43:21.934Z ? firestore-onCreate: Try re-installing playwright with "npm install playwright"
2021-06-01T13:43:21.934Z ? firestore-onCreate: Error
2021-06-01T13:43:21.934Z ? firestore-onCreate: at Object.captureStackTrace (/workspace/node_modules/playwright/lib/utils/stackTrace.js:50:19)
2021-06-01T13:43:21.934Z ? firestore-onCreate: at Connection.sendMessageToServer (/workspace/node_modules/playwright/lib/client/connection.js:65:48)
2021-06-01T13:43:21.934Z ? firestore-onCreate: at Proxy.<anonymous> (/workspace/node_modules/playwright/lib/client/channelOwner.js:64:61)
2021-06-01T13:43:21.934Z ? firestore-onCreate: at /workspace/node_modules/playwright/lib/client/browserType.js:60:67
2021-06-01T13:43:21.934Z ? firestore-onCreate: at BrowserType._wrapApiCall (/workspace/node_modules/playwright/lib/client/channelOwner.js:77:34)
2021-06-01T13:43:21.934Z ? firestore-onCreate: at BrowserType.launch (/workspace/node_modules/playwright/lib/client/browserType.js:51:21)
2021-06-01T13:43:21.934Z ? firestore-onCreate: at Object.exports.getZennArticleUrlsOfMonth (/workspace/lib/blog/zenn-client.js:14:49)
2021-06-01T13:43:21.934Z ? firestore-onCreate: at /workspace/lib/firestore/blog-url-sender.js:25:46
2021-06-01T13:43:21.934Z ? firestore-onCreate: at processTicksAndRejections (internal/process/task_queues.js:97:5)
調べてみると同じような現象に遭遇している方はいて、
- 特定バージョンのchromiumをダウンロード
- 上記を使うようにパスを設定
すればOKらしいみたいだが、Functions上でどう設定するかよくわからなかったのでパス。
そこで、chromiumとPlaywrightがパッケージされたplaywright-aws-lambda
というパッケージを発見したのでこちらを利用すると上記のエラーは解消されました。なお、こちらのパッケージはREADMEをみるとわかりますが、Cloud Functionsでも使えます。
デフォルトのメモリ容量256MBだと足りないのでメモリを増やす必要がある
playwright-aws-lambdaを導入することでchromiumを起動できないというエラーは解消することができました。
ところが、今度は以下のエラーに遭遇しました。
"textPayload": "Error: memory limit exceeded. Function invocation was interrupted."
// 省略
メモリ制限に引っかかってしまいました。こちら解消するにはFunctionsのメモリを増やす必要があります。
※デフォルトだと256MBでした。
メモリを増やすにはFirebaseの管理画面上からではなく、GCPのコンソール上から設定します。
- GCPのコンソールにアクセス
- メモリを上げたいFunctionsがあるプロジェクト選択して以下の画面を開く
- 左のハンバーガメニューからを開いてCloud Functionsを選択
- メモリを増やしたい関数を選択してクリック
- 関数の詳細画面で「編集」をクリックする
- 「割り当てられるメモリ」を増やして「次へ」を選択
- 「デプロイ」を押して完了。あとは反映されるまで待つ!
恥ずかしながらメモリを増やせることを知らず、よく出入りしている「エンジニアと人生コミュニティ」で@mogaさんにヒントをもらいました!あざます!!
Discussion
ちなみにAPIをアクセス禁止にしたわけではなく、
https://api.zenn.dev/*
がhttps://zenn.dev/api/*
に変わった感じです!catnoseさん、わざわざありがとうございます!
URLが変わっていたんですね。新しいURLを見つけられず、勘違いしておりました。
記事を更新しておこうと思いますが、コメントの内容は記事にのせてしまっても大丈夫でしょうか?
大丈夫です!ただ変更先もやはり公式に提供しているものではないので、同様に今後変更される可能性があることは書いてもらえるとありがたいです。
承知しました!変更される可能性もあることも合わせて記載します!