ある顧客が、管理UIからローカルのDiscourseバックアップをアップロードする際に、再現可能な問題に遭遇しました。
バックアップアップローダーは固定の5 MBチャンクを使用しており、十分に高速な接続環境では、Discourse自体のアプリケーションレベルのリクエストレート制限を超えるほどのリクエストを生成する可能性があります。その場合、サーバーはHTTP 429を返しますが、チャンクアップローダーは429レスポンスのリトライを行わず、Retry-Afterヘッダーも尊重しません。その結果、バックアップのアップロード全体が失敗します。
非2xxレスポンスはエラーに変換されます:
if (ev.target.status < 200 || ev.target.status >= 300) {
const error = new Error("Non 2xx");
error.source = ev.target;
reject(error);
return;
}
リトライロジックは以下の通りです:
_shouldRetry(err) {
if (err.source && typeof err.source.status === "number") {
const { status } = err.source;
return (
status === 0 ||
status === 409 ||
status === 423 ||
(status >= 500 && status < 600)
);
}
return false;
}
したがって、HTTP 429は明示的にリトライ可能ではありません。
429レスポンスが1回あるだけで、チャンクアップロードのプロミスが失敗し、最終的にバックアップアップロード全体でupload-errorがトリガーされます。
また、Retry-Afterレスポンスヘッダーの処理もありません。
2021年のこのトピックを見つけましたが、かなり早く話題が逸れました。しかし、おそらくまったく同じ問題と思われます。