コンテンツにスキップ

バインディング (env)

バインディングを使用すると、WorkerがCloudflare Developer Platform上のリソースとインタラクションできます。

現在利用可能なバインディングは以下の通りです:

バインディングとは?

Workerでバインディングを宣言すると、特定の機能を付与します。たとえば、R2バケットにファイルを読み書きすることができるようになります。例えば:

main = "./src/index.js"
r2_buckets = [
{ binding = "MY_BUCKET", bucket_name = "<MY_BUCKET_NAME>" }
]
export default {
async fetch(request, env) {
const key = url.pathname.slice(1);
await env.MY_BUCKET.put(key, request.body);
return new Response(`Put ${key} successfully!`);
}
}

バインディングは、権限とAPIを一つにまとめたものと考えることができます。バインディングを使用すると、Cloudflareアカウントのリソースにアクセスするために、秘密鍵やトークンをWorkerに追加する必要がありません — 権限はAPI自体に埋め込まれています。基盤となる秘密はWorkerのコードに露出することはなく、したがって偶発的に漏洩することはありません。

バインディングの変更

Workerに変更をデプロイする際、バインディングのみを変更する場合(つまり、Workerのコードを変更しない場合)、Cloudflareは既に実行中のWorkerを再利用することがあります。これによりパフォーマンスが向上します — 環境変数や他のバインディングを変更しても、コードを不必要に再読み込みすることなく行えます。

そのため、バインディングの派生物でグローバルスコープを「汚染」しないように注意が必要です。そこで作成したものは、基盤となるバインディングに変更を加えても存在し続ける可能性があります。たとえば、envからアクセスされる秘密APIキーを使用する外部クライアントインスタンスがある場合:このクライアントインスタンスをグローバルスコープに置き、秘密を変更すると、元の値を使用しているクライアントインスタンスが存在し続けるかもしれません。正しいアプローチは、各リクエストごとに新しいクライアントインスタンスを作成することです。

以下は良いアプローチです:

export default {
fetch(request, env) {
let client = new Client(env.MY_SECRET); // `client`は、各リクエストごとに新しいインスタンスが構築されるため、最新の`env.MY_SECRET`の値であることが保証されます
// ... `client`を使って処理を行う
}
}

これに対して、驚くべき望ましくない動作を引き起こす可能性のある代替案:

let client = undefined;
export default {
fetch(request, env) {
client ??= new Client(env.MY_SECRET); // `client`はここで`env.MY_SECRET`が変更されても更新されない可能性があります。なぜなら、グローバルスコープに既に存在しているかもしれないからです
// ... `client`を使って処理を行う
}
}

より高度なニーズがある場合は、AsyncLocalStorage APIを探求してください。これは、子実行ハンドラに値を露出するためのメカニズムを提供します。