You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
{{ message }}
Repository navigation
oauth/xai: Retry-After is capped at 2000ms in postXaiToken, so a 429 with Retry-After: 60 retries after 2s #4045
src/oauth/xai.ts line 98 (retryDelay), on dev (blob f876b18):
returnMath.min(2000,Math.max(j,seconds*1000));
Problem
Math.min(2000, ...) wraps the server-provided Retry-After value, so any delay the token endpoint asks for is truncated to 2 seconds. Measured on Node 24 with the function extracted verbatim:
retryDelay(2, "60", () => 0.5) -> 2000
When auth.x.ai answers 429 with Retry-After: 60, postXaiToken sleeps 2s, hits 429 again, and burns all 3 attempts in ~4s instead of honoring the server. RFC 9110 §10.2.3 treats Retry-After as a value to honor, not a ceiling to clamp.
Fix
Apply the 2000ms cap to the jitter only, and honor Retry-After (with a generous absolute ceiling such as 60s to avoid pathological values):
Found while porting this module into ima2-gen (devlog 260909_grok_native_oauth/001_opencodex_port_spec.md D1). Related: the HTTP-date form of Retry-After is also ignored (separate issue).
이 이슈는 Grok(xAI) OAuth 토큰 POST가 서버가 시킨 대기 시간을 지키지 못하는 버그입니다. 지금 dev HEAD cfff026d5의 src/oauth/xai.tsretryDelay(대략 98행)는 이렇게 끝납니다.
returnMath.min(2000,Math.max(j,seconds*1000));
서버가 Retry-After: 60을 줘도 Math.min(2000, …) 때문에 항상 최대 2초만 쉽니다. 이슈가 Node 24에서 함수만 빼서 측정한 값도 retryDelay(2, "60", () => 0.5) -> 2000입니다. postXaiToken은 429/5xx에서 최대 3번 재시도하므로, 실제로는 약 4초 안에 세 번을 다 태우고 실패합니다. RFC 9110 §10.2.3는 Retry-After를 존중하라고 말하고, 지금 코드는 존중이 아니라 상한으로 잘라 버립니다.
왜 지금 큐에 올릴 만하냐면, dev는 패키지 2.49.0이고 Grok/xAI OAuth(XaiOAuthFlow / refreshXai)가 account-pool·로그인 경로에 이미 들어가 있습니다. 토큰 엔드포인트가 짧게라도 rate-limit을 걸면 로그인·리프레시가 “네트워크/토큰 요청 실패”로 보이기 쉽습니다. 같은 파일의 HTTP-date 파싱 구멍(#4046)과 abort 재시도 구멍(#4047)과 한 묶음으로 고치는 편이 싸습니다. types.ts/config.ts 분할과는 무관합니다.
제안 수정은 명확합니다. 서버가 준 초 단위 값은 그대로(다만 60초 같은 절대 천장) 쓰고, 2000ms 캡은 지터 폴백에만 적용합니다.
Activity
lidge-jun commentedon Sep 8, 2026
리뷰 · 우선순위 62 / 80
이 이슈는 Grok(xAI) OAuth 토큰 POST가 서버가 시킨 대기 시간을 지키지 못하는 버그입니다. 지금
devHEAD cfff026d5의src/oauth/xai.tsretryDelay(대략 98행)는 이렇게 끝납니다.서버가
Retry-After: 60을 줘도Math.min(2000, …)때문에 항상 최대 2초만 쉽니다. 이슈가 Node 24에서 함수만 빼서 측정한 값도retryDelay(2, "60", () => 0.5) -> 2000입니다.postXaiToken은 429/5xx에서 최대 3번 재시도하므로, 실제로는 약 4초 안에 세 번을 다 태우고 실패합니다. RFC 9110 §10.2.3는Retry-After를 존중하라고 말하고, 지금 코드는 존중이 아니라 상한으로 잘라 버립니다.왜 지금 큐에 올릴 만하냐면,
dev는 패키지 2.49.0이고 Grok/xAI OAuth(XaiOAuthFlow/refreshXai)가 account-pool·로그인 경로에 이미 들어가 있습니다. 토큰 엔드포인트가 짧게라도 rate-limit을 걸면 로그인·리프레시가 “네트워크/토큰 요청 실패”로 보이기 쉽습니다. 같은 파일의 HTTP-date 파싱 구멍(#4046)과 abort 재시도 구멍(#4047)과 한 묶음으로 고치는 편이 싸습니다. types.ts/config.ts 분할과는 무관합니다.제안 수정은 명확합니다. 서버가 준 초 단위 값은 그대로(다만 60초 같은 절대 천장) 쓰고, 2000ms 캡은 지터 폴백에만 적용합니다.
라인 98 · retryDelay -
Math.min(2000, Math.max(j, seconds*1000))가 Retry-After를 2초로 자릅니다. 측정값과 코드가 일치합니다.경로 postXaiToken 재시도 루프 - 429마다 짧은 sleep만 하니 서버 의도(60초)와 클라이언트 행동(2초×N)이 어긋납니다. 사용자에게는 간헐적 Grok 로그인 실패로 보입니다.
경로 테스트 - 이슈 본문의
retryDelay(1,"60")단위 테스트만 있어도 회귀를 막을 수 있습니다. 지금은 공개 테스트가 안 보입니다.메인테이너의 판단이 필요한 지점
너의 추천
수락하세요.
help wanted로 두되 우선은 중간 이상입니다. 가능하면 #4046과 같은retryDelayPR에 넣고, 단위 테스트 한 줄을 같이 받으세요. close-don't-rebase 대상이 아닙니다.이 댓글은 grok-bot이 작성했습니다
lidge-jun commentedon Sep 9, 2026
Fixed on
devvia #4087 at 4a08c75.devlog: plan the xAI OAuth retry hardening unit (lidge-jun#4045, lidg…
oauth/xai: honor Retry-After and stop retrying aborted token requests (…
docs(grok): docs-first roadmap for native xAI OAuth, replacing the pr…
devlog: plan the xAI OAuth retry hardening unit (lidge-jun#4045, lidg…
oauth/xai: honor Retry-After and stop retrying aborted token requests (…