React Native 標準の URL は '../x' を解決しない

ウェブサイトと React Native アプリで共有するクライアントライブラリが壊れるのは、fetch ではなく、Web プラットフォームの地味な部分であることが多いです。React Native 0.87.1 と Expo 57 のソースを読むと、ランタイムが3層あること、ウェブなら ‘/b/x’ になるところを ‘/b/c/d/../x’ と返す URL クラスがあること、Expo が置き換えない限り fetch にレスポンスのストリームがないことが分かります。必要なものを確認する小さなクライアントを、4つの模擬ランタイムでテストします。

2026年9月26日 | 11 min

Durable Object のアラームは、失敗しても6回再試行して終わる

Durable Object のアラームは1つだけで、少なくとも1回実行され、失敗するハンドラーはバックオフ付きで最大6回再試行されます。それが尽きると、オブジェクトを再び起こすものは何もありません。この3つに耐えるリース失効の台帳を、コードに注釈をつけて見ていきます。真実を持つ表、アラームを再設定するコンストラクター、2回実行されても困らない副作用です。ローカルの workerd で動かし、制限は Cloudflare の文書から引用しています。

2026年9月24日 | 11 min

Durable ObjectがハイバネーションするとWebSocketは残り、クラスのフィールドは消える

CloudflareのドキュメントはWebSocket Hibernationについて、接続は維持され、メモリ上の状態は破棄される、と書いています。この記事では小さなDurable Objectをローカルのworkerdで動かし、それが具体的に何を意味するかを観察します。ソケットはOPENのまま、次のメッセージでコンストラクターが再実行され、クラスのフィールドは初期化され、アタッチメントはserializeしたものだけが残り、保留中のタイマーや標準のWebSocket APIを使うとハイバネーションがひそかに無効になります。本番の挙動や課金は試していません。

2026年9月22日 | 14 min

HTTP/2で1本がタイムアウトしたら、閉じるのは接続ではなくストリーム

たくさんのリクエストを同時に流している1本の接続で、1つのリクエストの期限が来たとき、接続ごと閉じるべきか、そのリクエストだけを閉じるべきか。小さなNodeの実験では、HTTP/2のセッションを閉じると無関係な2本が失敗し、ストリームだけをキャンセルすると同じTCP接続のまま2本とも完了しました。ただし、TCPの1パケットの遅れは接続上の全ストリームを止めます。その場合に接続の生死を確かめる方法として、PINGを使った確認も試します。

2026年9月8日 | 17 min

bufferedAmountを待っても守れるのは送信側だけで、遅い受信側は守れない

WebSocketのsend()は待ってくれず、bufferedAmountが見ているのは自分のプロセスの中の待ち行列だけです。小さな実験では、bufferedAmountが減るのを待ってから送る送信側でも、受信側のメモリには、400件のほぼ全部が溜まりました。受信側が処理済みを返す「クレジット窓」(8件)なら、溜まるのは8件で止まりました。send()、bufferedAmount、メッセージサイズ、バックプレッシャーについてよくある4つの思い込みを実際に試し、使い分けの表にまとめます。

2026年9月6日 | 14 min

リフレッシュトークンをローテーションすると、並行リクエストでログアウトされることがある

リフレッシュトークンのローテーションは、使用済みトークンの再利用を盗難の警報として扱います。期限切れのアクセストークンで3つのリクエストを同時に送り、401ごとに更新するクライアントは、同じリフレッシュトークンを3回提示して、自分で警報を鳴らします。この記事では、素朴なクライアントをあえて壊し、single-flight と stale check で直します。そのうえで、サーバー側の猶予期間、リクエストの待機、先回り更新、送信者制約付きトークンを比べます。

2026年8月30日 | 13 min

従量課金のリレーでのバッチ送信とフレーム上限

WebSocket のメッセージごとに課金され、フレームにも上限がある環境では、独立したフラッシュ条件を持つバッチ送信、上限より低い単一フレームのしきい値、上限付きの分割、混在バージョンのロールアウトを生き延びる能力フラグが必要です。難所は、終了時の順序と、ワイヤ上から消えるゼロ値です。

2026年8月19日 | 11 min