zevairouter 1.0.150 → 1.0.152

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (344) hide show
  1. package/CHANGELOG.md +13 -0
  2. package/cli/app/.next-cli-build/BUILD_ID +1 -1
  3. package/cli/app/.next-cli-build/app-path-routes-manifest.json +7 -7
  4. package/cli/app/.next-cli-build/build-manifest.json +2 -2
  5. package/cli/app/.next-cli-build/server/app/(dashboard)/dashboard/automation/page_client-reference-manifest.js +1 -1
  6. package/cli/app/.next-cli-build/server/app/(dashboard)/dashboard/basic-chat/page_client-reference-manifest.js +1 -1
  7. package/cli/app/.next-cli-build/server/app/(dashboard)/dashboard/cli-tools/[toolId]/page_client-reference-manifest.js +1 -1
  8. package/cli/app/.next-cli-build/server/app/(dashboard)/dashboard/cli-tools/page_client-reference-manifest.js +1 -1
  9. package/cli/app/.next-cli-build/server/app/(dashboard)/dashboard/combos/page_client-reference-manifest.js +1 -1
  10. package/cli/app/.next-cli-build/server/app/(dashboard)/dashboard/console-log/page_client-reference-manifest.js +1 -1
  11. package/cli/app/.next-cli-build/server/app/(dashboard)/dashboard/context/page_client-reference-manifest.js +1 -1
  12. package/cli/app/.next-cli-build/server/app/(dashboard)/dashboard/endpoint/page_client-reference-manifest.js +1 -1
  13. package/cli/app/.next-cli-build/server/app/(dashboard)/dashboard/media-providers/[kind]/[id]/page_client-reference-manifest.js +1 -1
  14. package/cli/app/.next-cli-build/server/app/(dashboard)/dashboard/media-providers/[kind]/page_client-reference-manifest.js +1 -1
  15. package/cli/app/.next-cli-build/server/app/(dashboard)/dashboard/media-providers/combo/[id]/page_client-reference-manifest.js +1 -1
  16. package/cli/app/.next-cli-build/server/app/(dashboard)/dashboard/media-providers/web/page_client-reference-manifest.js +1 -1
  17. package/cli/app/.next-cli-build/server/app/(dashboard)/dashboard/mitm/page_client-reference-manifest.js +1 -1
  18. package/cli/app/.next-cli-build/server/app/(dashboard)/dashboard/page_client-reference-manifest.js +1 -1
  19. package/cli/app/.next-cli-build/server/app/(dashboard)/dashboard/playground/page_client-reference-manifest.js +1 -1
  20. package/cli/app/.next-cli-build/server/app/(dashboard)/dashboard/profile/page_client-reference-manifest.js +1 -1
  21. package/cli/app/.next-cli-build/server/app/(dashboard)/dashboard/providers/[id]/page_client-reference-manifest.js +1 -1
  22. package/cli/app/.next-cli-build/server/app/(dashboard)/dashboard/providers/new/page_client-reference-manifest.js +1 -1
  23. package/cli/app/.next-cli-build/server/app/(dashboard)/dashboard/providers/page_client-reference-manifest.js +1 -1
  24. package/cli/app/.next-cli-build/server/app/(dashboard)/dashboard/proxy-pools/page_client-reference-manifest.js +1 -1
  25. package/cli/app/.next-cli-build/server/app/(dashboard)/dashboard/pxpipe/page_client-reference-manifest.js +1 -1
  26. package/cli/app/.next-cli-build/server/app/(dashboard)/dashboard/quota/page_client-reference-manifest.js +1 -1
  27. package/cli/app/.next-cli-build/server/app/(dashboard)/dashboard/terminal/page_client-reference-manifest.js +1 -1
  28. package/cli/app/.next-cli-build/server/app/(dashboard)/dashboard/token-saver/page_client-reference-manifest.js +1 -1
  29. package/cli/app/.next-cli-build/server/app/(dashboard)/dashboard/translator/page_client-reference-manifest.js +1 -1
  30. package/cli/app/.next-cli-build/server/app/(dashboard)/dashboard/usage/page_client-reference-manifest.js +1 -1
  31. package/cli/app/.next-cli-build/server/app/_global-error/page_client-reference-manifest.js +1 -1
  32. package/cli/app/.next-cli-build/server/app/_global-error.html +1 -1
  33. package/cli/app/.next-cli-build/server/app/_global-error.rsc +1 -1
  34. package/cli/app/.next-cli-build/server/app/_global-error.segments/_full.segment.rsc +1 -1
  35. package/cli/app/.next-cli-build/server/app/_global-error.segments/_global-error/__PAGE__.segment.rsc +1 -1
  36. package/cli/app/.next-cli-build/server/app/_global-error.segments/_global-error.segment.rsc +1 -1
  37. package/cli/app/.next-cli-build/server/app/_global-error.segments/_head.segment.rsc +1 -1
  38. package/cli/app/.next-cli-build/server/app/_global-error.segments/_index.segment.rsc +1 -1
  39. package/cli/app/.next-cli-build/server/app/_global-error.segments/_tree.segment.rsc +1 -1
  40. package/cli/app/.next-cli-build/server/app/_not-found/page_client-reference-manifest.js +1 -1
  41. package/cli/app/.next-cli-build/server/app/_not-found.html +1 -1
  42. package/cli/app/.next-cli-build/server/app/_not-found.rsc +3 -3
  43. package/cli/app/.next-cli-build/server/app/_not-found.segments/_full.segment.rsc +3 -3
  44. package/cli/app/.next-cli-build/server/app/_not-found.segments/_head.segment.rsc +1 -1
  45. package/cli/app/.next-cli-build/server/app/_not-found.segments/_index.segment.rsc +3 -3
  46. package/cli/app/.next-cli-build/server/app/_not-found.segments/_not-found/__PAGE__.segment.rsc +1 -1
  47. package/cli/app/.next-cli-build/server/app/_not-found.segments/_not-found.segment.rsc +1 -1
  48. package/cli/app/.next-cli-build/server/app/_not-found.segments/_tree.segment.rsc +1 -1
  49. package/cli/app/.next-cli-build/server/app/api/combos/[id]/route.js +1 -1
  50. package/cli/app/.next-cli-build/server/app/api/models/route.js +1 -1
  51. package/cli/app/.next-cli-build/server/app/api/oauth/cloudflare-ai/bulk-import/[jobId]/cancel/route.js +1 -1
  52. package/cli/app/.next-cli-build/server/app/api/oauth/cloudflare-ai/bulk-import/[jobId]/manual/[workerId]/route.js +1 -1
  53. package/cli/app/.next-cli-build/server/app/api/oauth/cloudflare-ai/bulk-import/[jobId]/route.js +1 -1
  54. package/cli/app/.next-cli-build/server/app/api/oauth/cloudflare-ai/bulk-import/latest/route.js +1 -1
  55. package/cli/app/.next-cli-build/server/app/api/oauth/cloudflare-ai/bulk-import/route.js +1 -1
  56. package/cli/app/.next-cli-build/server/app/api/oauth/kiro/bulk-import/[jobId]/cancel/route.js +1 -1
  57. package/cli/app/.next-cli-build/server/app/api/oauth/kiro/bulk-import/[jobId]/manual/[workerId]/route.js +1 -1
  58. package/cli/app/.next-cli-build/server/app/api/oauth/kiro/bulk-import/[jobId]/route.js +1 -1
  59. package/cli/app/.next-cli-build/server/app/api/oauth/kiro/bulk-import/latest/route.js +1 -1
  60. package/cli/app/.next-cli-build/server/app/api/oauth/kiro/bulk-import/route.js +1 -1
  61. package/cli/app/.next-cli-build/server/app/api/oauth/kiro/import/route.js +1 -1
  62. package/cli/app/.next-cli-build/server/app/api/oauth/qoder/bulk-import/[jobId]/cancel/route.js +1 -1
  63. package/cli/app/.next-cli-build/server/app/api/oauth/qoder/bulk-import/[jobId]/manual/[workerId]/route.js +1 -1
  64. package/cli/app/.next-cli-build/server/app/api/oauth/qoder/bulk-import/[jobId]/route.js +1 -1
  65. package/cli/app/.next-cli-build/server/app/api/oauth/qoder/bulk-import/latest/route.js +1 -1
  66. package/cli/app/.next-cli-build/server/app/api/oauth/qoder/bulk-import/route.js +1 -1
  67. package/cli/app/.next-cli-build/server/app/api/providers/route.js +1 -1
  68. package/cli/app/.next-cli-build/server/app/api/providers/validate/route.js +1 -1
  69. package/cli/app/.next-cli-build/server/app/api/settings/route.js +1 -1
  70. package/cli/app/.next-cli-build/server/app/api/translator/console-logs/route.js +1 -1
  71. package/cli/app/.next-cli-build/server/app/api/translator/console-logs/stream/route.js +1 -1
  72. package/cli/app/.next-cli-build/server/app/api/v1/audio/speech/route.js +1 -1
  73. package/cli/app/.next-cli-build/server/app/api/v1/audio/transcriptions/route.js +1 -1
  74. package/cli/app/.next-cli-build/server/app/api/v1/embeddings/route.js +1 -1
  75. package/cli/app/.next-cli-build/server/app/api/v1/images/generations/route.js +1 -1
  76. package/cli/app/.next-cli-build/server/app/api/v1/search/route.js +1 -1
  77. package/cli/app/.next-cli-build/server/app/api/v1/web/fetch/route.js +1 -1
  78. package/cli/app/.next-cli-build/server/app/api/version/route.js +1 -1
  79. package/cli/app/.next-cli-build/server/app/api/version/shutdown/route.js +1 -1
  80. package/cli/app/.next-cli-build/server/app/api/version/update/route.js +1 -1
  81. package/cli/app/.next-cli-build/server/app/callback/page_client-reference-manifest.js +1 -1
  82. package/cli/app/.next-cli-build/server/app/callback.html +1 -1
  83. package/cli/app/.next-cli-build/server/app/callback.rsc +3 -3
  84. package/cli/app/.next-cli-build/server/app/callback.segments/_full.segment.rsc +3 -3
  85. package/cli/app/.next-cli-build/server/app/callback.segments/_head.segment.rsc +1 -1
  86. package/cli/app/.next-cli-build/server/app/callback.segments/_index.segment.rsc +3 -3
  87. package/cli/app/.next-cli-build/server/app/callback.segments/_tree.segment.rsc +1 -1
  88. package/cli/app/.next-cli-build/server/app/callback.segments/callback/__PAGE__.segment.rsc +1 -1
  89. package/cli/app/.next-cli-build/server/app/callback.segments/callback.segment.rsc +1 -1
  90. package/cli/app/.next-cli-build/server/app/dashboard/automation.html +1 -1
  91. package/cli/app/.next-cli-build/server/app/dashboard/automation.rsc +5 -5
  92. package/cli/app/.next-cli-build/server/app/dashboard/automation.segments/!KGRhc2hib2FyZCk/dashboard/automation/__PAGE__.segment.rsc +2 -2
  93. package/cli/app/.next-cli-build/server/app/dashboard/automation.segments/!KGRhc2hib2FyZCk/dashboard/automation.segment.rsc +1 -1
  94. package/cli/app/.next-cli-build/server/app/dashboard/automation.segments/!KGRhc2hib2FyZCk/dashboard.segment.rsc +1 -1
  95. package/cli/app/.next-cli-build/server/app/dashboard/automation.segments/!KGRhc2hib2FyZCk.segment.rsc +2 -2
  96. package/cli/app/.next-cli-build/server/app/dashboard/automation.segments/_full.segment.rsc +5 -5
  97. package/cli/app/.next-cli-build/server/app/dashboard/automation.segments/_head.segment.rsc +1 -1
  98. package/cli/app/.next-cli-build/server/app/dashboard/automation.segments/_index.segment.rsc +3 -3
  99. package/cli/app/.next-cli-build/server/app/dashboard/automation.segments/_tree.segment.rsc +1 -1
  100. package/cli/app/.next-cli-build/server/app/dashboard/basic-chat.html +1 -1
  101. package/cli/app/.next-cli-build/server/app/dashboard/basic-chat.rsc +5 -5
  102. package/cli/app/.next-cli-build/server/app/dashboard/basic-chat.segments/!KGRhc2hib2FyZCk/dashboard/basic-chat/__PAGE__.segment.rsc +2 -2
  103. package/cli/app/.next-cli-build/server/app/dashboard/basic-chat.segments/!KGRhc2hib2FyZCk/dashboard/basic-chat.segment.rsc +1 -1
  104. package/cli/app/.next-cli-build/server/app/dashboard/basic-chat.segments/!KGRhc2hib2FyZCk/dashboard.segment.rsc +1 -1
  105. package/cli/app/.next-cli-build/server/app/dashboard/basic-chat.segments/!KGRhc2hib2FyZCk.segment.rsc +2 -2
  106. package/cli/app/.next-cli-build/server/app/dashboard/basic-chat.segments/_full.segment.rsc +5 -5
  107. package/cli/app/.next-cli-build/server/app/dashboard/basic-chat.segments/_head.segment.rsc +1 -1
  108. package/cli/app/.next-cli-build/server/app/dashboard/basic-chat.segments/_index.segment.rsc +3 -3
  109. package/cli/app/.next-cli-build/server/app/dashboard/basic-chat.segments/_tree.segment.rsc +1 -1
  110. package/cli/app/.next-cli-build/server/app/dashboard/cli-tools.html +1 -1
  111. package/cli/app/.next-cli-build/server/app/dashboard/cli-tools.rsc +5 -5
  112. package/cli/app/.next-cli-build/server/app/dashboard/cli-tools.segments/!KGRhc2hib2FyZCk/dashboard/cli-tools/__PAGE__.segment.rsc +2 -2
  113. package/cli/app/.next-cli-build/server/app/dashboard/cli-tools.segments/!KGRhc2hib2FyZCk/dashboard/cli-tools.segment.rsc +1 -1
  114. package/cli/app/.next-cli-build/server/app/dashboard/cli-tools.segments/!KGRhc2hib2FyZCk/dashboard.segment.rsc +1 -1
  115. package/cli/app/.next-cli-build/server/app/dashboard/cli-tools.segments/!KGRhc2hib2FyZCk.segment.rsc +2 -2
  116. package/cli/app/.next-cli-build/server/app/dashboard/cli-tools.segments/_full.segment.rsc +5 -5
  117. package/cli/app/.next-cli-build/server/app/dashboard/cli-tools.segments/_head.segment.rsc +1 -1
  118. package/cli/app/.next-cli-build/server/app/dashboard/cli-tools.segments/_index.segment.rsc +3 -3
  119. package/cli/app/.next-cli-build/server/app/dashboard/cli-tools.segments/_tree.segment.rsc +1 -1
  120. package/cli/app/.next-cli-build/server/app/dashboard/combos.html +1 -1
  121. package/cli/app/.next-cli-build/server/app/dashboard/combos.rsc +5 -5
  122. package/cli/app/.next-cli-build/server/app/dashboard/combos.segments/!KGRhc2hib2FyZCk/dashboard/combos/__PAGE__.segment.rsc +2 -2
  123. package/cli/app/.next-cli-build/server/app/dashboard/combos.segments/!KGRhc2hib2FyZCk/dashboard/combos.segment.rsc +1 -1
  124. package/cli/app/.next-cli-build/server/app/dashboard/combos.segments/!KGRhc2hib2FyZCk/dashboard.segment.rsc +1 -1
  125. package/cli/app/.next-cli-build/server/app/dashboard/combos.segments/!KGRhc2hib2FyZCk.segment.rsc +2 -2
  126. package/cli/app/.next-cli-build/server/app/dashboard/combos.segments/_full.segment.rsc +5 -5
  127. package/cli/app/.next-cli-build/server/app/dashboard/combos.segments/_head.segment.rsc +1 -1
  128. package/cli/app/.next-cli-build/server/app/dashboard/combos.segments/_index.segment.rsc +3 -3
  129. package/cli/app/.next-cli-build/server/app/dashboard/combos.segments/_tree.segment.rsc +1 -1
  130. package/cli/app/.next-cli-build/server/app/dashboard/context.html +1 -1
  131. package/cli/app/.next-cli-build/server/app/dashboard/context.rsc +5 -5
  132. package/cli/app/.next-cli-build/server/app/dashboard/context.segments/!KGRhc2hib2FyZCk/dashboard/context/__PAGE__.segment.rsc +2 -2
  133. package/cli/app/.next-cli-build/server/app/dashboard/context.segments/!KGRhc2hib2FyZCk/dashboard/context.segment.rsc +1 -1
  134. package/cli/app/.next-cli-build/server/app/dashboard/context.segments/!KGRhc2hib2FyZCk/dashboard.segment.rsc +1 -1
  135. package/cli/app/.next-cli-build/server/app/dashboard/context.segments/!KGRhc2hib2FyZCk.segment.rsc +2 -2
  136. package/cli/app/.next-cli-build/server/app/dashboard/context.segments/_full.segment.rsc +5 -5
  137. package/cli/app/.next-cli-build/server/app/dashboard/context.segments/_head.segment.rsc +1 -1
  138. package/cli/app/.next-cli-build/server/app/dashboard/context.segments/_index.segment.rsc +3 -3
  139. package/cli/app/.next-cli-build/server/app/dashboard/context.segments/_tree.segment.rsc +1 -1
  140. package/cli/app/.next-cli-build/server/app/dashboard/endpoint.html +1 -1
  141. package/cli/app/.next-cli-build/server/app/dashboard/endpoint.rsc +5 -5
  142. package/cli/app/.next-cli-build/server/app/dashboard/endpoint.segments/!KGRhc2hib2FyZCk/dashboard/endpoint/__PAGE__.segment.rsc +2 -2
  143. package/cli/app/.next-cli-build/server/app/dashboard/endpoint.segments/!KGRhc2hib2FyZCk/dashboard/endpoint.segment.rsc +1 -1
  144. package/cli/app/.next-cli-build/server/app/dashboard/endpoint.segments/!KGRhc2hib2FyZCk/dashboard.segment.rsc +1 -1
  145. package/cli/app/.next-cli-build/server/app/dashboard/endpoint.segments/!KGRhc2hib2FyZCk.segment.rsc +2 -2
  146. package/cli/app/.next-cli-build/server/app/dashboard/endpoint.segments/_full.segment.rsc +5 -5
  147. package/cli/app/.next-cli-build/server/app/dashboard/endpoint.segments/_head.segment.rsc +1 -1
  148. package/cli/app/.next-cli-build/server/app/dashboard/endpoint.segments/_index.segment.rsc +3 -3
  149. package/cli/app/.next-cli-build/server/app/dashboard/endpoint.segments/_tree.segment.rsc +1 -1
  150. package/cli/app/.next-cli-build/server/app/dashboard/media-providers/web.html +1 -1
  151. package/cli/app/.next-cli-build/server/app/dashboard/media-providers/web.rsc +5 -5
  152. package/cli/app/.next-cli-build/server/app/dashboard/media-providers/web.segments/!KGRhc2hib2FyZCk/dashboard/media-providers/web/__PAGE__.segment.rsc +2 -2
  153. package/cli/app/.next-cli-build/server/app/dashboard/media-providers/web.segments/!KGRhc2hib2FyZCk/dashboard/media-providers/web.segment.rsc +1 -1
  154. package/cli/app/.next-cli-build/server/app/dashboard/media-providers/web.segments/!KGRhc2hib2FyZCk/dashboard/media-providers.segment.rsc +1 -1
  155. package/cli/app/.next-cli-build/server/app/dashboard/media-providers/web.segments/!KGRhc2hib2FyZCk/dashboard.segment.rsc +1 -1
  156. package/cli/app/.next-cli-build/server/app/dashboard/media-providers/web.segments/!KGRhc2hib2FyZCk.segment.rsc +2 -2
  157. package/cli/app/.next-cli-build/server/app/dashboard/media-providers/web.segments/_full.segment.rsc +5 -5
  158. package/cli/app/.next-cli-build/server/app/dashboard/media-providers/web.segments/_head.segment.rsc +1 -1
  159. package/cli/app/.next-cli-build/server/app/dashboard/media-providers/web.segments/_index.segment.rsc +3 -3
  160. package/cli/app/.next-cli-build/server/app/dashboard/media-providers/web.segments/_tree.segment.rsc +1 -1
  161. package/cli/app/.next-cli-build/server/app/dashboard/mitm.html +1 -1
  162. package/cli/app/.next-cli-build/server/app/dashboard/mitm.rsc +5 -5
  163. package/cli/app/.next-cli-build/server/app/dashboard/mitm.segments/!KGRhc2hib2FyZCk/dashboard/mitm/__PAGE__.segment.rsc +2 -2
  164. package/cli/app/.next-cli-build/server/app/dashboard/mitm.segments/!KGRhc2hib2FyZCk/dashboard/mitm.segment.rsc +1 -1
  165. package/cli/app/.next-cli-build/server/app/dashboard/mitm.segments/!KGRhc2hib2FyZCk/dashboard.segment.rsc +1 -1
  166. package/cli/app/.next-cli-build/server/app/dashboard/mitm.segments/!KGRhc2hib2FyZCk.segment.rsc +2 -2
  167. package/cli/app/.next-cli-build/server/app/dashboard/mitm.segments/_full.segment.rsc +5 -5
  168. package/cli/app/.next-cli-build/server/app/dashboard/mitm.segments/_head.segment.rsc +1 -1
  169. package/cli/app/.next-cli-build/server/app/dashboard/mitm.segments/_index.segment.rsc +3 -3
  170. package/cli/app/.next-cli-build/server/app/dashboard/mitm.segments/_tree.segment.rsc +1 -1
  171. package/cli/app/.next-cli-build/server/app/dashboard/playground.html +1 -1
  172. package/cli/app/.next-cli-build/server/app/dashboard/playground.rsc +5 -5
  173. package/cli/app/.next-cli-build/server/app/dashboard/playground.segments/!KGRhc2hib2FyZCk/dashboard/playground/__PAGE__.segment.rsc +2 -2
  174. package/cli/app/.next-cli-build/server/app/dashboard/playground.segments/!KGRhc2hib2FyZCk/dashboard/playground.segment.rsc +1 -1
  175. package/cli/app/.next-cli-build/server/app/dashboard/playground.segments/!KGRhc2hib2FyZCk/dashboard.segment.rsc +1 -1
  176. package/cli/app/.next-cli-build/server/app/dashboard/playground.segments/!KGRhc2hib2FyZCk.segment.rsc +2 -2
  177. package/cli/app/.next-cli-build/server/app/dashboard/playground.segments/_full.segment.rsc +5 -5
  178. package/cli/app/.next-cli-build/server/app/dashboard/playground.segments/_head.segment.rsc +1 -1
  179. package/cli/app/.next-cli-build/server/app/dashboard/playground.segments/_index.segment.rsc +3 -3
  180. package/cli/app/.next-cli-build/server/app/dashboard/playground.segments/_tree.segment.rsc +1 -1
  181. package/cli/app/.next-cli-build/server/app/dashboard/profile.html +1 -1
  182. package/cli/app/.next-cli-build/server/app/dashboard/profile.rsc +5 -5
  183. package/cli/app/.next-cli-build/server/app/dashboard/profile.segments/!KGRhc2hib2FyZCk/dashboard/profile/__PAGE__.segment.rsc +2 -2
  184. package/cli/app/.next-cli-build/server/app/dashboard/profile.segments/!KGRhc2hib2FyZCk/dashboard/profile.segment.rsc +1 -1
  185. package/cli/app/.next-cli-build/server/app/dashboard/profile.segments/!KGRhc2hib2FyZCk/dashboard.segment.rsc +1 -1
  186. package/cli/app/.next-cli-build/server/app/dashboard/profile.segments/!KGRhc2hib2FyZCk.segment.rsc +2 -2
  187. package/cli/app/.next-cli-build/server/app/dashboard/profile.segments/_full.segment.rsc +5 -5
  188. package/cli/app/.next-cli-build/server/app/dashboard/profile.segments/_head.segment.rsc +1 -1
  189. package/cli/app/.next-cli-build/server/app/dashboard/profile.segments/_index.segment.rsc +3 -3
  190. package/cli/app/.next-cli-build/server/app/dashboard/profile.segments/_tree.segment.rsc +1 -1
  191. package/cli/app/.next-cli-build/server/app/dashboard/providers/new.html +1 -1
  192. package/cli/app/.next-cli-build/server/app/dashboard/providers/new.rsc +5 -5
  193. package/cli/app/.next-cli-build/server/app/dashboard/providers/new.segments/!KGRhc2hib2FyZCk/dashboard/providers/new/__PAGE__.segment.rsc +2 -2
  194. package/cli/app/.next-cli-build/server/app/dashboard/providers/new.segments/!KGRhc2hib2FyZCk/dashboard/providers/new.segment.rsc +1 -1
  195. package/cli/app/.next-cli-build/server/app/dashboard/providers/new.segments/!KGRhc2hib2FyZCk/dashboard/providers.segment.rsc +1 -1
  196. package/cli/app/.next-cli-build/server/app/dashboard/providers/new.segments/!KGRhc2hib2FyZCk/dashboard.segment.rsc +1 -1
  197. package/cli/app/.next-cli-build/server/app/dashboard/providers/new.segments/!KGRhc2hib2FyZCk.segment.rsc +2 -2
  198. package/cli/app/.next-cli-build/server/app/dashboard/providers/new.segments/_full.segment.rsc +5 -5
  199. package/cli/app/.next-cli-build/server/app/dashboard/providers/new.segments/_head.segment.rsc +1 -1
  200. package/cli/app/.next-cli-build/server/app/dashboard/providers/new.segments/_index.segment.rsc +3 -3
  201. package/cli/app/.next-cli-build/server/app/dashboard/providers/new.segments/_tree.segment.rsc +1 -1
  202. package/cli/app/.next-cli-build/server/app/dashboard/providers.html +1 -1
  203. package/cli/app/.next-cli-build/server/app/dashboard/providers.rsc +5 -5
  204. package/cli/app/.next-cli-build/server/app/dashboard/providers.segments/!KGRhc2hib2FyZCk/dashboard/providers/__PAGE__.segment.rsc +2 -2
  205. package/cli/app/.next-cli-build/server/app/dashboard/providers.segments/!KGRhc2hib2FyZCk/dashboard/providers.segment.rsc +1 -1
  206. package/cli/app/.next-cli-build/server/app/dashboard/providers.segments/!KGRhc2hib2FyZCk/dashboard.segment.rsc +1 -1
  207. package/cli/app/.next-cli-build/server/app/dashboard/providers.segments/!KGRhc2hib2FyZCk.segment.rsc +2 -2
  208. package/cli/app/.next-cli-build/server/app/dashboard/providers.segments/_full.segment.rsc +5 -5
  209. package/cli/app/.next-cli-build/server/app/dashboard/providers.segments/_head.segment.rsc +1 -1
  210. package/cli/app/.next-cli-build/server/app/dashboard/providers.segments/_index.segment.rsc +3 -3
  211. package/cli/app/.next-cli-build/server/app/dashboard/providers.segments/_tree.segment.rsc +1 -1
  212. package/cli/app/.next-cli-build/server/app/dashboard/proxy-pools.html +1 -1
  213. package/cli/app/.next-cli-build/server/app/dashboard/proxy-pools.rsc +5 -5
  214. package/cli/app/.next-cli-build/server/app/dashboard/proxy-pools.segments/!KGRhc2hib2FyZCk/dashboard/proxy-pools/__PAGE__.segment.rsc +2 -2
  215. package/cli/app/.next-cli-build/server/app/dashboard/proxy-pools.segments/!KGRhc2hib2FyZCk/dashboard/proxy-pools.segment.rsc +1 -1
  216. package/cli/app/.next-cli-build/server/app/dashboard/proxy-pools.segments/!KGRhc2hib2FyZCk/dashboard.segment.rsc +1 -1
  217. package/cli/app/.next-cli-build/server/app/dashboard/proxy-pools.segments/!KGRhc2hib2FyZCk.segment.rsc +2 -2
  218. package/cli/app/.next-cli-build/server/app/dashboard/proxy-pools.segments/_full.segment.rsc +5 -5
  219. package/cli/app/.next-cli-build/server/app/dashboard/proxy-pools.segments/_head.segment.rsc +1 -1
  220. package/cli/app/.next-cli-build/server/app/dashboard/proxy-pools.segments/_index.segment.rsc +3 -3
  221. package/cli/app/.next-cli-build/server/app/dashboard/proxy-pools.segments/_tree.segment.rsc +1 -1
  222. package/cli/app/.next-cli-build/server/app/dashboard/pxpipe.html +1 -1
  223. package/cli/app/.next-cli-build/server/app/dashboard/pxpipe.rsc +5 -5
  224. package/cli/app/.next-cli-build/server/app/dashboard/pxpipe.segments/!KGRhc2hib2FyZCk/dashboard/pxpipe/__PAGE__.segment.rsc +2 -2
  225. package/cli/app/.next-cli-build/server/app/dashboard/pxpipe.segments/!KGRhc2hib2FyZCk/dashboard/pxpipe.segment.rsc +1 -1
  226. package/cli/app/.next-cli-build/server/app/dashboard/pxpipe.segments/!KGRhc2hib2FyZCk/dashboard.segment.rsc +1 -1
  227. package/cli/app/.next-cli-build/server/app/dashboard/pxpipe.segments/!KGRhc2hib2FyZCk.segment.rsc +2 -2
  228. package/cli/app/.next-cli-build/server/app/dashboard/pxpipe.segments/_full.segment.rsc +5 -5
  229. package/cli/app/.next-cli-build/server/app/dashboard/pxpipe.segments/_head.segment.rsc +1 -1
  230. package/cli/app/.next-cli-build/server/app/dashboard/pxpipe.segments/_index.segment.rsc +3 -3
  231. package/cli/app/.next-cli-build/server/app/dashboard/pxpipe.segments/_tree.segment.rsc +1 -1
  232. package/cli/app/.next-cli-build/server/app/dashboard/quota.html +2 -2
  233. package/cli/app/.next-cli-build/server/app/dashboard/quota.rsc +6 -6
  234. package/cli/app/.next-cli-build/server/app/dashboard/quota.segments/!KGRhc2hib2FyZCk/dashboard/quota/__PAGE__.segment.rsc +3 -3
  235. package/cli/app/.next-cli-build/server/app/dashboard/quota.segments/!KGRhc2hib2FyZCk/dashboard/quota.segment.rsc +1 -1
  236. package/cli/app/.next-cli-build/server/app/dashboard/quota.segments/!KGRhc2hib2FyZCk/dashboard.segment.rsc +1 -1
  237. package/cli/app/.next-cli-build/server/app/dashboard/quota.segments/!KGRhc2hib2FyZCk.segment.rsc +2 -2
  238. package/cli/app/.next-cli-build/server/app/dashboard/quota.segments/_full.segment.rsc +6 -6
  239. package/cli/app/.next-cli-build/server/app/dashboard/quota.segments/_head.segment.rsc +1 -1
  240. package/cli/app/.next-cli-build/server/app/dashboard/quota.segments/_index.segment.rsc +3 -3
  241. package/cli/app/.next-cli-build/server/app/dashboard/quota.segments/_tree.segment.rsc +1 -1
  242. package/cli/app/.next-cli-build/server/app/dashboard/settings/pricing/page_client-reference-manifest.js +1 -1
  243. package/cli/app/.next-cli-build/server/app/dashboard/settings/pricing.html +1 -1
  244. package/cli/app/.next-cli-build/server/app/dashboard/settings/pricing.rsc +3 -3
  245. package/cli/app/.next-cli-build/server/app/dashboard/settings/pricing.segments/_full.segment.rsc +3 -3
  246. package/cli/app/.next-cli-build/server/app/dashboard/settings/pricing.segments/_head.segment.rsc +1 -1
  247. package/cli/app/.next-cli-build/server/app/dashboard/settings/pricing.segments/_index.segment.rsc +3 -3
  248. package/cli/app/.next-cli-build/server/app/dashboard/settings/pricing.segments/_tree.segment.rsc +1 -1
  249. package/cli/app/.next-cli-build/server/app/dashboard/settings/pricing.segments/dashboard/settings/pricing/__PAGE__.segment.rsc +1 -1
  250. package/cli/app/.next-cli-build/server/app/dashboard/settings/pricing.segments/dashboard/settings/pricing.segment.rsc +1 -1
  251. package/cli/app/.next-cli-build/server/app/dashboard/settings/pricing.segments/dashboard/settings.segment.rsc +1 -1
  252. package/cli/app/.next-cli-build/server/app/dashboard/settings/pricing.segments/dashboard.segment.rsc +1 -1
  253. package/cli/app/.next-cli-build/server/app/dashboard/token-saver.html +1 -1
  254. package/cli/app/.next-cli-build/server/app/dashboard/token-saver.rsc +5 -5
  255. package/cli/app/.next-cli-build/server/app/dashboard/token-saver.segments/!KGRhc2hib2FyZCk/dashboard/token-saver/__PAGE__.segment.rsc +2 -2
  256. package/cli/app/.next-cli-build/server/app/dashboard/token-saver.segments/!KGRhc2hib2FyZCk/dashboard/token-saver.segment.rsc +1 -1
  257. package/cli/app/.next-cli-build/server/app/dashboard/token-saver.segments/!KGRhc2hib2FyZCk/dashboard.segment.rsc +1 -1
  258. package/cli/app/.next-cli-build/server/app/dashboard/token-saver.segments/!KGRhc2hib2FyZCk.segment.rsc +2 -2
  259. package/cli/app/.next-cli-build/server/app/dashboard/token-saver.segments/_full.segment.rsc +5 -5
  260. package/cli/app/.next-cli-build/server/app/dashboard/token-saver.segments/_head.segment.rsc +1 -1
  261. package/cli/app/.next-cli-build/server/app/dashboard/token-saver.segments/_index.segment.rsc +3 -3
  262. package/cli/app/.next-cli-build/server/app/dashboard/token-saver.segments/_tree.segment.rsc +1 -1
  263. package/cli/app/.next-cli-build/server/app/dashboard/translator.html +1 -1
  264. package/cli/app/.next-cli-build/server/app/dashboard/translator.rsc +5 -5
  265. package/cli/app/.next-cli-build/server/app/dashboard/translator.segments/!KGRhc2hib2FyZCk/dashboard/translator/__PAGE__.segment.rsc +2 -2
  266. package/cli/app/.next-cli-build/server/app/dashboard/translator.segments/!KGRhc2hib2FyZCk/dashboard/translator.segment.rsc +1 -1
  267. package/cli/app/.next-cli-build/server/app/dashboard/translator.segments/!KGRhc2hib2FyZCk/dashboard.segment.rsc +1 -1
  268. package/cli/app/.next-cli-build/server/app/dashboard/translator.segments/!KGRhc2hib2FyZCk.segment.rsc +2 -2
  269. package/cli/app/.next-cli-build/server/app/dashboard/translator.segments/_full.segment.rsc +5 -5
  270. package/cli/app/.next-cli-build/server/app/dashboard/translator.segments/_head.segment.rsc +1 -1
  271. package/cli/app/.next-cli-build/server/app/dashboard/translator.segments/_index.segment.rsc +3 -3
  272. package/cli/app/.next-cli-build/server/app/dashboard/translator.segments/_tree.segment.rsc +1 -1
  273. package/cli/app/.next-cli-build/server/app/dashboard/usage.html +1 -1
  274. package/cli/app/.next-cli-build/server/app/dashboard/usage.rsc +5 -5
  275. package/cli/app/.next-cli-build/server/app/dashboard/usage.segments/!KGRhc2hib2FyZCk/dashboard/usage/__PAGE__.segment.rsc +2 -2
  276. package/cli/app/.next-cli-build/server/app/dashboard/usage.segments/!KGRhc2hib2FyZCk/dashboard/usage.segment.rsc +1 -1
  277. package/cli/app/.next-cli-build/server/app/dashboard/usage.segments/!KGRhc2hib2FyZCk/dashboard.segment.rsc +1 -1
  278. package/cli/app/.next-cli-build/server/app/dashboard/usage.segments/!KGRhc2hib2FyZCk.segment.rsc +2 -2
  279. package/cli/app/.next-cli-build/server/app/dashboard/usage.segments/_full.segment.rsc +5 -5
  280. package/cli/app/.next-cli-build/server/app/dashboard/usage.segments/_head.segment.rsc +1 -1
  281. package/cli/app/.next-cli-build/server/app/dashboard/usage.segments/_index.segment.rsc +3 -3
  282. package/cli/app/.next-cli-build/server/app/dashboard/usage.segments/_tree.segment.rsc +1 -1
  283. package/cli/app/.next-cli-build/server/app/dashboard.html +1 -1
  284. package/cli/app/.next-cli-build/server/app/dashboard.rsc +5 -5
  285. package/cli/app/.next-cli-build/server/app/dashboard.segments/!KGRhc2hib2FyZCk/dashboard/__PAGE__.segment.rsc +2 -2
  286. package/cli/app/.next-cli-build/server/app/dashboard.segments/!KGRhc2hib2FyZCk/dashboard.segment.rsc +1 -1
  287. package/cli/app/.next-cli-build/server/app/dashboard.segments/!KGRhc2hib2FyZCk.segment.rsc +2 -2
  288. package/cli/app/.next-cli-build/server/app/dashboard.segments/_full.segment.rsc +5 -5
  289. package/cli/app/.next-cli-build/server/app/dashboard.segments/_head.segment.rsc +1 -1
  290. package/cli/app/.next-cli-build/server/app/dashboard.segments/_index.segment.rsc +3 -3
  291. package/cli/app/.next-cli-build/server/app/dashboard.segments/_tree.segment.rsc +1 -1
  292. package/cli/app/.next-cli-build/server/app/index.html +1 -1
  293. package/cli/app/.next-cli-build/server/app/index.rsc +3 -3
  294. package/cli/app/.next-cli-build/server/app/index.segments/__PAGE__.segment.rsc +1 -1
  295. package/cli/app/.next-cli-build/server/app/index.segments/_full.segment.rsc +3 -3
  296. package/cli/app/.next-cli-build/server/app/index.segments/_head.segment.rsc +1 -1
  297. package/cli/app/.next-cli-build/server/app/index.segments/_index.segment.rsc +3 -3
  298. package/cli/app/.next-cli-build/server/app/index.segments/_tree.segment.rsc +1 -1
  299. package/cli/app/.next-cli-build/server/app/landing/page_client-reference-manifest.js +1 -1
  300. package/cli/app/.next-cli-build/server/app/landing.html +1 -1
  301. package/cli/app/.next-cli-build/server/app/landing.rsc +4 -4
  302. package/cli/app/.next-cli-build/server/app/landing.segments/_full.segment.rsc +4 -4
  303. package/cli/app/.next-cli-build/server/app/landing.segments/_head.segment.rsc +1 -1
  304. package/cli/app/.next-cli-build/server/app/landing.segments/_index.segment.rsc +3 -3
  305. package/cli/app/.next-cli-build/server/app/landing.segments/_tree.segment.rsc +1 -1
  306. package/cli/app/.next-cli-build/server/app/landing.segments/landing/__PAGE__.segment.rsc +2 -2
  307. package/cli/app/.next-cli-build/server/app/landing.segments/landing.segment.rsc +1 -1
  308. package/cli/app/.next-cli-build/server/app/login/page_client-reference-manifest.js +1 -1
  309. package/cli/app/.next-cli-build/server/app/login.html +1 -1
  310. package/cli/app/.next-cli-build/server/app/login.rsc +4 -4
  311. package/cli/app/.next-cli-build/server/app/login.segments/_full.segment.rsc +4 -4
  312. package/cli/app/.next-cli-build/server/app/login.segments/_head.segment.rsc +1 -1
  313. package/cli/app/.next-cli-build/server/app/login.segments/_index.segment.rsc +3 -3
  314. package/cli/app/.next-cli-build/server/app/login.segments/_tree.segment.rsc +1 -1
  315. package/cli/app/.next-cli-build/server/app/login.segments/login/__PAGE__.segment.rsc +2 -2
  316. package/cli/app/.next-cli-build/server/app/login.segments/login.segment.rsc +1 -1
  317. package/cli/app/.next-cli-build/server/app/page_client-reference-manifest.js +1 -1
  318. package/cli/app/.next-cli-build/server/app-paths-manifest.json +7 -7
  319. package/cli/app/.next-cli-build/server/chunks/1019.js +1 -1
  320. package/cli/app/.next-cli-build/server/chunks/3155.js +1 -1
  321. package/cli/app/.next-cli-build/server/chunks/3579.js +1 -1
  322. package/cli/app/.next-cli-build/server/chunks/4566.js +1 -1
  323. package/cli/app/.next-cli-build/server/chunks/4746.js +1 -1
  324. package/cli/app/.next-cli-build/server/chunks/5000.js +1 -1
  325. package/cli/app/.next-cli-build/server/chunks/5307.js +1 -1
  326. package/cli/app/.next-cli-build/server/chunks/5949.js +3 -3
  327. package/cli/app/.next-cli-build/server/chunks/8306.js +1 -1
  328. package/cli/app/.next-cli-build/server/chunks/8371.js +1 -1
  329. package/cli/app/.next-cli-build/server/chunks/8895.js +1 -1
  330. package/cli/app/.next-cli-build/server/chunks/9621.js +1 -1
  331. package/cli/app/.next-cli-build/server/middleware-build-manifest.js +1 -1
  332. package/cli/app/.next-cli-build/server/pages/404.html +1 -1
  333. package/cli/app/.next-cli-build/server/pages/500.html +1 -1
  334. package/cli/app/.next-cli-build/static/chunks/{620-4698719a19477138.js → 620-51d6fc84653a20a0.js} +1 -1
  335. package/cli/app/CHANGELOG.md +13 -0
  336. package/cli/app/package.json +1 -1
  337. package/cli/package.json +1 -1
  338. package/open-sse/services/accountFallback.js +37 -0
  339. package/package.json +1 -1
  340. package/src/lib/oauth/services/bulkImportBrowserEngine.js +241 -32
  341. package/src/lib/oauth/services/codebuddyCnBulkImportManager.js +39 -34
  342. package/src/sse/services/auth.js +28 -7
  343. /package/cli/app/.next-cli-build/static/{STIs6ehtw793h3BxKhNWo → i-IN0_JUvDPX2TawfW0UV}/_buildManifest.js +0 -0
  344. /package/cli/app/.next-cli-build/static/{STIs6ehtw793h3BxKhNWo → i-IN0_JUvDPX2TawfW0UV}/_ssgManifest.js +0 -0
