POSTリクエストのキャッシュ
Cache POSTリクエストをCache APIを使用してキャッシュします。
export default { async fetch(request, env, ctx) { async function sha256(message) { // UTF-8としてエンコード const msgBuffer = await new TextEncoder().encode(message); // メッセージをハッシュ化 const hashBuffer = await crypto.subtle.digest("SHA-256", msgBuffer); // バイトを16進数文字列に変換 return [...new Uint8Array(hashBuffer)] .map((b) => b.toString(16).padStart(2, "0")) .join(""); } try { if (request.method.toUpperCase() === "POST") { const body = await request.clone().text(); // キャッシュキーの一部としてリクエストボディをハッシュ化 const hash = await sha256(body); const cacheUrl = new URL(request.url); // ボディのハッシュを前に付けてURLをキャッシュに保存 cacheUrl.pathname = "/posts" + cacheUrl.pathname + hash; // キャッシュ可能にするためにGETに変換 const cacheKey = new Request(cacheUrl.toString(), { headers: request.headers, method: "GET", });
const cache = caches.default; // キャッシュ内でキャッシュキーを探す let response = await cache.match(cacheKey); // そうでなければ、オリジンからPOSTリクエストのレスポンスを取得 if (!response) { response = await fetch(request); ctx.waitUntil(cache.put(cacheKey, response.clone())); } return response; } return fetch(request); } catch (e) { return new Response("エラーが発生しました " + e.message); } },};interface Env {}export default { async fetch(request, env, ctx): Promise<Response> { async function sha256(message) { // UTF-8としてエンコード const msgBuffer = await new TextEncoder().encode(message); // メッセージをハッシュ化 const hashBuffer = await crypto.subtle.digest("SHA-256", msgBuffer); // バイトを16進数文字列に変換 return [...new Uint8Array(hashBuffer)] .map((b) => b.toString(16).padStart(2, "0")) .join(""); } try { if (request.method.toUpperCase() === "POST") { const body = await request.clone().text(); // キャッシュキーの一部としてリクエストボディをハッシュ化 const hash = await sha256(body); const cacheUrl = new URL(request.url); // ボディのハッシュを前に付けてURLをキャッシュに保存 cacheUrl.pathname = "/posts" + cacheUrl.pathname + hash; // キャッシュ可能にするためにGETに変換 const cacheKey = new Request(cacheUrl.toString(), { headers: request.headers, method: "GET", });
const cache = caches.default; // キャッシュ内でキャッシュキーを探す let response = await cache.match(cacheKey); // そうでなければ、オリジンからPOSTリクエストのレスポンスを取得 if (!response) { response = await fetch(request); ctx.waitUntil(cache.put(cacheKey, response.clone())); } return response; } return fetch(request); } catch (e) { return new Response("エラーが発生しました " + e.message); } },} satisfies ExportedHandler<Env>;import hashlibfrom pyodide.ffi import create_proxyfrom js import fetch, URL, Headers, Request, caches
async def on_fetch(request, _, ctx): if 'POST' in request.method: # キャッシュキーの一部としてリクエストボディをハッシュ化 body = await request.clone().text() body_hash = hashlib.sha256(body.encode('UTF-8')).hexdigest()
# ボディのハッシュを前に付けてURLをキャッシュに保存 cache_url = URL.new(request.url) cache_url.pathname = "/posts" + cache_url.pathname + body_hash
# キャッシュ可能にするためにGETに変換 headers = Headers.new(dict(request.headers).items()) cache_key = Request.new(cache_url.toString(), method='GET', headers=headers)
# キャッシュ内でキャッシュキーを探す cache = caches.default response = await cache.match(cache_key)
# そうでなければ、オリジンからPOSTリクエストのレスポンスを取得 if response is None: response = await fetch(request) ctx.waitUntil(create_proxy(cache.put(cache_key, response.clone())))
return response
return fetch(request)