@@ -1,3 +1,16 @@
1
+ # v1.0.152 (2026-07-27)
2
+
3
+ ## Fixes
4
+ - **Accurate Codex quota recovery**: a newer quota snapshot that explicitly reports capacity can now supersede a stale per-model lock instead of returning a false long-lived 429 while quota remains available.
5
+ - **Bounded recovery probes**: recovered accounts are retried once only when the quota snapshot is newer than the locking error; a fresh upstream failure immediately restores the lock and prevents retry loops.
6
+
7
+ # v1.0.151 (2026-07-27)
8
+
9
+ ## Fixes
10
+ - **Deterministic DataImpulse sticky sessions**: CodeBuddy CN now initializes pasted proxies with sequential CN-accessible exit checks, preventing parallel first requests from racing sticky-port assignment and falsely reporting an immediate rotation.
11
+ - **Exit-aligned CloakBrowser identity**: the verified residential exit is applied directly to WebRTC, timezone, and locale flags instead of allowing failed foreign echo services to substitute the proxy gateway address.
12
+ - **Safe pre-purchase verification**: browser-context checks use the same sequential fallback order and compare the initial exit with the exit immediately before the 5sim purchase, without modifying pasted credentials or Proxy Pool data.
13
+
1
14
  # v1.0.150 (2026-07-27)
2
15
 
3
16
  ## Fixes
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "zevairouter",
3
- "version": "1.0.150",
3
+ "version": "1.0.152",
4
4
  "description": "Self-hosted AI router: many providers, one OpenAI-compatible /v1 endpoint and dashboard",
5
5
  "bin": {
6
6
  "zevai": "./cli/cli.js"
package/cli/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "zevairouter-cli",
3
- "version": "1.0.150",
3
+ "version": "1.0.152",
4
4
  "description": "ZevaiRouter CLI - Start and manage ZevaiRouter server",
5
5
  "bin": {
6
6
  "zevai": "./cli.js"
@@ -53,6 +53,43 @@ export function getQuotaExhaustedUntil(usage) {
53
53
  return getQuotaResetAt(usage);
54
54
  }
55
55
 
56
+ /**
57
+ * Return true only when a quota snapshot explicitly says every known window
58
+ * still has capacity. Requiring all windows avoids treating an account with an
59
+ * exhausted weekly window as recovered just because its short window is open.
60
+ */
61
+ export function hasAvailableQuota(usage) {
62
+ if (!usage || usage.limitReached === true) return false;
63
+ const quotas = Object.values(usage.quotas || {});
64
+ const remaining = quotas.map((quota) => {
65
+ if (Number.isFinite(quota?.remaining)) return quota.remaining;
66
+ if (Number.isFinite(quota?.remainingPercentage)) return quota.remainingPercentage;
67
+ return null;
68
+ }).filter((value) => value !== null);
69
+
70
+ return remaining.length > 0
71
+ && remaining.length === quotas.length
72
+ && remaining.every((value) => value > 0);
73
+ }
74
+
75
+ /**
76
+ * A successful quota poll newer than the error which created a model lock is
77
+ * authoritative evidence that a Codex account recovered. The caller may probe
78
+ * the account once; a fresh upstream failure updates lastErrorAt and makes the
79
+ * same snapshot too old to bypass the replacement lock.
80
+ */
81
+ export function isModelLockRecoveredByQuota(connection, model, snapshot) {
82
+ if (!isModelLockActive(connection, model) || !hasAvailableQuota(snapshot?.usage)) {
83
+ return false;
84
+ }
85
+
86
+ const fetchedAt = Date.parse(snapshot?.fetchedAt);
87
+ const errorAt = Date.parse(connection?.lastErrorAt);
88
+ return Number.isFinite(fetchedAt)
89
+ && Number.isFinite(errorAt)
90
+ && fetchedAt > errorAt;
91
+ }
92
+
56
93
  /**
57
94
  * Calculate exponential backoff cooldown for rate limits (429)
58
95
  * Level 1: 1s, Level 2: 2s, Level 3: 4s... → max 4 min
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "zevairouter",
3
- "version": "1.0.150",
3
+ "version": "1.0.152",
4
4
  "description": "Self-hosted AI router: many providers, one OpenAI-compatible /v1 endpoint and dashboard",
5
5
  "bin": {
6
6
  "zevai": "./cli/cli.js"
@@ -1,5 +1,7 @@
1
1
  import { createHash } from "node:crypto";
2
2
  import { createRequire } from "node:module";
3
+ import net from "node:net";
4
+ import { ProxyAgent, fetch as undiciFetch } from "undici";
3
5
 
4
6
  const requireFromHere = createRequire(import.meta.url);
5
7
 
@@ -14,6 +16,27 @@ export const DEFAULT_BULK_IMPORT_ENGINE = "cloakbrowser";
14
16
  const SUPPORTED_ENGINES = new Set(["cloakbrowser"]);
15
17
  const CLOAK_PROXY_PROFILES = new WeakMap();
16
18
 
19
+ export const PROXY_EGRESS_ECHO_URLS = Object.freeze([
20
+ "https://myip.ipip.net",
21
+ "https://ip.3322.net",
22
+ "https://cip.cc",
23
+ ]);
24
+
25
+ const PROXY_GEO_PROFILES = Object.freeze({
26
+ CN: { timezone: "Asia/Shanghai", locale: "zh-CN" },
27
+ HK: { timezone: "Asia/Hong_Kong", locale: "zh-HK" },
28
+ MO: { timezone: "Asia/Macau", locale: "zh-MO" },
29
+ TW: { timezone: "Asia/Taipei", locale: "zh-TW" },
30
+ SG: { timezone: "Asia/Singapore", locale: "en-SG" },
31
+ JP: { timezone: "Asia/Tokyo", locale: "ja-JP" },
32
+ KR: { timezone: "Asia/Seoul", locale: "ko-KR" },
33
+ US: { locale: "en-US" },
34
+ GB: { locale: "en-GB" },
35
+ });
36
+
37
+ const DEFAULT_PROXY_PROBE_TIMEOUT_MS = 8_000;
38
+ const DEFAULT_PROXY_GEO_TIMEOUT_MS = 5_000;
39
+
17
40
  export function normalizeBulkImportEngine(value) {
18
41
  if (typeof value !== "string" || !value.trim()) return DEFAULT_BULK_IMPORT_ENGINE;
19
42
  const lower = value.trim().toLowerCase();
@@ -208,6 +231,220 @@ export async function newStealthContext(browser, options = {}) {
208
231
  return context;
209
232
  }
210
233
 
234
+ export function parseProxyEgressIp(value) {
235
+ const raw = String(value || "").trim();
236
+ if (!raw) return null;
237
+ if (net.isIP(raw)) return raw;
238
+
239
+ try {
240
+ const parsed = JSON.parse(raw);
241
+ for (const key of ["ip", "query", "address", "origin"]) {
242
+ const candidate = String(parsed?.[key] || "").trim();
243
+ if (net.isIP(candidate)) return candidate;
244
+ }
245
+ } catch {
246
+ // Plain-text echo services are expected here.
247
+ }
248
+
249
+ for (const match of raw.matchAll(/(?:\d{1,3}\.){3}\d{1,3}/g)) {
250
+ if (net.isIP(match[0])) return match[0];
251
+ }
252
+
253
+ const tokens = raw.split(/[\s,;()[\]{}<>"'=\uFF1A]+/);
254
+ for (const token of tokens) {
255
+ const candidate = token.replace(/^[^0-9a-f:]+|[^0-9a-f:]+$/gi, "");
256
+ if (candidate.includes(":") && net.isIP(candidate)) return candidate;
257
+ }
258
+ return null;
259
+ }
260
+
261
+ function inferProxyRegionalProfile(proxyUrl) {
262
+ try {
263
+ const parsed = new URL(String(proxyUrl || "").trim());
264
+ const username = decodeURIComponent(parsed.username || "");
265
+ const matches = [...username.matchAll(/(?:^|__)cr\.([a-z]{2})(?=__|$)/gi)];
266
+ const countryCode = matches.at(-1)?.[1]?.toUpperCase() || null;
267
+ const regional = countryCode ? PROXY_GEO_PROFILES[countryCode] : null;
268
+ return regional?.timezone && regional?.locale
269
+ ? { countryCode, ...regional, source: "proxy-country" }
270
+ : null;
271
+ } catch {
272
+ return null;
273
+ }
274
+ }
275
+
276
+ async function closeProxyAgent(agent) {
277
+ if (!agent) return;
278
+ if (typeof agent.close === "function") {
279
+ await Promise.resolve(agent.close()).catch(() => null);
280
+ return;
281
+ }
282
+ if (typeof agent.destroy === "function") {
283
+ await Promise.resolve(agent.destroy()).catch(() => null);
284
+ }
285
+ }
286
+
287
+ /**
288
+ * Pin a fresh sticky proxy with one request at a time. Parallel first-use
289
+ * requests can race session assignment on providers such as DataImpulse.
290
+ */
291
+ export async function probeProxyEgressBeforeLaunch(
292
+ proxyUrl,
293
+ {
294
+ timeoutMs = DEFAULT_PROXY_PROBE_TIMEOUT_MS,
295
+ urls = PROXY_EGRESS_ECHO_URLS,
296
+ fetchImpl = undiciFetch,
297
+ createProxyAgent = (url) => new ProxyAgent(url),
298
+ } = {},
299
+ ) {
300
+ let agent = null;
301
+ const attemptedUrls = [];
302
+ let lastError = null;
303
+
304
+ try {
305
+ try {
306
+ agent = createProxyAgent(proxyUrl);
307
+ } catch {
308
+ return {
309
+ ok: false,
310
+ ip: null,
311
+ url: null,
312
+ attempts: 0,
313
+ attemptedUrls,
314
+ error: "proxy agent setup failed",
315
+ };
316
+ }
317
+
318
+ for (const url of urls) {
319
+ attemptedUrls.push(url);
320
+ try {
321
+ const response = await fetchImpl(url, {
322
+ dispatcher: agent,
323
+ redirect: "follow",
324
+ signal: AbortSignal.timeout(timeoutMs),
325
+ headers: {
326
+ Accept: "text/plain, application/json;q=0.9, */*;q=0.1",
327
+ "Cache-Control": "no-cache",
328
+ },
329
+ });
330
+ if (!response?.ok) {
331
+ lastError = `HTTP ${response?.status || 0}`;
332
+ continue;
333
+ }
334
+ const ip = parseProxyEgressIp(await response.text());
335
+ if (!ip) {
336
+ lastError = "exit-IP response was not recognized";
337
+ continue;
338
+ }
339
+ return {
340
+ ok: true,
341
+ ip,
342
+ url,
343
+ attempts: attemptedUrls.length,
344
+ attemptedUrls,
345
+ error: null,
346
+ };
347
+ } catch (error) {
348
+ lastError = error?.name === "TimeoutError"
349
+ ? `timed out after ${timeoutMs}ms`
350
+ : "request failed";
351
+ }
352
+ }
353
+
354
+ return {
355
+ ok: false,
356
+ ip: null,
357
+ url: null,
358
+ attempts: attemptedUrls.length,
359
+ attemptedUrls,
360
+ error: lastError || "all exit-IP services failed",
361
+ };
362
+ } finally {
363
+ await closeProxyAgent(agent);
364
+ }
365
+ }
366
+
367
+ async function lookupProxyGeoProfile(
368
+ egressIp,
369
+ { timeoutMs = DEFAULT_PROXY_GEO_TIMEOUT_MS, fetchImpl = undiciFetch } = {},
370
+ ) {
371
+ try {
372
+ const response = await fetchImpl(`https://ipwho.is/${encodeURIComponent(egressIp)}`, {
373
+ redirect: "follow",
374
+ signal: AbortSignal.timeout(timeoutMs),
375
+ headers: { Accept: "application/json" },
376
+ });
377
+ if (!response?.ok) return null;
378
+ const data = await response.json();
379
+ if (data?.success === false) return null;
380
+ const countryCode = String(data?.country_code || "").trim().toUpperCase();
381
+ const timezone = String(data?.timezone?.id || "").trim();
382
+ const locale = PROXY_GEO_PROFILES[countryCode]?.locale
383
+ || (countryCode ? `en-${countryCode}` : "");
384
+ return timezone && locale
385
+ ? { countryCode: countryCode || null, timezone, locale, source: "ip-geo" }
386
+ : null;
387
+ } catch {
388
+ return null;
389
+ }
390
+ }
391
+
392
+ export async function resolveProxyLaunchProfile(proxyUrl, options = {}) {
393
+ const probe = await probeProxyEgressBeforeLaunch(proxyUrl, options);
394
+ if (!probe.ok || !probe.ip) {
395
+ const error = new Error(
396
+ `Manual proxy exit IP could not be verified before browser launch (${probe.error || "no response"}); no phone number was purchased`,
397
+ );
398
+ error.code = "CLOAKBROWSER_PROXY_EGRESS_UNAVAILABLE";
399
+ throw error;
400
+ }
401
+
402
+ const regional = inferProxyRegionalProfile(proxyUrl)
403
+ || await lookupProxyGeoProfile(probe.ip, options);
404
+ if (!regional?.timezone || !regional?.locale) {
405
+ const error = new Error(
406
+ "Manual proxy region could not be aligned with CloakBrowser; no phone number was purchased",
407
+ );
408
+ error.code = "CLOAKBROWSER_PROXY_GEOIP_UNAVAILABLE";
409
+ throw error;
410
+ }
411
+
412
+ return Object.freeze({
413
+ egressIp: probe.ip,
414
+ timezone: regional.timezone,
415
+ locale: regional.locale,
416
+ countryCode: regional.countryCode || null,
417
+ source: regional.source,
418
+ probeUrl: probe.url,
419
+ probeAttempts: probe.attempts,
420
+ });
421
+ }
422
+
423
+ export function buildVerifiedProxyLaunchOptions(launchOpts, proxyProfile) {
424
+ const managedPrefixes = [
425
+ "--fingerprint-webrtc-ip=",
426
+ "--fingerprint-timezone=",
427
+ "--fingerprint-locale=",
428
+ "--lang=",
429
+ ];
430
+ const args = (launchOpts?.args || []).filter(
431
+ (arg) => !managedPrefixes.some((prefix) => String(arg).startsWith(prefix)),
432
+ );
433
+ args.push(
434
+ `--fingerprint-webrtc-ip=${proxyProfile.egressIp}`,
435
+ `--fingerprint-timezone=${proxyProfile.timezone}`,
436
+ `--lang=${proxyProfile.locale}`,
437
+ `--fingerprint-locale=${proxyProfile.locale}`,
438
+ );
439
+ return {
440
+ ...launchOpts,
441
+ args,
442
+ timezone: proxyProfile.timezone,
443
+ locale: proxyProfile.locale,
444
+ geoip: false,
445
+ };
446
+ }
447
+
211
448
  /**
212
449
  * CloakBrowser — sole bulk-import engine (patched stealth Chromium).
213
450
  * Prefer headed (headless=false); Turnstile / Google bot checks often fail headless.
@@ -292,38 +529,10 @@ async function launchCloakbrowser({
292
529
  let effectiveLaunchOpts = launchOpts;
293
530
  let proxyProfile = null;
294
531
  if (proxyUrl && requireProxyGeoip) {
295
- if (typeof cloak.buildLaunchOptions !== "function") {
296
- const error = new Error("CloakBrowser runtime cannot verify proxy GeoIP before launch");
297
- error.code = "CLOAKBROWSER_PROXY_GEOIP_UNSUPPORTED";
298
- throw error;
299
- }
300
- // Slow residential CONNECT handshakes regularly exceed CloakBrowser's 5s
301
- // default. Resolve once with a bounded 12s budget, then reuse those flags.
302
- const previousGeoipTimeout = process.env.CLOAKBROWSER_GEOIP_TIMEOUT_SECONDS;
303
- if (!previousGeoipTimeout) process.env.CLOAKBROWSER_GEOIP_TIMEOUT_SECONDS = "12";
304
- let resolved;
305
- try {
306
- resolved = await cloak.buildLaunchOptions(launchOpts);
307
- } finally {
308
- if (previousGeoipTimeout === undefined) {
309
- delete process.env.CLOAKBROWSER_GEOIP_TIMEOUT_SECONDS;
310
- } else {
311
- process.env.CLOAKBROWSER_GEOIP_TIMEOUT_SECONDS = previousGeoipTimeout;
312
- }
313
- }
314
- proxyProfile = extractCloakProxyProfile(resolved?.args || []);
315
- if (!proxyProfile.egressIp || !proxyProfile.timezone || !proxyProfile.locale) {
316
- const error = new Error(
317
- "Manual proxy exit GeoIP could not be verified; no phone number was purchased",
318
- );
319
- error.code = "CLOAKBROWSER_PROXY_GEOIP_UNAVAILABLE";
320
- throw error;
321
- }
322
- effectiveLaunchOpts = {
323
- ...launchOpts,
324
- args: resolved.args || launchOpts.args,
325
- geoip: false,
326
- };
532
+ // Resolve the exit ourselves through CN-accessible endpoints. CloakBrowser's
533
+ // foreign echo fallbacks can time out and mistake the gateway IP for the exit.
534
+ proxyProfile = await resolveProxyLaunchProfile(proxyUrl);
535
+ effectiveLaunchOpts = buildVerifiedProxyLaunchOptions(launchOpts, proxyProfile);
327
536
  }
328
537
 
329
538
  try {
@@ -18,7 +18,6 @@
18
18
  */
19
19
 
20
20
  import { randomUUID } from "crypto";
21
- import net from "node:net";
22
21
  import {
23
22
  KiroBulkImportManager,
24
23
  buildLookupResponse,
@@ -44,6 +43,8 @@ import {
44
43
  import {
45
44
  forceCloseBrowser,
46
45
  getCloakProxyProfile,
46
+ parseProxyEgressIp,
47
+ PROXY_EGRESS_ECHO_URLS,
47
48
  } from "./bulkImportBrowserEngine.js";
48
49
 
49
50
  const CODEBUDDY_CN_PROVIDER_ID = "codebuddy-cn";
@@ -89,11 +90,6 @@ const CODEBUDDY_CN_FIVESIM_SETTLE_TIMEOUT_MS = 12_000;
89
90
  const CODEBUDDY_CN_EGRESS_PROBE_TIMEOUT_MS = 6_000;
90
91
  const CODEBUDDY_CN_API_KEY_OUTCOME_UNKNOWN = "CN_API_KEY_OUTCOME_UNKNOWN";
91
92
  const CODEBUDDY_CN_ACCOUNT_RESTRICTED = "CN_ACCOUNT_RESTRICTED";
92
- const CODEBUDDY_CN_EGRESS_ECHO_URLS = [
93
- "https://api.ipify.org",
94
- "https://checkip.amazonaws.com",
95
- "https://ifconfig.me/ip",
96
- ];
97
93
 
98
94
  // Supported 5sim regions
99
95
  const SUPPORTED_REGIONS = new Set(["hongkong", "china", "any"]);
@@ -142,15 +138,7 @@ function resolveCnJobConcurrency(value, { manualProxy = false } = {}) {
142
138
  }
143
139
 
144
140
  function parseEgressIp(value) {
145
- const raw = String(value || "").trim();
146
- if (net.isIP(raw)) return raw;
147
- try {
148
- const parsed = JSON.parse(raw);
149
- const ip = String(parsed?.ip || parsed?.query || "").trim();
150
- return net.isIP(ip) ? ip : null;
151
- } catch {
152
- return null;
153
- }
141
+ return parseProxyEgressIp(value);
154
142
  }
155
143
 
156
144
  async function probeCodeBuddyProxyEgress(
@@ -167,7 +155,10 @@ async function probeCodeBuddyProxyEgress(
167
155
  return { ok: false, ip: null, ips: [], samples: 0, error: "context request unavailable" };
168
156
  }
169
157
 
170
- const results = await Promise.all(CODEBUDDY_CN_EGRESS_ECHO_URLS.map(async (url) => {
158
+ const attemptedUrls = [];
159
+ let lastError = null;
160
+ for (const url of PROXY_EGRESS_ECHO_URLS) {
161
+ attemptedUrls.push(url);
171
162
  let response = null;
172
163
  try {
173
164
  response = await requestContext.get(url, {
@@ -178,30 +169,44 @@ async function probeCodeBuddyProxyEgress(
178
169
  "Cache-Control": "no-cache",
179
170
  },
180
171
  });
181
- if (response.status() < 200 || response.status() >= 300) return null;
182
- return parseEgressIp(await response.text().catch(() => ""));
183
- } catch {
184
- return null;
172
+ if (response.status() < 200 || response.status() >= 300) {
173
+ lastError = `HTTP ${response.status()}`;
174
+ continue;
175
+ }
176
+ const ip = parseEgressIp(await response.text().catch(() => ""));
177
+ if (!ip) {
178
+ lastError = "exit-IP response was not recognized";
179
+ continue;
180
+ }
181
+ return {
182
+ ok: true,
183
+ ip,
184
+ ips: [ip],
185
+ samples: 1,
186
+ attempts: attemptedUrls.length,
187
+ attemptedUrls,
188
+ unstable: false,
189
+ error: null,
190
+ };
191
+ } catch (error) {
192
+ lastError = error?.name === "TimeoutError"
193
+ ? `timed out after ${timeoutMs}ms`
194
+ : "request failed";
185
195
  } finally {
186
196
  if (typeof response?.dispose === "function") {
187
197
  await Promise.resolve(response.dispose()).catch(() => null);
188
198
  }
189
199
  }
190
- }));
191
-
192
- const successful = results.filter(Boolean);
193
- const ips = [...new Set(successful)];
200
+ }
194
201
  return {
195
- ok: ips.length === 1,
196
- ip: ips.length === 1 ? ips[0] : null,
197
- ips,
198
- samples: successful.length,
199
- unstable: ips.length > 1,
200
- error: ips.length === 0
201
- ? "all exit-IP services failed"
202
- : ips.length > 1
203
- ? `proxy returned ${ips.length} exit IPs in one probe`
204
- : null,
202
+ ok: false,
203
+ ip: null,
204
+ ips: [],
205
+ samples: 0,
206
+ attempts: attemptedUrls.length,
207
+ attemptedUrls,
208
+ unstable: false,
209
+ error: lastError || "all exit-IP services failed",
205
210
  };
206
211
  }
207
212
 
@@ -1,6 +1,6 @@
1
1
  import { getProviderConnections, validateApiKey, updateProviderConnection, getSettings, getQuotaSnapshot, getAllQuotaSnapshots, getProxyPools } from "@/lib/localDb";
2
2
  import { resolveConnectionProxyConfig, pickProxyPoolId } from "@/lib/network/connectionProxy";
3
- import { formatRetryAfter, checkFallbackError, isModelLockActive, buildModelLockUpdate, getEarliestModelLockUntil, isNonAccountError, extractProviderErrorCode, getQuotaResetAt, getQuotaExhaustedUntil } from "open-sse/services/accountFallback.js";
3
+ import { formatRetryAfter, checkFallbackError, isModelLockActive, isModelLockRecoveredByQuota, buildModelLockUpdate, getEarliestModelLockUntil, isNonAccountError, extractProviderErrorCode, getQuotaResetAt, getQuotaExhaustedUntil } from "open-sse/services/accountFallback.js";
4
4
  import { MAX_RATE_LIMIT_COOLDOWN_MS } from "open-sse/config/errorConfig.js";
5
5
  import { resolveProviderId, FREE_PROVIDERS } from "@/shared/constants/providers.js";
6
6
  import * as log from "../utils/logger.js";
@@ -77,9 +77,29 @@ export async function getProviderCredentials(provider, excludeConnectionIds = nu
77
77
  }
78
78
  }
79
79
 
80
+ // Codex can return a precise usage-limit reset which creates a long-lived
81
+ // model lock. If a newer quota poll explicitly reports capacity again, let
82
+ // that account be probed once instead of serving a stale all-rate-limited
83
+ // response until the old reset timestamp. A new failure is newer than the
84
+ // snapshot, so it immediately restores the lock without a retry loop.
85
+ const recoveredModelLocks = new Set();
86
+ if (providerId === "codex" && model) {
87
+ const snapshots = await getAllQuotaSnapshots(providerId);
88
+ const byConnection = new Map(snapshots.map((snapshot) => [snapshot.connectionId, snapshot]));
89
+ for (const connection of connections) {
90
+ if (isModelLockRecoveredByQuota(connection, model, byConnection.get(connection.id))) {
91
+ recoveredModelLocks.add(connection.id);
92
+ }
93
+ }
94
+ }
95
+
96
+ const hasBlockingModelLock = (connection) => (
97
+ isModelLockActive(connection, model) && !recoveredModelLocks.has(connection.id)
98
+ );
99
+
80
100
  const baseAvailableConnections = connections.filter(c => {
81
101
  if (excludeSet.has(c.id)) return false;
82
- if (isModelLockActive(c, model)) return false;
102
+ if (hasBlockingModelLock(c)) return false;
83
103
  if (quotaExhausted.has(c.id)) return false;
84
104
  return true;
85
105
  });
@@ -98,7 +118,7 @@ export async function getProviderCredentials(provider, excludeConnectionIds = nu
98
118
  log.warn("AUTH", `${provider} | pinned account excluded after failure: ${preferred.id?.slice(0, 8)}`);
99
119
  return null;
100
120
  }
101
- if (isModelLockActive(preferred, model) || quotaExhausted.has(preferred.id)) {
121
+ if (hasBlockingModelLock(preferred) || quotaExhausted.has(preferred.id)) {
102
122
  const retryAfter = [
103
123
  getEarliestModelLockUntil(preferred),
104
124
  quotaExhausted.has(preferred.id)
@@ -119,17 +139,18 @@ export async function getProviderCredentials(provider, excludeConnectionIds = nu
119
139
  log.debug("AUTH", `${provider} | available: ${availableConnections.length}/${connections.length}`);
120
140
  connections.forEach(c => {
121
141
  const excluded = excludeSet.has(c.id);
122
- const locked = isModelLockActive(c, model);
142
+ const locked = hasBlockingModelLock(c);
143
+ const recovered = recoveredModelLocks.has(c.id);
123
144
  const exhaustedUntil = quotaExhausted.get(c.id);
124
- if (excluded || locked || exhaustedUntil) {
145
+ if (excluded || locked || exhaustedUntil || recovered) {
125
146
  const lockUntil = getEarliestModelLockUntil(c);
126
- log.debug("AUTH", ` \u2192 ${c.id?.slice(0, 8)} | ${excluded ? "excluded" : ""} ${locked ? `modelLocked(${model}) until ${lockUntil}` : ""} ${exhaustedUntil ? `quotaExhausted until ${new Date(exhaustedUntil).toISOString()}` : ""}`);
147
+ log.debug("AUTH", ` \u2192 ${c.id?.slice(0, 8)} | ${excluded ? "excluded" : ""} ${locked ? `modelLocked(${model}) until ${lockUntil}` : ""} ${recovered ? `staleLockRecovered(${model})` : ""} ${exhaustedUntil ? `quotaExhausted until ${new Date(exhaustedUntil).toISOString()}` : ""}`);
127
148
  }
128
149
  });
129
150
 
130
151
  if (availableConnections.length === 0) {
131
152
  // Find earliest lock expiry across all connections for retry timing
132
- const lockedConns = connections.filter(c => isModelLockActive(c, model));
153
+ const lockedConns = connections.filter(c => hasBlockingModelLock(c));
133
154
  const expiries = [
134
155
  ...lockedConns.map(c => getEarliestModelLockUntil(c)).filter(Boolean),
135
156
  ...quotaExhausted.values().map(timestamp => new Date(timestamp).toISOString()),