@neontechspace/fluxerly 1000.0.0-nightly.12

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 (1319) hide show
  1. package/CHANGELOG.md +833 -0
  2. package/LICENSE +201 -0
  3. package/README.md +129 -0
  4. package/agents/AGENTS.md +195 -0
  5. package/dist/api/default/application.d.ts +34 -0
  6. package/dist/api/default/application.d.ts.map +1 -0
  7. package/dist/api/default/application.js +2 -0
  8. package/dist/api/default/application.js.map +1 -0
  9. package/dist/api/default/attachments.d.ts +89 -0
  10. package/dist/api/default/attachments.d.ts.map +1 -0
  11. package/dist/api/default/attachments.js +2 -0
  12. package/dist/api/default/attachments.js.map +1 -0
  13. package/dist/api/default/audit-logs.d.ts +48 -0
  14. package/dist/api/default/audit-logs.d.ts.map +1 -0
  15. package/dist/api/default/audit-logs.js +2 -0
  16. package/dist/api/default/audit-logs.js.map +1 -0
  17. package/dist/api/default/bot.d.ts +200 -0
  18. package/dist/api/default/bot.d.ts.map +1 -0
  19. package/dist/api/default/bot.js +309 -0
  20. package/dist/api/default/bot.js.map +1 -0
  21. package/dist/api/default/cache.d.ts +105 -0
  22. package/dist/api/default/cache.d.ts.map +1 -0
  23. package/dist/api/default/cache.js +2 -0
  24. package/dist/api/default/cache.js.map +1 -0
  25. package/dist/api/default/channels.d.ts +249 -0
  26. package/dist/api/default/channels.d.ts.map +1 -0
  27. package/dist/api/default/channels.js +2 -0
  28. package/dist/api/default/channels.js.map +1 -0
  29. package/dist/api/default/client.d.ts +528 -0
  30. package/dist/api/default/client.d.ts.map +1 -0
  31. package/dist/api/default/client.js +301 -0
  32. package/dist/api/default/client.js.map +1 -0
  33. package/dist/api/default/collectors.d.ts +76 -0
  34. package/dist/api/default/collectors.d.ts.map +1 -0
  35. package/dist/api/default/collectors.js +2 -0
  36. package/dist/api/default/collectors.js.map +1 -0
  37. package/dist/api/default/commands.d.ts +91 -0
  38. package/dist/api/default/commands.d.ts.map +1 -0
  39. package/dist/api/default/commands.js +92 -0
  40. package/dist/api/default/commands.js.map +1 -0
  41. package/dist/api/default/direct-messages.d.ts +111 -0
  42. package/dist/api/default/direct-messages.d.ts.map +1 -0
  43. package/dist/api/default/direct-messages.js +2 -0
  44. package/dist/api/default/direct-messages.js.map +1 -0
  45. package/dist/api/default/discovery.d.ts +76 -0
  46. package/dist/api/default/discovery.d.ts.map +1 -0
  47. package/dist/api/default/discovery.js +2 -0
  48. package/dist/api/default/discovery.js.map +1 -0
  49. package/dist/api/default/emojis.d.ts +88 -0
  50. package/dist/api/default/emojis.d.ts.map +1 -0
  51. package/dist/api/default/emojis.js +2 -0
  52. package/dist/api/default/emojis.js.map +1 -0
  53. package/dist/api/default/events.d.ts +127 -0
  54. package/dist/api/default/events.d.ts.map +1 -0
  55. package/dist/api/default/events.js +2 -0
  56. package/dist/api/default/events.js.map +1 -0
  57. package/dist/api/default/gateway.d.ts +62 -0
  58. package/dist/api/default/gateway.d.ts.map +1 -0
  59. package/dist/api/default/gateway.js +2 -0
  60. package/dist/api/default/gateway.js.map +1 -0
  61. package/dist/api/default/guards.d.ts +87 -0
  62. package/dist/api/default/guards.d.ts.map +1 -0
  63. package/dist/api/default/guards.js +78 -0
  64. package/dist/api/default/guards.js.map +1 -0
  65. package/dist/api/default/guilds.d.ts +230 -0
  66. package/dist/api/default/guilds.d.ts.map +1 -0
  67. package/dist/api/default/guilds.js +2 -0
  68. package/dist/api/default/guilds.js.map +1 -0
  69. package/dist/api/default/helpers.d.ts +79 -0
  70. package/dist/api/default/helpers.d.ts.map +1 -0
  71. package/dist/api/default/helpers.js +79 -0
  72. package/dist/api/default/helpers.js.map +1 -0
  73. package/dist/api/default/instance.d.ts +47 -0
  74. package/dist/api/default/instance.d.ts.map +1 -0
  75. package/dist/api/default/instance.js +2 -0
  76. package/dist/api/default/instance.js.map +1 -0
  77. package/dist/api/default/invites.d.ts +57 -0
  78. package/dist/api/default/invites.d.ts.map +1 -0
  79. package/dist/api/default/invites.js +2 -0
  80. package/dist/api/default/invites.js.map +1 -0
  81. package/dist/api/default/logging.d.ts +37 -0
  82. package/dist/api/default/logging.d.ts.map +1 -0
  83. package/dist/api/default/logging.js +2 -0
  84. package/dist/api/default/logging.js.map +1 -0
  85. package/dist/api/default/members.d.ts +442 -0
  86. package/dist/api/default/members.d.ts.map +1 -0
  87. package/dist/api/default/members.js +2 -0
  88. package/dist/api/default/members.js.map +1 -0
  89. package/dist/api/default/messages.d.ts +898 -0
  90. package/dist/api/default/messages.d.ts.map +1 -0
  91. package/dist/api/default/messages.js +2 -0
  92. package/dist/api/default/messages.js.map +1 -0
  93. package/dist/api/default/oauth.d.ts +168 -0
  94. package/dist/api/default/oauth.d.ts.map +1 -0
  95. package/dist/api/default/oauth.js +84 -0
  96. package/dist/api/default/oauth.js.map +1 -0
  97. package/dist/api/default/permissions.d.ts +44 -0
  98. package/dist/api/default/permissions.d.ts.map +1 -0
  99. package/dist/api/default/permissions.js +2 -0
  100. package/dist/api/default/permissions.js.map +1 -0
  101. package/dist/api/default/presence.d.ts +88 -0
  102. package/dist/api/default/presence.d.ts.map +1 -0
  103. package/dist/api/default/presence.js +2 -0
  104. package/dist/api/default/presence.js.map +1 -0
  105. package/dist/api/default/rest.d.ts +28 -0
  106. package/dist/api/default/rest.d.ts.map +1 -0
  107. package/dist/api/default/rest.js +2 -0
  108. package/dist/api/default/rest.js.map +1 -0
  109. package/dist/api/default/results.d.ts +31 -0
  110. package/dist/api/default/results.d.ts.map +1 -0
  111. package/dist/api/default/results.js +14 -0
  112. package/dist/api/default/results.js.map +1 -0
  113. package/dist/api/default/roles.d.ts +119 -0
  114. package/dist/api/default/roles.d.ts.map +1 -0
  115. package/dist/api/default/roles.js +2 -0
  116. package/dist/api/default/roles.js.map +1 -0
  117. package/dist/api/default/stickers.d.ts +92 -0
  118. package/dist/api/default/stickers.d.ts.map +1 -0
  119. package/dist/api/default/stickers.js +2 -0
  120. package/dist/api/default/stickers.js.map +1 -0
  121. package/dist/api/default/supervisor.d.ts +51 -0
  122. package/dist/api/default/supervisor.d.ts.map +1 -0
  123. package/dist/api/default/supervisor.js +53 -0
  124. package/dist/api/default/supervisor.js.map +1 -0
  125. package/dist/api/default/threads.d.ts +158 -0
  126. package/dist/api/default/threads.d.ts.map +1 -0
  127. package/dist/api/default/threads.js +2 -0
  128. package/dist/api/default/threads.js.map +1 -0
  129. package/dist/api/default/users.d.ts +73 -0
  130. package/dist/api/default/users.d.ts.map +1 -0
  131. package/dist/api/default/users.js +2 -0
  132. package/dist/api/default/users.js.map +1 -0
  133. package/dist/api/default/webhook-client.d.ts +149 -0
  134. package/dist/api/default/webhook-client.d.ts.map +1 -0
  135. package/dist/api/default/webhook-client.js +69 -0
  136. package/dist/api/default/webhook-client.js.map +1 -0
  137. package/dist/api/default/webhooks.d.ts +62 -0
  138. package/dist/api/default/webhooks.d.ts.map +1 -0
  139. package/dist/api/default/webhooks.js +2 -0
  140. package/dist/api/default/webhooks.js.map +1 -0
  141. package/dist/api/effect/application.d.ts +29 -0
  142. package/dist/api/effect/application.d.ts.map +1 -0
  143. package/dist/api/effect/application.js +2 -0
  144. package/dist/api/effect/application.js.map +1 -0
  145. package/dist/api/effect/attachments.d.ts +84 -0
  146. package/dist/api/effect/attachments.d.ts.map +1 -0
  147. package/dist/api/effect/attachments.js +2 -0
  148. package/dist/api/effect/attachments.js.map +1 -0
  149. package/dist/api/effect/audit-logs.d.ts +42 -0
  150. package/dist/api/effect/audit-logs.d.ts.map +1 -0
  151. package/dist/api/effect/audit-logs.js +2 -0
  152. package/dist/api/effect/audit-logs.js.map +1 -0
  153. package/dist/api/effect/bot.d.ts +233 -0
  154. package/dist/api/effect/bot.d.ts.map +1 -0
  155. package/dist/api/effect/bot.js +230 -0
  156. package/dist/api/effect/bot.js.map +1 -0
  157. package/dist/api/effect/cache.d.ts +103 -0
  158. package/dist/api/effect/cache.d.ts.map +1 -0
  159. package/dist/api/effect/cache.js +2 -0
  160. package/dist/api/effect/cache.js.map +1 -0
  161. package/dist/api/effect/channels.d.ts +231 -0
  162. package/dist/api/effect/channels.d.ts.map +1 -0
  163. package/dist/api/effect/channels.js +2 -0
  164. package/dist/api/effect/channels.js.map +1 -0
  165. package/dist/api/effect/client.d.ts +622 -0
  166. package/dist/api/effect/client.d.ts.map +1 -0
  167. package/dist/api/effect/client.js +191 -0
  168. package/dist/api/effect/client.js.map +1 -0
  169. package/dist/api/effect/collectors.d.ts +90 -0
  170. package/dist/api/effect/collectors.d.ts.map +1 -0
  171. package/dist/api/effect/collectors.js +2 -0
  172. package/dist/api/effect/collectors.js.map +1 -0
  173. package/dist/api/effect/commands.d.ts +86 -0
  174. package/dist/api/effect/commands.d.ts.map +1 -0
  175. package/dist/api/effect/commands.js +87 -0
  176. package/dist/api/effect/commands.js.map +1 -0
  177. package/dist/api/effect/direct-messages.d.ts +102 -0
  178. package/dist/api/effect/direct-messages.d.ts.map +1 -0
  179. package/dist/api/effect/direct-messages.js +2 -0
  180. package/dist/api/effect/direct-messages.js.map +1 -0
  181. package/dist/api/effect/discovery.d.ts +68 -0
  182. package/dist/api/effect/discovery.d.ts.map +1 -0
  183. package/dist/api/effect/discovery.js +2 -0
  184. package/dist/api/effect/discovery.js.map +1 -0
  185. package/dist/api/effect/emojis.d.ts +77 -0
  186. package/dist/api/effect/emojis.d.ts.map +1 -0
  187. package/dist/api/effect/emojis.js +2 -0
  188. package/dist/api/effect/emojis.js.map +1 -0
  189. package/dist/api/effect/events.d.ts +78 -0
  190. package/dist/api/effect/events.d.ts.map +1 -0
  191. package/dist/api/effect/events.js +12 -0
  192. package/dist/api/effect/events.js.map +1 -0
  193. package/dist/api/effect/failures.d.ts +14 -0
  194. package/dist/api/effect/failures.d.ts.map +1 -0
  195. package/dist/api/effect/failures.js +2 -0
  196. package/dist/api/effect/failures.js.map +1 -0
  197. package/dist/api/effect/gateway.d.ts +63 -0
  198. package/dist/api/effect/gateway.d.ts.map +1 -0
  199. package/dist/api/effect/gateway.js +2 -0
  200. package/dist/api/effect/gateway.js.map +1 -0
  201. package/dist/api/effect/guards.d.ts +91 -0
  202. package/dist/api/effect/guards.d.ts.map +1 -0
  203. package/dist/api/effect/guards.js +94 -0
  204. package/dist/api/effect/guards.js.map +1 -0
  205. package/dist/api/effect/guilds.d.ts +221 -0
  206. package/dist/api/effect/guilds.d.ts.map +1 -0
  207. package/dist/api/effect/guilds.js +2 -0
  208. package/dist/api/effect/guilds.js.map +1 -0
  209. package/dist/api/effect/helpers.d.ts +300 -0
  210. package/dist/api/effect/helpers.d.ts.map +1 -0
  211. package/dist/api/effect/helpers.js +156 -0
  212. package/dist/api/effect/helpers.js.map +1 -0
  213. package/dist/api/effect/hierarchy.d.ts +26 -0
  214. package/dist/api/effect/hierarchy.d.ts.map +1 -0
  215. package/dist/api/effect/hierarchy.js +26 -0
  216. package/dist/api/effect/hierarchy.js.map +1 -0
  217. package/dist/api/effect/instance.d.ts +46 -0
  218. package/dist/api/effect/instance.d.ts.map +1 -0
  219. package/dist/api/effect/instance.js +8 -0
  220. package/dist/api/effect/instance.js.map +1 -0
  221. package/dist/api/effect/invites.d.ts +49 -0
  222. package/dist/api/effect/invites.d.ts.map +1 -0
  223. package/dist/api/effect/invites.js +2 -0
  224. package/dist/api/effect/invites.js.map +1 -0
  225. package/dist/api/effect/logging.d.ts +37 -0
  226. package/dist/api/effect/logging.d.ts.map +1 -0
  227. package/dist/api/effect/logging.js +2 -0
  228. package/dist/api/effect/logging.js.map +1 -0
  229. package/dist/api/effect/members.d.ts +433 -0
  230. package/dist/api/effect/members.d.ts.map +1 -0
  231. package/dist/api/effect/members.js +2 -0
  232. package/dist/api/effect/members.js.map +1 -0
  233. package/dist/api/effect/messages.d.ts +877 -0
  234. package/dist/api/effect/messages.d.ts.map +1 -0
  235. package/dist/api/effect/messages.js +2 -0
  236. package/dist/api/effect/messages.js.map +1 -0
  237. package/dist/api/effect/oauth.d.ts +148 -0
  238. package/dist/api/effect/oauth.d.ts.map +1 -0
  239. package/dist/api/effect/oauth.js +51 -0
  240. package/dist/api/effect/oauth.js.map +1 -0
  241. package/dist/api/effect/permissions.d.ts +41 -0
  242. package/dist/api/effect/permissions.d.ts.map +1 -0
  243. package/dist/api/effect/permissions.js +2 -0
  244. package/dist/api/effect/permissions.js.map +1 -0
  245. package/dist/api/effect/presence.d.ts +83 -0
  246. package/dist/api/effect/presence.d.ts.map +1 -0
  247. package/dist/api/effect/presence.js +2 -0
  248. package/dist/api/effect/presence.js.map +1 -0
  249. package/dist/api/effect/rest.d.ts +27 -0
  250. package/dist/api/effect/rest.d.ts.map +1 -0
  251. package/dist/api/effect/rest.js +2 -0
  252. package/dist/api/effect/rest.js.map +1 -0
  253. package/dist/api/effect/roles.d.ts +104 -0
  254. package/dist/api/effect/roles.d.ts.map +1 -0
  255. package/dist/api/effect/roles.js +2 -0
  256. package/dist/api/effect/roles.js.map +1 -0
  257. package/dist/api/effect/service.d.ts +76 -0
  258. package/dist/api/effect/service.d.ts.map +1 -0
  259. package/dist/api/effect/service.js +79 -0
  260. package/dist/api/effect/service.js.map +1 -0
  261. package/dist/api/effect/stickers.d.ts +81 -0
  262. package/dist/api/effect/stickers.d.ts.map +1 -0
  263. package/dist/api/effect/stickers.js +2 -0
  264. package/dist/api/effect/stickers.js.map +1 -0
  265. package/dist/api/effect/supervisor.d.ts +56 -0
  266. package/dist/api/effect/supervisor.d.ts.map +1 -0
  267. package/dist/api/effect/supervisor.js +58 -0
  268. package/dist/api/effect/supervisor.js.map +1 -0
  269. package/dist/api/effect/threads.d.ts +154 -0
  270. package/dist/api/effect/threads.d.ts.map +1 -0
  271. package/dist/api/effect/threads.js +2 -0
  272. package/dist/api/effect/threads.js.map +1 -0
  273. package/dist/api/effect/users.d.ts +62 -0
  274. package/dist/api/effect/users.d.ts.map +1 -0
  275. package/dist/api/effect/users.js +2 -0
  276. package/dist/api/effect/users.js.map +1 -0
  277. package/dist/api/effect/webhook-client.d.ts +140 -0
  278. package/dist/api/effect/webhook-client.d.ts.map +1 -0
  279. package/dist/api/effect/webhook-client.js +50 -0
  280. package/dist/api/effect/webhook-client.js.map +1 -0
  281. package/dist/api/effect/webhooks.d.ts +54 -0
  282. package/dist/api/effect/webhooks.d.ts.map +1 -0
  283. package/dist/api/effect/webhooks.js +2 -0
  284. package/dist/api/effect/webhooks.js.map +1 -0
  285. package/dist/api-errors.d.ts +609 -0
  286. package/dist/api-errors.d.ts.map +1 -0
  287. package/dist/api-errors.js +589 -0
  288. package/dist/api-errors.js.map +1 -0
  289. package/dist/application.d.ts +85 -0
  290. package/dist/application.d.ts.map +1 -0
  291. package/dist/application.js +44 -0
  292. package/dist/application.js.map +1 -0
  293. package/dist/assets.d.ts +197 -0
  294. package/dist/assets.d.ts.map +1 -0
  295. package/dist/assets.js +419 -0
  296. package/dist/assets.js.map +1 -0
  297. package/dist/attachments.d.ts +400 -0
  298. package/dist/attachments.d.ts.map +1 -0
  299. package/dist/attachments.js +88 -0
  300. package/dist/attachments.js.map +1 -0
  301. package/dist/audit-logs.d.ts +292 -0
  302. package/dist/audit-logs.d.ts.map +1 -0
  303. package/dist/audit-logs.js +46 -0
  304. package/dist/audit-logs.js.map +1 -0
  305. package/dist/bot-runner.d.ts +69 -0
  306. package/dist/bot-runner.d.ts.map +1 -0
  307. package/dist/bot-runner.js +41 -0
  308. package/dist/bot-runner.js.map +1 -0
  309. package/dist/builders.d.ts +153 -0
  310. package/dist/builders.d.ts.map +1 -0
  311. package/dist/builders.js +326 -0
  312. package/dist/builders.js.map +1 -0
  313. package/dist/cache.d.ts +187 -0
  314. package/dist/cache.d.ts.map +1 -0
  315. package/dist/cache.js +2 -0
  316. package/dist/cache.js.map +1 -0
  317. package/dist/channels.d.ts +903 -0
  318. package/dist/channels.d.ts.map +1 -0
  319. package/dist/channels.js +125 -0
  320. package/dist/channels.js.map +1 -0
  321. package/dist/cli.d.ts +9 -0
  322. package/dist/cli.d.ts.map +1 -0
  323. package/dist/cli.js +65 -0
  324. package/dist/cli.js.map +1 -0
  325. package/dist/client.d.ts +645 -0
  326. package/dist/client.d.ts.map +1 -0
  327. package/dist/client.js +2 -0
  328. package/dist/client.js.map +1 -0
  329. package/dist/collectors.d.ts +205 -0
  330. package/dist/collectors.d.ts.map +1 -0
  331. package/dist/collectors.js +71 -0
  332. package/dist/collectors.js.map +1 -0
  333. package/dist/colors.d.ts +55 -0
  334. package/dist/colors.d.ts.map +1 -0
  335. package/dist/colors.js +40 -0
  336. package/dist/colors.js.map +1 -0
  337. package/dist/command-arguments.d.ts +353 -0
  338. package/dist/command-arguments.d.ts.map +1 -0
  339. package/dist/command-arguments.js +2 -0
  340. package/dist/command-arguments.js.map +1 -0
  341. package/dist/command-help.d.ts +54 -0
  342. package/dist/command-help.d.ts.map +1 -0
  343. package/dist/command-help.js +2 -0
  344. package/dist/command-help.js.map +1 -0
  345. package/dist/commands.d.ts +328 -0
  346. package/dist/commands.d.ts.map +1 -0
  347. package/dist/commands.js +62 -0
  348. package/dist/commands.js.map +1 -0
  349. package/dist/counts.d.ts +124 -0
  350. package/dist/counts.d.ts.map +1 -0
  351. package/dist/counts.js +52 -0
  352. package/dist/counts.js.map +1 -0
  353. package/dist/default-commands.d.ts +400 -0
  354. package/dist/default-commands.d.ts.map +1 -0
  355. package/dist/default-commands.js +488 -0
  356. package/dist/default-commands.js.map +1 -0
  357. package/dist/default-supervisor.d.ts +111 -0
  358. package/dist/default-supervisor.d.ts.map +1 -0
  359. package/dist/default-supervisor.js +277 -0
  360. package/dist/default-supervisor.js.map +1 -0
  361. package/dist/discovery.d.ts +223 -0
  362. package/dist/discovery.d.ts.map +1 -0
  363. package/dist/discovery.js +18 -0
  364. package/dist/discovery.js.map +1 -0
  365. package/dist/effect-testing.d.ts +388 -0
  366. package/dist/effect-testing.d.ts.map +1 -0
  367. package/dist/effect-testing.js +261 -0
  368. package/dist/effect-testing.js.map +1 -0
  369. package/dist/effect.d.ts +220 -0
  370. package/dist/effect.d.ts.map +1 -0
  371. package/dist/effect.js +101 -0
  372. package/dist/effect.js.map +1 -0
  373. package/dist/embeds.d.ts +243 -0
  374. package/dist/embeds.d.ts.map +1 -0
  375. package/dist/embeds.js +2 -0
  376. package/dist/embeds.js.map +1 -0
  377. package/dist/error-tools.d.ts +101 -0
  378. package/dist/error-tools.d.ts.map +1 -0
  379. package/dist/error-tools.js +125 -0
  380. package/dist/error-tools.js.map +1 -0
  381. package/dist/errors.d.ts +386 -0
  382. package/dist/errors.d.ts.map +1 -0
  383. package/dist/errors.js +440 -0
  384. package/dist/errors.js.map +1 -0
  385. package/dist/events.d.ts +798 -0
  386. package/dist/events.d.ts.map +1 -0
  387. package/dist/events.js +2 -0
  388. package/dist/events.js.map +1 -0
  389. package/dist/expressions.d.ts +188 -0
  390. package/dist/expressions.d.ts.map +1 -0
  391. package/dist/expressions.js +2 -0
  392. package/dist/expressions.js.map +1 -0
  393. package/dist/failures.d.ts +53 -0
  394. package/dist/failures.d.ts.map +1 -0
  395. package/dist/failures.js +2 -0
  396. package/dist/failures.js.map +1 -0
  397. package/dist/gateway.d.ts +48 -0
  398. package/dist/gateway.d.ts.map +1 -0
  399. package/dist/gateway.js +60 -0
  400. package/dist/gateway.js.map +1 -0
  401. package/dist/guilds.d.ts +923 -0
  402. package/dist/guilds.d.ts.map +1 -0
  403. package/dist/guilds.js +204 -0
  404. package/dist/guilds.js.map +1 -0
  405. package/dist/helpers.d.ts +423 -0
  406. package/dist/helpers.d.ts.map +1 -0
  407. package/dist/helpers.js +434 -0
  408. package/dist/helpers.js.map +1 -0
  409. package/dist/index.d.ts +228 -0
  410. package/dist/index.d.ts.map +1 -0
  411. package/dist/index.js +109 -0
  412. package/dist/index.js.map +1 -0
  413. package/dist/input-validation.d.ts +51 -0
  414. package/dist/input-validation.d.ts.map +1 -0
  415. package/dist/input-validation.js +34 -0
  416. package/dist/input-validation.js.map +1 -0
  417. package/dist/instance.d.ts +101 -0
  418. package/dist/instance.d.ts.map +1 -0
  419. package/dist/instance.js +2 -0
  420. package/dist/instance.js.map +1 -0
  421. package/dist/internal/agents-section.d.ts +22 -0
  422. package/dist/internal/agents-section.d.ts.map +1 -0
  423. package/dist/internal/agents-section.js +101 -0
  424. package/dist/internal/agents-section.js.map +1 -0
  425. package/dist/internal/application.d.ts +16 -0
  426. package/dist/internal/application.d.ts.map +1 -0
  427. package/dist/internal/application.js +33 -0
  428. package/dist/internal/application.js.map +1 -0
  429. package/dist/internal/attachment-refresh.d.ts +18 -0
  430. package/dist/internal/attachment-refresh.d.ts.map +1 -0
  431. package/dist/internal/attachment-refresh.js +39 -0
  432. package/dist/internal/attachment-refresh.js.map +1 -0
  433. package/dist/internal/attachments.d.ts +45 -0
  434. package/dist/internal/attachments.d.ts.map +1 -0
  435. package/dist/internal/attachments.js +230 -0
  436. package/dist/internal/attachments.js.map +1 -0
  437. package/dist/internal/audit-logs.d.ts +13 -0
  438. package/dist/internal/audit-logs.d.ts.map +1 -0
  439. package/dist/internal/audit-logs.js +295 -0
  440. package/dist/internal/audit-logs.js.map +1 -0
  441. package/dist/internal/audit.d.ts +12 -0
  442. package/dist/internal/audit.d.ts.map +1 -0
  443. package/dist/internal/audit.js +22 -0
  444. package/dist/internal/audit.js.map +1 -0
  445. package/dist/internal/binding/default-adapters.d.ts +22 -0
  446. package/dist/internal/binding/default-adapters.d.ts.map +1 -0
  447. package/dist/internal/binding/default-adapters.js +304 -0
  448. package/dist/internal/binding/default-adapters.js.map +1 -0
  449. package/dist/internal/binding/default.d.ts +45 -0
  450. package/dist/internal/binding/default.d.ts.map +1 -0
  451. package/dist/internal/binding/default.js +86 -0
  452. package/dist/internal/binding/default.js.map +1 -0
  453. package/dist/internal/binding/execute.d.ts +51 -0
  454. package/dist/internal/binding/execute.d.ts.map +1 -0
  455. package/dist/internal/binding/execute.js +123 -0
  456. package/dist/internal/binding/execute.js.map +1 -0
  457. package/dist/internal/binding/native-adapters.d.ts +23 -0
  458. package/dist/internal/binding/native-adapters.d.ts.map +1 -0
  459. package/dist/internal/binding/native-adapters.js +90 -0
  460. package/dist/internal/binding/native-adapters.js.map +1 -0
  461. package/dist/internal/binding/native.d.ts +41 -0
  462. package/dist/internal/binding/native.d.ts.map +1 -0
  463. package/dist/internal/binding/native.js +34 -0
  464. package/dist/internal/binding/native.js.map +1 -0
  465. package/dist/internal/binding/operations.d.ts +361 -0
  466. package/dist/internal/binding/operations.d.ts.map +1 -0
  467. package/dist/internal/binding/operations.js +272 -0
  468. package/dist/internal/binding/operations.js.map +1 -0
  469. package/dist/internal/bot-runner.d.ts +65 -0
  470. package/dist/internal/bot-runner.d.ts.map +1 -0
  471. package/dist/internal/bot-runner.js +363 -0
  472. package/dist/internal/bot-runner.js.map +1 -0
  473. package/dist/internal/cache-changes.d.ts +43 -0
  474. package/dist/internal/cache-changes.d.ts.map +1 -0
  475. package/dist/internal/cache-changes.js +320 -0
  476. package/dist/internal/cache-changes.js.map +1 -0
  477. package/dist/internal/cache.d.ts +57 -0
  478. package/dist/internal/cache.d.ts.map +1 -0
  479. package/dist/internal/cache.js +318 -0
  480. package/dist/internal/cache.js.map +1 -0
  481. package/dist/internal/calls.d.ts +16 -0
  482. package/dist/internal/calls.d.ts.map +1 -0
  483. package/dist/internal/calls.js +108 -0
  484. package/dist/internal/calls.js.map +1 -0
  485. package/dist/internal/channel-cache.d.ts +69 -0
  486. package/dist/internal/channel-cache.d.ts.map +1 -0
  487. package/dist/internal/channel-cache.js +413 -0
  488. package/dist/internal/channel-cache.js.map +1 -0
  489. package/dist/internal/channel-decode.d.ts +44 -0
  490. package/dist/internal/channel-decode.d.ts.map +1 -0
  491. package/dist/internal/channel-decode.js +377 -0
  492. package/dist/internal/channel-decode.js.map +1 -0
  493. package/dist/internal/channels.d.ts +60 -0
  494. package/dist/internal/channels.d.ts.map +1 -0
  495. package/dist/internal/channels.js +605 -0
  496. package/dist/internal/channels.js.map +1 -0
  497. package/dist/internal/client/backoff.d.ts +42 -0
  498. package/dist/internal/client/backoff.d.ts.map +1 -0
  499. package/dist/internal/client/backoff.js +36 -0
  500. package/dist/internal/client/backoff.js.map +1 -0
  501. package/dist/internal/client/configuration-fields.d.ts +14 -0
  502. package/dist/internal/client/configuration-fields.d.ts.map +1 -0
  503. package/dist/internal/client/configuration-fields.js +11 -0
  504. package/dist/internal/client/configuration-fields.js.map +1 -0
  505. package/dist/internal/client/drain.d.ts +33 -0
  506. package/dist/internal/client/drain.d.ts.map +1 -0
  507. package/dist/internal/client/drain.js +109 -0
  508. package/dist/internal/client/drain.js.map +1 -0
  509. package/dist/internal/client/intake.d.ts +27 -0
  510. package/dist/internal/client/intake.d.ts.map +1 -0
  511. package/dist/internal/client/intake.js +198 -0
  512. package/dist/internal/client/intake.js.map +1 -0
  513. package/dist/internal/client/lifetime.d.ts +35 -0
  514. package/dist/internal/client/lifetime.d.ts.map +1 -0
  515. package/dist/internal/client/lifetime.js +109 -0
  516. package/dist/internal/client/lifetime.js.map +1 -0
  517. package/dist/internal/client/shard-loop.d.ts +93 -0
  518. package/dist/internal/client/shard-loop.d.ts.map +1 -0
  519. package/dist/internal/client/shard-loop.js +452 -0
  520. package/dist/internal/client/shard-loop.js.map +1 -0
  521. package/dist/internal/client-registry.d.ts +26 -0
  522. package/dist/internal/client-registry.d.ts.map +1 -0
  523. package/dist/internal/client-registry.js +11 -0
  524. package/dist/internal/client-registry.js.map +1 -0
  525. package/dist/internal/client.d.ts +189 -0
  526. package/dist/internal/client.d.ts.map +1 -0
  527. package/dist/internal/client.js +1935 -0
  528. package/dist/internal/client.js.map +1 -0
  529. package/dist/internal/clock.d.ts +9 -0
  530. package/dist/internal/clock.d.ts.map +1 -0
  531. package/dist/internal/clock.js +5 -0
  532. package/dist/internal/clock.js.map +1 -0
  533. package/dist/internal/code-catalogue.d.ts +712 -0
  534. package/dist/internal/code-catalogue.d.ts.map +1 -0
  535. package/dist/internal/code-catalogue.js +655 -0
  536. package/dist/internal/code-catalogue.js.map +1 -0
  537. package/dist/internal/collector.d.ts +34 -0
  538. package/dist/internal/collector.d.ts.map +1 -0
  539. package/dist/internal/collector.js +400 -0
  540. package/dist/internal/collector.js.map +1 -0
  541. package/dist/internal/command-arguments.d.ts +29 -0
  542. package/dist/internal/command-arguments.d.ts.map +1 -0
  543. package/dist/internal/command-arguments.js +484 -0
  544. package/dist/internal/command-arguments.js.map +1 -0
  545. package/dist/internal/command-guards.d.ts +57 -0
  546. package/dist/internal/command-guards.d.ts.map +1 -0
  547. package/dist/internal/command-guards.js +81 -0
  548. package/dist/internal/command-guards.js.map +1 -0
  549. package/dist/internal/command-help.d.ts +15 -0
  550. package/dist/internal/command-help.d.ts.map +1 -0
  551. package/dist/internal/command-help.js +121 -0
  552. package/dist/internal/command-help.js.map +1 -0
  553. package/dist/internal/commands.d.ts +212 -0
  554. package/dist/internal/commands.d.ts.map +1 -0
  555. package/dist/internal/commands.js +1004 -0
  556. package/dist/internal/commands.js.map +1 -0
  557. package/dist/internal/configuration.d.ts +86 -0
  558. package/dist/internal/configuration.d.ts.map +1 -0
  559. package/dist/internal/configuration.js +401 -0
  560. package/dist/internal/configuration.js.map +1 -0
  561. package/dist/internal/counts.d.ts +33 -0
  562. package/dist/internal/counts.d.ts.map +1 -0
  563. package/dist/internal/counts.js +348 -0
  564. package/dist/internal/counts.js.map +1 -0
  565. package/dist/internal/decode/primitives.d.ts +30 -0
  566. package/dist/internal/decode/primitives.d.ts.map +1 -0
  567. package/dist/internal/decode/primitives.js +56 -0
  568. package/dist/internal/decode/primitives.js.map +1 -0
  569. package/dist/internal/decode/timestamp.d.ts +13 -0
  570. package/dist/internal/decode/timestamp.d.ts.map +1 -0
  571. package/dist/internal/decode/timestamp.js +27 -0
  572. package/dist/internal/decode/timestamp.js.map +1 -0
  573. package/dist/internal/decode/trace.d.ts +11 -0
  574. package/dist/internal/decode/trace.d.ts.map +1 -0
  575. package/dist/internal/decode/trace.js +69 -0
  576. package/dist/internal/decode/trace.js.map +1 -0
  577. package/dist/internal/defects.d.ts +48 -0
  578. package/dist/internal/defects.d.ts.map +1 -0
  579. package/dist/internal/defects.js +100 -0
  580. package/dist/internal/defects.js.map +1 -0
  581. package/dist/internal/effect-failures.d.ts +12 -0
  582. package/dist/internal/effect-failures.d.ts.map +1 -0
  583. package/dist/internal/effect-failures.js +45 -0
  584. package/dist/internal/effect-failures.js.map +1 -0
  585. package/dist/internal/embeds.d.ts +12 -0
  586. package/dist/internal/embeds.d.ts.map +1 -0
  587. package/dist/internal/embeds.js +308 -0
  588. package/dist/internal/embeds.js.map +1 -0
  589. package/dist/internal/events.d.ts +156 -0
  590. package/dist/internal/events.d.ts.map +1 -0
  591. package/dist/internal/events.js +1071 -0
  592. package/dist/internal/events.js.map +1 -0
  593. package/dist/internal/expiry-queue.d.ts +42 -0
  594. package/dist/internal/expiry-queue.d.ts.map +1 -0
  595. package/dist/internal/expiry-queue.js +138 -0
  596. package/dist/internal/expiry-queue.js.map +1 -0
  597. package/dist/internal/expressions.d.ts +35 -0
  598. package/dist/internal/expressions.d.ts.map +1 -0
  599. package/dist/internal/expressions.js +311 -0
  600. package/dist/internal/expressions.js.map +1 -0
  601. package/dist/internal/failures.d.ts +107 -0
  602. package/dist/internal/failures.d.ts.map +1 -0
  603. package/dist/internal/failures.js +416 -0
  604. package/dist/internal/failures.js.map +1 -0
  605. package/dist/internal/field-text.d.ts +10 -0
  606. package/dist/internal/field-text.d.ts.map +1 -0
  607. package/dist/internal/field-text.js +37 -0
  608. package/dist/internal/field-text.js.map +1 -0
  609. package/dist/internal/gateway/commands.d.ts +92 -0
  610. package/dist/internal/gateway/commands.d.ts.map +1 -0
  611. package/dist/internal/gateway/commands.js +223 -0
  612. package/dist/internal/gateway/commands.js.map +1 -0
  613. package/dist/internal/gateway/dispatch-table.d.ts +42 -0
  614. package/dist/internal/gateway/dispatch-table.d.ts.map +1 -0
  615. package/dist/internal/gateway/dispatch-table.js +288 -0
  616. package/dist/internal/gateway/dispatch-table.js.map +1 -0
  617. package/dist/internal/gateway/event-dispatches.d.ts +97 -0
  618. package/dist/internal/gateway/event-dispatches.d.ts.map +1 -0
  619. package/dist/internal/gateway/event-dispatches.js +172 -0
  620. package/dist/internal/gateway/event-dispatches.js.map +1 -0
  621. package/dist/internal/gateway/frames.d.ts +45 -0
  622. package/dist/internal/gateway/frames.d.ts.map +1 -0
  623. package/dist/internal/gateway/frames.js +121 -0
  624. package/dist/internal/gateway/frames.js.map +1 -0
  625. package/dist/internal/gateway/options.d.ts +24 -0
  626. package/dist/internal/gateway/options.d.ts.map +1 -0
  627. package/dist/internal/gateway/options.js +103 -0
  628. package/dist/internal/gateway/options.js.map +1 -0
  629. package/dist/internal/gateway/session.d.ts +104 -0
  630. package/dist/internal/gateway/session.d.ts.map +1 -0
  631. package/dist/internal/gateway/session.js +420 -0
  632. package/dist/internal/gateway/session.js.map +1 -0
  633. package/dist/internal/gateway-requests.d.ts +10 -0
  634. package/dist/internal/gateway-requests.d.ts.map +1 -0
  635. package/dist/internal/gateway-requests.js +26 -0
  636. package/dist/internal/gateway-requests.js.map +1 -0
  637. package/dist/internal/gateway.d.ts +19 -0
  638. package/dist/internal/gateway.d.ts.map +1 -0
  639. package/dist/internal/gateway.js +11 -0
  640. package/dist/internal/gateway.js.map +1 -0
  641. package/dist/internal/guild-cache.d.ts +69 -0
  642. package/dist/internal/guild-cache.d.ts.map +1 -0
  643. package/dist/internal/guild-cache.js +402 -0
  644. package/dist/internal/guild-cache.js.map +1 -0
  645. package/dist/internal/guild-discovery.d.ts +15 -0
  646. package/dist/internal/guild-discovery.d.ts.map +1 -0
  647. package/dist/internal/guild-discovery.js +258 -0
  648. package/dist/internal/guild-discovery.js.map +1 -0
  649. package/dist/internal/guild-lifecycle.d.ts +18 -0
  650. package/dist/internal/guild-lifecycle.d.ts.map +1 -0
  651. package/dist/internal/guild-lifecycle.js +119 -0
  652. package/dist/internal/guild-lifecycle.js.map +1 -0
  653. package/dist/internal/guild-settings.d.ts +11 -0
  654. package/dist/internal/guild-settings.d.ts.map +1 -0
  655. package/dist/internal/guild-settings.js +150 -0
  656. package/dist/internal/guild-settings.js.map +1 -0
  657. package/dist/internal/guilds.d.ts +94 -0
  658. package/dist/internal/guilds.d.ts.map +1 -0
  659. package/dist/internal/guilds.js +785 -0
  660. package/dist/internal/guilds.js.map +1 -0
  661. package/dist/internal/init-command.d.ts +54 -0
  662. package/dist/internal/init-command.d.ts.map +1 -0
  663. package/dist/internal/init-command.js +248 -0
  664. package/dist/internal/init-command.js.map +1 -0
  665. package/dist/internal/instance.d.ts +69 -0
  666. package/dist/internal/instance.d.ts.map +1 -0
  667. package/dist/internal/instance.js +455 -0
  668. package/dist/internal/instance.js.map +1 -0
  669. package/dist/internal/invalid-callback-return.d.ts +3 -0
  670. package/dist/internal/invalid-callback-return.d.ts.map +1 -0
  671. package/dist/internal/invalid-callback-return.js +26 -0
  672. package/dist/internal/invalid-callback-return.js.map +1 -0
  673. package/dist/internal/invites.d.ts +19 -0
  674. package/dist/internal/invites.d.ts.map +1 -0
  675. package/dist/internal/invites.js +182 -0
  676. package/dist/internal/invites.js.map +1 -0
  677. package/dist/internal/logging.d.ts +129 -0
  678. package/dist/internal/logging.d.ts.map +1 -0
  679. package/dist/internal/logging.js +868 -0
  680. package/dist/internal/logging.js.map +1 -0
  681. package/dist/internal/logical-scheduler.d.ts +27 -0
  682. package/dist/internal/logical-scheduler.d.ts.map +1 -0
  683. package/dist/internal/logical-scheduler.js +102 -0
  684. package/dist/internal/logical-scheduler.js.map +1 -0
  685. package/dist/internal/masking.d.ts +13 -0
  686. package/dist/internal/masking.d.ts.map +1 -0
  687. package/dist/internal/masking.js +235 -0
  688. package/dist/internal/masking.js.map +1 -0
  689. package/dist/internal/member-chunks.d.ts +96 -0
  690. package/dist/internal/member-chunks.d.ts.map +1 -0
  691. package/dist/internal/member-chunks.js +557 -0
  692. package/dist/internal/member-chunks.js.map +1 -0
  693. package/dist/internal/member-search-workflow.d.ts +19 -0
  694. package/dist/internal/member-search-workflow.d.ts.map +1 -0
  695. package/dist/internal/member-search-workflow.js +143 -0
  696. package/dist/internal/member-search-workflow.js.map +1 -0
  697. package/dist/internal/member-search.d.ts +20 -0
  698. package/dist/internal/member-search.d.ts.map +1 -0
  699. package/dist/internal/member-search.js +201 -0
  700. package/dist/internal/member-search.js.map +1 -0
  701. package/dist/internal/message-cleanup.d.ts +9 -0
  702. package/dist/internal/message-cleanup.d.ts.map +1 -0
  703. package/dist/internal/message-cleanup.js +368 -0
  704. package/dist/internal/message-cleanup.js.map +1 -0
  705. package/dist/internal/message-fields.d.ts +9 -0
  706. package/dist/internal/message-fields.d.ts.map +1 -0
  707. package/dist/internal/message-fields.js +55 -0
  708. package/dist/internal/message-fields.js.map +1 -0
  709. package/dist/internal/message-search-workflow.d.ts +14 -0
  710. package/dist/internal/message-search-workflow.d.ts.map +1 -0
  711. package/dist/internal/message-search-workflow.js +101 -0
  712. package/dist/internal/message-search-workflow.js.map +1 -0
  713. package/dist/internal/message-search.d.ts +19 -0
  714. package/dist/internal/message-search.d.ts.map +1 -0
  715. package/dist/internal/message-search.js +317 -0
  716. package/dist/internal/message-search.js.map +1 -0
  717. package/dist/internal/message.d.ts +34 -0
  718. package/dist/internal/message.d.ts.map +1 -0
  719. package/dist/internal/message.js +723 -0
  720. package/dist/internal/message.js.map +1 -0
  721. package/dist/internal/metrics.d.ts +16 -0
  722. package/dist/internal/metrics.d.ts.map +1 -0
  723. package/dist/internal/metrics.js +49 -0
  724. package/dist/internal/metrics.js.map +1 -0
  725. package/dist/internal/moderation.d.ts +20 -0
  726. package/dist/internal/moderation.d.ts.map +1 -0
  727. package/dist/internal/moderation.js +219 -0
  728. package/dist/internal/moderation.js.map +1 -0
  729. package/dist/internal/multipart.d.ts +10 -0
  730. package/dist/internal/multipart.d.ts.map +1 -0
  731. package/dist/internal/multipart.js +156 -0
  732. package/dist/internal/multipart.js.map +1 -0
  733. package/dist/internal/node-version.d.ts +10 -0
  734. package/dist/internal/node-version.d.ts.map +1 -0
  735. package/dist/internal/node-version.js +21 -0
  736. package/dist/internal/node-version.js.map +1 -0
  737. package/dist/internal/oauth.d.ts +29 -0
  738. package/dist/internal/oauth.d.ts.map +1 -0
  739. package/dist/internal/oauth.js +721 -0
  740. package/dist/internal/oauth.js.map +1 -0
  741. package/dist/internal/observer.d.ts +21 -0
  742. package/dist/internal/observer.d.ts.map +1 -0
  743. package/dist/internal/observer.js +48 -0
  744. package/dist/internal/observer.js.map +1 -0
  745. package/dist/internal/operation-signal.d.ts +9 -0
  746. package/dist/internal/operation-signal.d.ts.map +1 -0
  747. package/dist/internal/operation-signal.js +19 -0
  748. package/dist/internal/operation-signal.js.map +1 -0
  749. package/dist/internal/pagination.d.ts +67 -0
  750. package/dist/internal/pagination.d.ts.map +1 -0
  751. package/dist/internal/pagination.js +306 -0
  752. package/dist/internal/pagination.js.map +1 -0
  753. package/dist/internal/permission-requirements.d.ts +34 -0
  754. package/dist/internal/permission-requirements.d.ts.map +1 -0
  755. package/dist/internal/permission-requirements.js +204 -0
  756. package/dist/internal/permission-requirements.js.map +1 -0
  757. package/dist/internal/permissions.d.ts +28 -0
  758. package/dist/internal/permissions.d.ts.map +1 -0
  759. package/dist/internal/permissions.js +314 -0
  760. package/dist/internal/permissions.js.map +1 -0
  761. package/dist/internal/pins.d.ts +24 -0
  762. package/dist/internal/pins.d.ts.map +1 -0
  763. package/dist/internal/pins.js +83 -0
  764. package/dist/internal/pins.js.map +1 -0
  765. package/dist/internal/presence.d.ts +101 -0
  766. package/dist/internal/presence.d.ts.map +1 -0
  767. package/dist/internal/presence.js +581 -0
  768. package/dist/internal/presence.js.map +1 -0
  769. package/dist/internal/protocol/gateway.d.ts +116 -0
  770. package/dist/internal/protocol/gateway.d.ts.map +1 -0
  771. package/dist/internal/protocol/gateway.js +258 -0
  772. package/dist/internal/protocol/gateway.js.map +1 -0
  773. package/dist/internal/rate-limit-templates.d.ts +2 -0
  774. package/dist/internal/rate-limit-templates.d.ts.map +1 -0
  775. package/dist/internal/rate-limit-templates.js +132 -0
  776. package/dist/internal/rate-limit-templates.js.map +1 -0
  777. package/dist/internal/rate-limits.d.ts +32 -0
  778. package/dist/internal/rate-limits.d.ts.map +1 -0
  779. package/dist/internal/rate-limits.js +306 -0
  780. package/dist/internal/rate-limits.js.map +1 -0
  781. package/dist/internal/reaction-collector.d.ts +39 -0
  782. package/dist/internal/reaction-collector.d.ts.map +1 -0
  783. package/dist/internal/reaction-collector.js +441 -0
  784. package/dist/internal/reaction-collector.js.map +1 -0
  785. package/dist/internal/reaction-pages.d.ts +18 -0
  786. package/dist/internal/reaction-pages.d.ts.map +1 -0
  787. package/dist/internal/reaction-pages.js +213 -0
  788. package/dist/internal/reaction-pages.js.map +1 -0
  789. package/dist/internal/reactions.d.ts +30 -0
  790. package/dist/internal/reactions.d.ts.map +1 -0
  791. package/dist/internal/reactions.js +160 -0
  792. package/dist/internal/reactions.js.map +1 -0
  793. package/dist/internal/rejection-scope.d.ts +25 -0
  794. package/dist/internal/rejection-scope.d.ts.map +1 -0
  795. package/dist/internal/rejection-scope.js +103 -0
  796. package/dist/internal/rejection-scope.js.map +1 -0
  797. package/dist/internal/response-json.d.ts +12 -0
  798. package/dist/internal/response-json.d.ts.map +1 -0
  799. package/dist/internal/response-json.js +74 -0
  800. package/dist/internal/response-json.js.map +1 -0
  801. package/dist/internal/rest/admission.d.ts +77 -0
  802. package/dist/internal/rest/admission.d.ts.map +1 -0
  803. package/dist/internal/rest/admission.js +178 -0
  804. package/dist/internal/rest/admission.js.map +1 -0
  805. package/dist/internal/rest/attempt.d.ts +124 -0
  806. package/dist/internal/rest/attempt.d.ts.map +1 -0
  807. package/dist/internal/rest/attempt.js +410 -0
  808. package/dist/internal/rest/attempt.js.map +1 -0
  809. package/dist/internal/rest/classify.d.ts +93 -0
  810. package/dist/internal/rest/classify.d.ts.map +1 -0
  811. package/dist/internal/rest/classify.js +304 -0
  812. package/dist/internal/rest/classify.js.map +1 -0
  813. package/dist/internal/rest/download.d.ts +66 -0
  814. package/dist/internal/rest/download.d.ts.map +1 -0
  815. package/dist/internal/rest/download.js +552 -0
  816. package/dist/internal/rest/download.js.map +1 -0
  817. package/dist/internal/rest/options.d.ts +42 -0
  818. package/dist/internal/rest/options.d.ts.map +1 -0
  819. package/dist/internal/rest/options.js +99 -0
  820. package/dist/internal/rest/options.js.map +1 -0
  821. package/dist/internal/rest/owner.d.ts +154 -0
  822. package/dist/internal/rest/owner.d.ts.map +1 -0
  823. package/dist/internal/rest/owner.js +1292 -0
  824. package/dist/internal/rest/owner.js.map +1 -0
  825. package/dist/internal/rest/request.d.ts +31 -0
  826. package/dist/internal/rest/request.d.ts.map +1 -0
  827. package/dist/internal/rest/request.js +227 -0
  828. package/dist/internal/rest/request.js.map +1 -0
  829. package/dist/internal/rest.d.ts +10 -0
  830. package/dist/internal/rest.d.ts.map +1 -0
  831. package/dist/internal/rest.js +9 -0
  832. package/dist/internal/rest.js.map +1 -0
  833. package/dist/internal/retention-age.d.ts +11 -0
  834. package/dist/internal/retention-age.d.ts.map +1 -0
  835. package/dist/internal/retention-age.js +29 -0
  836. package/dist/internal/retention-age.js.map +1 -0
  837. package/dist/internal/role-hierarchy-workflow.d.ts +15 -0
  838. package/dist/internal/role-hierarchy-workflow.d.ts.map +1 -0
  839. package/dist/internal/role-hierarchy-workflow.js +122 -0
  840. package/dist/internal/role-hierarchy-workflow.js.map +1 -0
  841. package/dist/internal/role-hierarchy.d.ts +11 -0
  842. package/dist/internal/role-hierarchy.d.ts.map +1 -0
  843. package/dist/internal/role-hierarchy.js +87 -0
  844. package/dist/internal/role-hierarchy.js.map +1 -0
  845. package/dist/internal/scheduled-tasks.d.ts +46 -0
  846. package/dist/internal/scheduled-tasks.d.ts.map +1 -0
  847. package/dist/internal/scheduled-tasks.js +190 -0
  848. package/dist/internal/scheduled-tasks.js.map +1 -0
  849. package/dist/internal/sharding.d.ts +62 -0
  850. package/dist/internal/sharding.d.ts.map +1 -0
  851. package/dist/internal/sharding.js +205 -0
  852. package/dist/internal/sharding.js.map +1 -0
  853. package/dist/internal/starter-project.d.ts +27 -0
  854. package/dist/internal/starter-project.d.ts.map +1 -0
  855. package/dist/internal/starter-project.js +224 -0
  856. package/dist/internal/starter-project.js.map +1 -0
  857. package/dist/internal/suggest.d.ts +12 -0
  858. package/dist/internal/suggest.d.ts.map +1 -0
  859. package/dist/internal/suggest.js +51 -0
  860. package/dist/internal/suggest.js.map +1 -0
  861. package/dist/internal/supervisor.d.ts +95 -0
  862. package/dist/internal/supervisor.d.ts.map +1 -0
  863. package/dist/internal/supervisor.js +1829 -0
  864. package/dist/internal/supervisor.js.map +1 -0
  865. package/dist/internal/testing/discovery.d.ts +24 -0
  866. package/dist/internal/testing/discovery.d.ts.map +1 -0
  867. package/dist/internal/testing/discovery.js +22 -0
  868. package/dist/internal/testing/discovery.js.map +1 -0
  869. package/dist/internal/testing/errors.d.ts +43 -0
  870. package/dist/internal/testing/errors.d.ts.map +1 -0
  871. package/dist/internal/testing/errors.js +63 -0
  872. package/dist/internal/testing/errors.js.map +1 -0
  873. package/dist/internal/testing/fixtures.d.ts +477 -0
  874. package/dist/internal/testing/fixtures.d.ts.map +1 -0
  875. package/dist/internal/testing/fixtures.js +233 -0
  876. package/dist/internal/testing/fixtures.js.map +1 -0
  877. package/dist/internal/testing/gateway.d.ts +51 -0
  878. package/dist/internal/testing/gateway.d.ts.map +1 -0
  879. package/dist/internal/testing/gateway.js +265 -0
  880. package/dist/internal/testing/gateway.js.map +1 -0
  881. package/dist/internal/testing/harness.d.ts +60 -0
  882. package/dist/internal/testing/harness.d.ts.map +1 -0
  883. package/dist/internal/testing/harness.js +280 -0
  884. package/dist/internal/testing/harness.js.map +1 -0
  885. package/dist/internal/testing/http.d.ts +31 -0
  886. package/dist/internal/testing/http.d.ts.map +1 -0
  887. package/dist/internal/testing/http.js +347 -0
  888. package/dist/internal/testing/http.js.map +1 -0
  889. package/dist/internal/testing/types.d.ts +222 -0
  890. package/dist/internal/testing/types.d.ts.map +1 -0
  891. package/dist/internal/testing/types.js +2 -0
  892. package/dist/internal/testing/types.js.map +1 -0
  893. package/dist/internal/testing/wait.d.ts +16 -0
  894. package/dist/internal/testing/wait.d.ts.map +1 -0
  895. package/dist/internal/testing/wait.js +55 -0
  896. package/dist/internal/testing/wait.js.map +1 -0
  897. package/dist/internal/thread-events.d.ts +40 -0
  898. package/dist/internal/thread-events.d.ts.map +1 -0
  899. package/dist/internal/thread-events.js +121 -0
  900. package/dist/internal/thread-events.js.map +1 -0
  901. package/dist/internal/threads.d.ts +47 -0
  902. package/dist/internal/threads.d.ts.map +1 -0
  903. package/dist/internal/threads.js +587 -0
  904. package/dist/internal/threads.js.map +1 -0
  905. package/dist/internal/transfer-source.d.ts +29 -0
  906. package/dist/internal/transfer-source.d.ts.map +1 -0
  907. package/dist/internal/transfer-source.js +347 -0
  908. package/dist/internal/transfer-source.js.map +1 -0
  909. package/dist/internal/transport/http.d.ts +12 -0
  910. package/dist/internal/transport/http.d.ts.map +1 -0
  911. package/dist/internal/transport/http.js +44 -0
  912. package/dist/internal/transport/http.js.map +1 -0
  913. package/dist/internal/transport/index.d.ts +21 -0
  914. package/dist/internal/transport/index.d.ts.map +1 -0
  915. package/dist/internal/transport/index.js +15 -0
  916. package/dist/internal/transport/index.js.map +1 -0
  917. package/dist/internal/transport/socket.d.ts +51 -0
  918. package/dist/internal/transport/socket.d.ts.map +1 -0
  919. package/dist/internal/transport/socket.js +27 -0
  920. package/dist/internal/transport/socket.js.map +1 -0
  921. package/dist/internal/transport/user-agent.d.ts +7 -0
  922. package/dist/internal/transport/user-agent.d.ts.map +1 -0
  923. package/dist/internal/transport/user-agent.js +42 -0
  924. package/dist/internal/transport/user-agent.js.map +1 -0
  925. package/dist/internal/uploads.d.ts +23 -0
  926. package/dist/internal/uploads.d.ts.map +1 -0
  927. package/dist/internal/uploads.js +89 -0
  928. package/dist/internal/uploads.js.map +1 -0
  929. package/dist/internal/user-cache.d.ts +50 -0
  930. package/dist/internal/user-cache.d.ts.map +1 -0
  931. package/dist/internal/user-cache.js +273 -0
  932. package/dist/internal/user-cache.js.map +1 -0
  933. package/dist/internal/users.d.ts +41 -0
  934. package/dist/internal/users.d.ts.map +1 -0
  935. package/dist/internal/users.js +333 -0
  936. package/dist/internal/users.js.map +1 -0
  937. package/dist/internal/vanity-url.d.ts +11 -0
  938. package/dist/internal/vanity-url.d.ts.map +1 -0
  939. package/dist/internal/vanity-url.js +58 -0
  940. package/dist/internal/vanity-url.js.map +1 -0
  941. package/dist/internal/webhooks.d.ts +58 -0
  942. package/dist/internal/webhooks.d.ts.map +1 -0
  943. package/dist/internal/webhooks.js +490 -0
  944. package/dist/internal/webhooks.js.map +1 -0
  945. package/dist/invites.d.ts +86 -0
  946. package/dist/invites.d.ts.map +1 -0
  947. package/dist/invites.js +2 -0
  948. package/dist/invites.js.map +1 -0
  949. package/dist/logging.d.ts +228 -0
  950. package/dist/logging.d.ts.map +1 -0
  951. package/dist/logging.js +2 -0
  952. package/dist/logging.js.map +1 -0
  953. package/dist/member-chunks.d.ts +145 -0
  954. package/dist/member-chunks.d.ts.map +1 -0
  955. package/dist/member-chunks.js +68 -0
  956. package/dist/member-chunks.js.map +1 -0
  957. package/dist/member-search.d.ts +140 -0
  958. package/dist/member-search.d.ts.map +1 -0
  959. package/dist/member-search.js +14 -0
  960. package/dist/member-search.js.map +1 -0
  961. package/dist/message-cleanup.d.ts +227 -0
  962. package/dist/message-cleanup.d.ts.map +1 -0
  963. package/dist/message-cleanup.js +101 -0
  964. package/dist/message-cleanup.js.map +1 -0
  965. package/dist/message-errors.d.ts +172 -0
  966. package/dist/message-errors.d.ts.map +1 -0
  967. package/dist/message-errors.js +173 -0
  968. package/dist/message-errors.js.map +1 -0
  969. package/dist/message-search.d.ts +201 -0
  970. package/dist/message-search.d.ts.map +1 -0
  971. package/dist/message-search.js +2 -0
  972. package/dist/message-search.js.map +1 -0
  973. package/dist/messages.d.ts +694 -0
  974. package/dist/messages.d.ts.map +1 -0
  975. package/dist/messages.js +37 -0
  976. package/dist/messages.js.map +1 -0
  977. package/dist/native-commands.d.ts +451 -0
  978. package/dist/native-commands.d.ts.map +1 -0
  979. package/dist/native-commands.js +432 -0
  980. package/dist/native-commands.js.map +1 -0
  981. package/dist/native-supervisor.d.ts +125 -0
  982. package/dist/native-supervisor.d.ts.map +1 -0
  983. package/dist/native-supervisor.js +126 -0
  984. package/dist/native-supervisor.js.map +1 -0
  985. package/dist/oauth.d.ts +298 -0
  986. package/dist/oauth.d.ts.map +1 -0
  987. package/dist/oauth.js +128 -0
  988. package/dist/oauth.js.map +1 -0
  989. package/dist/observer.d.ts +111 -0
  990. package/dist/observer.d.ts.map +1 -0
  991. package/dist/observer.js +2 -0
  992. package/dist/observer.js.map +1 -0
  993. package/dist/pagination.d.ts +117 -0
  994. package/dist/pagination.d.ts.map +1 -0
  995. package/dist/pagination.js +61 -0
  996. package/dist/pagination.js.map +1 -0
  997. package/dist/permissions.d.ts +73 -0
  998. package/dist/permissions.d.ts.map +1 -0
  999. package/dist/permissions.js +2 -0
  1000. package/dist/permissions.js.map +1 -0
  1001. package/dist/pins.d.ts +62 -0
  1002. package/dist/pins.d.ts.map +1 -0
  1003. package/dist/pins.js +2 -0
  1004. package/dist/pins.js.map +1 -0
  1005. package/dist/presence.d.ts +84 -0
  1006. package/dist/presence.d.ts.map +1 -0
  1007. package/dist/presence.js +46 -0
  1008. package/dist/presence.js.map +1 -0
  1009. package/dist/reaction-pages.d.ts +99 -0
  1010. package/dist/reaction-pages.d.ts.map +1 -0
  1011. package/dist/reaction-pages.js +2 -0
  1012. package/dist/reaction-pages.js.map +1 -0
  1013. package/dist/reactions.d.ts +118 -0
  1014. package/dist/reactions.d.ts.map +1 -0
  1015. package/dist/reactions.js +2 -0
  1016. package/dist/reactions.js.map +1 -0
  1017. package/dist/rest.d.ts +260 -0
  1018. package/dist/rest.d.ts.map +1 -0
  1019. package/dist/rest.js +46 -0
  1020. package/dist/rest.js.map +1 -0
  1021. package/dist/role-hierarchy.d.ts +81 -0
  1022. package/dist/role-hierarchy.d.ts.map +1 -0
  1023. package/dist/role-hierarchy.js +53 -0
  1024. package/dist/role-hierarchy.js.map +1 -0
  1025. package/dist/sharding.d.ts +219 -0
  1026. package/dist/sharding.d.ts.map +1 -0
  1027. package/dist/sharding.js +86 -0
  1028. package/dist/sharding.js.map +1 -0
  1029. package/dist/supervisor.d.ts +392 -0
  1030. package/dist/supervisor.d.ts.map +1 -0
  1031. package/dist/supervisor.js +101 -0
  1032. package/dist/supervisor.js.map +1 -0
  1033. package/dist/testing.d.ts +258 -0
  1034. package/dist/testing.d.ts.map +1 -0
  1035. package/dist/testing.js +202 -0
  1036. package/dist/testing.js.map +1 -0
  1037. package/dist/text.d.ts +38 -0
  1038. package/dist/text.d.ts.map +1 -0
  1039. package/dist/text.js +46 -0
  1040. package/dist/text.js.map +1 -0
  1041. package/dist/threads.d.ts +258 -0
  1042. package/dist/threads.d.ts.map +1 -0
  1043. package/dist/threads.js +2 -0
  1044. package/dist/threads.js.map +1 -0
  1045. package/dist/users.d.ts +204 -0
  1046. package/dist/users.d.ts.map +1 -0
  1047. package/dist/users.js +44 -0
  1048. package/dist/users.js.map +1 -0
  1049. package/dist/webhooks.d.ts +423 -0
  1050. package/dist/webhooks.d.ts.map +1 -0
  1051. package/dist/webhooks.js +68 -0
  1052. package/dist/webhooks.js.map +1 -0
  1053. package/esm-only.cjs +3 -0
  1054. package/examples/starter/bot-effect.ts +17 -0
  1055. package/examples/starter/bot.js +13 -0
  1056. package/examples/starter/bot.ts +13 -0
  1057. package/package.json +82 -0
  1058. package/src/api/default/application.ts +40 -0
  1059. package/src/api/default/attachments.ts +106 -0
  1060. package/src/api/default/audit-logs.ts +58 -0
  1061. package/src/api/default/bot.ts +586 -0
  1062. package/src/api/default/cache.ts +106 -0
  1063. package/src/api/default/channels.ts +317 -0
  1064. package/src/api/default/client.ts +829 -0
  1065. package/src/api/default/collectors.ts +81 -0
  1066. package/src/api/default/commands.ts +92 -0
  1067. package/src/api/default/direct-messages.ts +143 -0
  1068. package/src/api/default/discovery.ts +103 -0
  1069. package/src/api/default/emojis.ts +125 -0
  1070. package/src/api/default/events.ts +144 -0
  1071. package/src/api/default/gateway.ts +67 -0
  1072. package/src/api/default/guards.ts +173 -0
  1073. package/src/api/default/guilds.ts +271 -0
  1074. package/src/api/default/helpers.ts +97 -0
  1075. package/src/api/default/instance.ts +49 -0
  1076. package/src/api/default/invites.ts +73 -0
  1077. package/src/api/default/logging.ts +37 -0
  1078. package/src/api/default/members.ts +550 -0
  1079. package/src/api/default/messages.ts +1053 -0
  1080. package/src/api/default/oauth.ts +293 -0
  1081. package/src/api/default/permissions.ts +47 -0
  1082. package/src/api/default/presence.ts +88 -0
  1083. package/src/api/default/rest.ts +30 -0
  1084. package/src/api/default/results.ts +44 -0
  1085. package/src/api/default/roles.ts +154 -0
  1086. package/src/api/default/stickers.ts +129 -0
  1087. package/src/api/default/supervisor.ts +53 -0
  1088. package/src/api/default/threads.ts +233 -0
  1089. package/src/api/default/users.ts +82 -0
  1090. package/src/api/default/webhook-client.ts +266 -0
  1091. package/src/api/default/webhooks.ts +89 -0
  1092. package/src/api/effect/application.ts +29 -0
  1093. package/src/api/effect/attachments.ts +100 -0
  1094. package/src/api/effect/audit-logs.ts +50 -0
  1095. package/src/api/effect/bot.ts +546 -0
  1096. package/src/api/effect/cache.ts +110 -0
  1097. package/src/api/effect/channels.ts +293 -0
  1098. package/src/api/effect/client.ts +792 -0
  1099. package/src/api/effect/collectors.ts +103 -0
  1100. package/src/api/effect/commands.ts +87 -0
  1101. package/src/api/effect/direct-messages.ts +119 -0
  1102. package/src/api/effect/discovery.ts +87 -0
  1103. package/src/api/effect/emojis.ts +108 -0
  1104. package/src/api/effect/events.ts +92 -0
  1105. package/src/api/effect/failures.ts +14 -0
  1106. package/src/api/effect/gateway.ts +63 -0
  1107. package/src/api/effect/guards.ts +194 -0
  1108. package/src/api/effect/guilds.ts +247 -0
  1109. package/src/api/effect/helpers.ts +359 -0
  1110. package/src/api/effect/hierarchy.ts +26 -0
  1111. package/src/api/effect/instance.ts +50 -0
  1112. package/src/api/effect/invites.ts +59 -0
  1113. package/src/api/effect/logging.ts +37 -0
  1114. package/src/api/effect/members.ts +521 -0
  1115. package/src/api/effect/messages.ts +1003 -0
  1116. package/src/api/effect/oauth.ts +208 -0
  1117. package/src/api/effect/permissions.ts +44 -0
  1118. package/src/api/effect/presence.ts +83 -0
  1119. package/src/api/effect/rest.ts +27 -0
  1120. package/src/api/effect/roles.ts +136 -0
  1121. package/src/api/effect/service.ts +104 -0
  1122. package/src/api/effect/stickers.ts +112 -0
  1123. package/src/api/effect/supervisor.ts +58 -0
  1124. package/src/api/effect/threads.ts +221 -0
  1125. package/src/api/effect/users.ts +66 -0
  1126. package/src/api/effect/webhook-client.ts +206 -0
  1127. package/src/api/effect/webhooks.ts +75 -0
  1128. package/src/api-errors.ts +985 -0
  1129. package/src/application.ts +103 -0
  1130. package/src/assets.ts +731 -0
  1131. package/src/attachments.ts +469 -0
  1132. package/src/audit-logs.ts +355 -0
  1133. package/src/bot-runner.ts +91 -0
  1134. package/src/builders.ts +390 -0
  1135. package/src/cache.ts +190 -0
  1136. package/src/channels.ts +1051 -0
  1137. package/src/cli.ts +60 -0
  1138. package/src/client.ts +663 -0
  1139. package/src/collectors.ts +248 -0
  1140. package/src/colors.ts +91 -0
  1141. package/src/command-arguments.ts +432 -0
  1142. package/src/command-help.ts +55 -0
  1143. package/src/commands.ts +403 -0
  1144. package/src/counts.ts +160 -0
  1145. package/src/default-commands.ts +1147 -0
  1146. package/src/default-supervisor.ts +484 -0
  1147. package/src/discovery.ts +241 -0
  1148. package/src/effect-testing.ts +603 -0
  1149. package/src/effect.ts +751 -0
  1150. package/src/embeds.ts +253 -0
  1151. package/src/error-tools.ts +191 -0
  1152. package/src/errors.ts +849 -0
  1153. package/src/events.ts +830 -0
  1154. package/src/expressions.ts +198 -0
  1155. package/src/failures.ts +55 -0
  1156. package/src/gateway.ts +86 -0
  1157. package/src/guilds.ts +1108 -0
  1158. package/src/helpers.ts +836 -0
  1159. package/src/index.ts +796 -0
  1160. package/src/input-validation.ts +94 -0
  1161. package/src/instance.ts +111 -0
  1162. package/src/internal/agents-section.ts +114 -0
  1163. package/src/internal/application.ts +51 -0
  1164. package/src/internal/attachment-refresh.ts +57 -0
  1165. package/src/internal/attachments.ts +313 -0
  1166. package/src/internal/audit-logs.ts +336 -0
  1167. package/src/internal/audit.ts +33 -0
  1168. package/src/internal/binding/default-adapters.ts +482 -0
  1169. package/src/internal/binding/default.ts +155 -0
  1170. package/src/internal/binding/execute.ts +221 -0
  1171. package/src/internal/binding/native-adapters.ts +199 -0
  1172. package/src/internal/binding/native.ts +72 -0
  1173. package/src/internal/binding/operations.ts +1171 -0
  1174. package/src/internal/bot-runner.ts +480 -0
  1175. package/src/internal/cache-changes.ts +363 -0
  1176. package/src/internal/cache.ts +323 -0
  1177. package/src/internal/calls.ts +119 -0
  1178. package/src/internal/channel-cache.ts +435 -0
  1179. package/src/internal/channel-decode.ts +399 -0
  1180. package/src/internal/channels.ts +874 -0
  1181. package/src/internal/client/backoff.ts +69 -0
  1182. package/src/internal/client/configuration-fields.ts +18 -0
  1183. package/src/internal/client/drain.ts +150 -0
  1184. package/src/internal/client/intake.ts +228 -0
  1185. package/src/internal/client/lifetime.ts +165 -0
  1186. package/src/internal/client/shard-loop.ts +586 -0
  1187. package/src/internal/client-registry.ts +35 -0
  1188. package/src/internal/client.ts +2448 -0
  1189. package/src/internal/clock.ts +11 -0
  1190. package/src/internal/code-catalogue.ts +739 -0
  1191. package/src/internal/collector.ts +452 -0
  1192. package/src/internal/command-arguments.ts +585 -0
  1193. package/src/internal/command-guards.ts +96 -0
  1194. package/src/internal/command-help.ts +156 -0
  1195. package/src/internal/commands.ts +1319 -0
  1196. package/src/internal/configuration.ts +529 -0
  1197. package/src/internal/counts.ts +471 -0
  1198. package/src/internal/decode/primitives.ts +67 -0
  1199. package/src/internal/decode/timestamp.ts +29 -0
  1200. package/src/internal/decode/trace.ts +65 -0
  1201. package/src/internal/defects.ts +115 -0
  1202. package/src/internal/effect-failures.ts +65 -0
  1203. package/src/internal/embeds.ts +355 -0
  1204. package/src/internal/events.ts +1345 -0
  1205. package/src/internal/expiry-queue.ts +148 -0
  1206. package/src/internal/expressions.ts +415 -0
  1207. package/src/internal/failures.ts +492 -0
  1208. package/src/internal/field-text.ts +40 -0
  1209. package/src/internal/gateway/commands.ts +328 -0
  1210. package/src/internal/gateway/dispatch-table.ts +383 -0
  1211. package/src/internal/gateway/event-dispatches.ts +201 -0
  1212. package/src/internal/gateway/frames.ts +176 -0
  1213. package/src/internal/gateway/options.ts +144 -0
  1214. package/src/internal/gateway/session.ts +625 -0
  1215. package/src/internal/gateway-requests.ts +26 -0
  1216. package/src/internal/gateway.ts +22 -0
  1217. package/src/internal/guild-cache.ts +424 -0
  1218. package/src/internal/guild-discovery.ts +332 -0
  1219. package/src/internal/guild-lifecycle.ts +128 -0
  1220. package/src/internal/guild-settings.ts +209 -0
  1221. package/src/internal/guilds.ts +949 -0
  1222. package/src/internal/init-command.ts +305 -0
  1223. package/src/internal/instance.ts +645 -0
  1224. package/src/internal/invalid-callback-return.ts +28 -0
  1225. package/src/internal/invites.ts +234 -0
  1226. package/src/internal/logging.ts +1007 -0
  1227. package/src/internal/logical-scheduler.ts +139 -0
  1228. package/src/internal/masking.ts +224 -0
  1229. package/src/internal/member-chunks.ts +649 -0
  1230. package/src/internal/member-search-workflow.ts +237 -0
  1231. package/src/internal/member-search.ts +272 -0
  1232. package/src/internal/message-cleanup.ts +515 -0
  1233. package/src/internal/message-fields.ts +71 -0
  1234. package/src/internal/message-search-workflow.ts +166 -0
  1235. package/src/internal/message-search.ts +476 -0
  1236. package/src/internal/message.ts +879 -0
  1237. package/src/internal/metrics.ts +55 -0
  1238. package/src/internal/moderation.ts +288 -0
  1239. package/src/internal/multipart.ts +171 -0
  1240. package/src/internal/node-version.ts +22 -0
  1241. package/src/internal/oauth.ts +1146 -0
  1242. package/src/internal/observer.ts +62 -0
  1243. package/src/internal/operation-signal.ts +26 -0
  1244. package/src/internal/pagination.ts +494 -0
  1245. package/src/internal/permission-requirements.ts +359 -0
  1246. package/src/internal/permissions.ts +417 -0
  1247. package/src/internal/pins.ts +115 -0
  1248. package/src/internal/presence.ts +745 -0
  1249. package/src/internal/protocol/gateway.ts +299 -0
  1250. package/src/internal/rate-limit-templates.ts +138 -0
  1251. package/src/internal/rate-limits.ts +346 -0
  1252. package/src/internal/reaction-collector.ts +499 -0
  1253. package/src/internal/reaction-pages.ts +260 -0
  1254. package/src/internal/reactions.ts +174 -0
  1255. package/src/internal/rejection-scope.ts +119 -0
  1256. package/src/internal/response-json.ts +76 -0
  1257. package/src/internal/rest/admission.ts +210 -0
  1258. package/src/internal/rest/attempt.ts +617 -0
  1259. package/src/internal/rest/classify.ts +391 -0
  1260. package/src/internal/rest/download.ts +658 -0
  1261. package/src/internal/rest/options.ts +145 -0
  1262. package/src/internal/rest/owner.ts +1828 -0
  1263. package/src/internal/rest/request.ts +289 -0
  1264. package/src/internal/rest.ts +9 -0
  1265. package/src/internal/retention-age.ts +33 -0
  1266. package/src/internal/role-hierarchy-workflow.ts +150 -0
  1267. package/src/internal/role-hierarchy.ts +93 -0
  1268. package/src/internal/scheduled-tasks.ts +217 -0
  1269. package/src/internal/sharding.ts +270 -0
  1270. package/src/internal/starter-project.ts +251 -0
  1271. package/src/internal/suggest.ts +50 -0
  1272. package/src/internal/supervisor.ts +2253 -0
  1273. package/src/internal/testing/discovery.ts +23 -0
  1274. package/src/internal/testing/errors.ts +67 -0
  1275. package/src/internal/testing/fixtures.ts +714 -0
  1276. package/src/internal/testing/gateway.ts +305 -0
  1277. package/src/internal/testing/harness.ts +328 -0
  1278. package/src/internal/testing/http.ts +395 -0
  1279. package/src/internal/testing/types.ts +240 -0
  1280. package/src/internal/testing/wait.ts +63 -0
  1281. package/src/internal/thread-events.ts +128 -0
  1282. package/src/internal/threads.ts +718 -0
  1283. package/src/internal/transfer-source.ts +359 -0
  1284. package/src/internal/transport/http.ts +46 -0
  1285. package/src/internal/transport/index.ts +23 -0
  1286. package/src/internal/transport/socket.ts +71 -0
  1287. package/src/internal/transport/user-agent.ts +46 -0
  1288. package/src/internal/uploads.ts +111 -0
  1289. package/src/internal/user-cache.ts +294 -0
  1290. package/src/internal/users.ts +402 -0
  1291. package/src/internal/vanity-url.ts +80 -0
  1292. package/src/internal/webhooks.ts +690 -0
  1293. package/src/invites.ts +87 -0
  1294. package/src/logging.ts +247 -0
  1295. package/src/member-chunks.ts +195 -0
  1296. package/src/member-search.ts +152 -0
  1297. package/src/message-cleanup.ts +308 -0
  1298. package/src/message-errors.ts +245 -0
  1299. package/src/message-search.ts +213 -0
  1300. package/src/messages.ts +768 -0
  1301. package/src/native-commands.ts +1249 -0
  1302. package/src/native-supervisor.ts +345 -0
  1303. package/src/oauth.ts +413 -0
  1304. package/src/observer.ts +118 -0
  1305. package/src/pagination.ts +172 -0
  1306. package/src/permissions.ts +74 -0
  1307. package/src/pins.ts +65 -0
  1308. package/src/presence.ts +124 -0
  1309. package/src/reaction-pages.ts +106 -0
  1310. package/src/reactions.ts +126 -0
  1311. package/src/rest.ts +282 -0
  1312. package/src/role-hierarchy.ts +127 -0
  1313. package/src/sharding.ts +272 -0
  1314. package/src/supervisor.ts +460 -0
  1315. package/src/testing.ts +424 -0
  1316. package/src/text.ts +76 -0
  1317. package/src/threads.ts +274 -0
  1318. package/src/users.ts +237 -0
  1319. package/src/webhooks.ts +512 -0
@@ -0,0 +1,2253 @@
1
+ /**
2
+ * Local supervisor: Forked child clients with fixed or computed assignments, Identify coordination, restarts, child
3
+ * diagnostics and output forwarding.
4
+ * Invariant: Assignments are fixed once known: At creation, or at start after one community count for totalShards "auto".
5
+ * An automatic plan changes only when a child reports a 4011 (sharding required) closure: Every child stops, the
6
+ * communities are counted again and a larger plan starts, at most three times an hour.
7
+ * Only an application-supplied identify coordinator reaches beyond the children it forked. The children share Fluxer's
8
+ * account-wide limits through the parent: It relays a global rate-limit pause one child learns to the others, and keeps
9
+ * the one member request window, counting a granted request from its grant and again once it reached the socket. An
10
+ * unanswered child uses its own window. Per-route REST buckets stay per process, and session retention belongs to each
11
+ * child's own SessionStore. It terminates only an
12
+ * unresponsive child after the graceful deadline and awaits that child's exit, passes its resolved format to children
13
+ * through FLUXERLY_LOG_FORMAT and FLUXERLY_LOG_COLOR, and keeps forwarded JSON output valid JSON Lines. Implements [SDK contracts: Connection and recovery](/docs/SDK-CONTRACTS.md#connection-and-recovery)
14
+ */
15
+ import { fork, type ChildProcess } from "node:child_process"
16
+ import { isAbsolute } from "node:path"
17
+ import type { Readable, Writable } from "node:stream"
18
+ import { fileURLToPath } from "node:url"
19
+ import * as Cause from "effect/Cause"
20
+ import * as Deferred from "effect/Deferred"
21
+ import * as Effect from "effect/Effect"
22
+ import * as Exit from "effect/Exit"
23
+ import * as Fiber from "effect/Fiber"
24
+ import { ConfigurationError, ConnectionError } from "#sdk/errors"
25
+ import { loggingConfiguration, type ClientLogger } from "#sdk/internal/logging"
26
+ import { maskText } from "#sdk/internal/masking"
27
+ import { makeClient, type AccountLimits, type IdentifyGate } from "#sdk/internal/client"
28
+ import { memberRequestLimit, memberRequestWindowMs, type MemberRequestSlot } from "#sdk/internal/member-chunks"
29
+ import { validateConfiguration } from "#sdk/internal/configuration"
30
+ import {
31
+ admitReshard,
32
+ automaticShardPlan,
33
+ guildsPerShard,
34
+ largerShardPlan,
35
+ maximumShardCount,
36
+ } from "#sdk/internal/sharding"
37
+ import { CloseCode } from "#sdk/internal/protocol/gateway"
38
+ import {
39
+ SupervisorChildError,
40
+ SupervisorError,
41
+ type SupervisorAssignment,
42
+ type SupervisorChildDiagnostics,
43
+ type SupervisorChildState,
44
+ type SupervisorOptions,
45
+ type SupervisorState,
46
+ type SupervisorStatus,
47
+ } from "#sdk/supervisor"
48
+ import type { ClientDiagnostics, ConnectionState } from "#sdk/client"
49
+ import { record, safeInteger, snapshotArray } from "#sdk/internal/decode/primitives"
50
+ import { callerFields, readCaller, suspendMarked } from "#sdk/internal/defects"
51
+ import { unsupportedKeyHint } from "#sdk/internal/suggest"
52
+ import type { LogCode } from "#sdk/internal/code-catalogue"
53
+
54
+ const maximumTimerMs = 2_147_483_647
55
+ const maximumAttempts = 100
56
+ const maximumChildEnvironmentEntries = 64
57
+ const maximumArgumentEntries = 64
58
+ const maximumArgumentLength = 4_096
59
+ const maximumChildIdLength = 128
60
+ const defaultStartupTimeoutMs = 30_000
61
+ const defaultShutdownTimeoutMs = 5_000
62
+ const grantAcknowledgementMs = 5_000
63
+ /** Longest wait for the parent's answer to a member request slot, after which the child uses its own window */
64
+ const memberAnswerMs = 1_000
65
+ const defaultDiagnosticsIntervalMs = 5_000
66
+ /** Part of shutdownTimeoutMs a stopping child keeps for closing its connections after draining running work */
67
+ const childCloseReserveMs = 1_000
68
+ /** Longest wait after a child exits for its forwarded output streams to close */
69
+ const outputDrainGraceMs = 1_000
70
+
71
+ interface RestartConfiguration {
72
+ readonly maxAttempts: number
73
+ readonly minDelayMs: number
74
+ readonly maxDelayMs: number
75
+ /** Running time after readiness that restores a child's full restart budget at its next exit */
76
+ readonly healthyResetMs: number
77
+ }
78
+
79
+ /** The documented restart defaults, used when the restart option is omitted */
80
+ const defaultRestart: RestartConfiguration = Object.freeze({
81
+ maxAttempts: 3,
82
+ minDelayMs: 1_000,
83
+ maxDelayMs: 30_000,
84
+ healthyResetMs: 60_000,
85
+ })
86
+
87
+ /** How processes or shardsPerProcess divide every shard among the children */
88
+ type ProcessSplit = { readonly processes: number } | { readonly shardsPerProcess: number }
89
+
90
+ /** Settings for sizing the plan at start from the bot's community count */
91
+ interface AutomaticPlan {
92
+ readonly split: ProcessSplit
93
+ /** Validated client options for the transient client that counts the communities */
94
+ readonly clientOptions: Readonly<Record<string, unknown>>
95
+ }
96
+
97
+ /** Bound permit function of an application identify coordinator */
98
+ type CoordinatorPermit = (shardId: number, totalShards: number, signal: AbortSignal) => unknown
99
+
100
+ interface SupervisorConfiguration {
101
+ readonly entry: string
102
+ /** Known assignments, empty until start has counted an automatic plan */
103
+ readonly children: readonly ChildConfiguration[]
104
+ readonly automatic: AutomaticPlan | undefined
105
+ readonly restart: RestartConfiguration | undefined
106
+ readonly minimumSpacingMs: number
107
+ readonly coordinator: CoordinatorPermit | undefined
108
+ readonly diagnosticsIntervalMs: number
109
+ readonly startupTimeoutMs: number
110
+ readonly shutdownTimeoutMs: number
111
+ readonly environment: readonly (readonly [string, string])[]
112
+ readonly args: readonly string[]
113
+ readonly execArgv: readonly string[]
114
+ /** How child standard output and error reach the parent */
115
+ readonly childOutput: "prefix" | "inherit" | "ignore"
116
+ /** Supervisor records for spawn, exit, crash and restart */
117
+ readonly logger: ClientLogger
118
+ }
119
+
120
+ interface ChildConfiguration {
121
+ readonly id: string
122
+ readonly assignment: SupervisorAssignment
123
+ }
124
+
125
+ interface ChildSlot {
126
+ readonly configuration: ChildConfiguration
127
+ generation: number
128
+ restarts: number
129
+ child: ChildProcess | undefined
130
+ hello: boolean
131
+ ready: boolean
132
+ /** Host time at which the current process finished configuration */
133
+ readyAt: number | undefined
134
+ connectionState: ConnectionState | null
135
+ /** Latest diagnostics snapshot from the current process */
136
+ diagnostics: SupervisorChildDiagnostics | null
137
+ state: SupervisorChildState
138
+ restartTimer: ReturnType<typeof setTimeout> | undefined
139
+ startupTimer: ReturnType<typeof setTimeout> | undefined
140
+ stopTimer: ReturnType<typeof setTimeout> | undefined
141
+ disconnectTimer: ReturnType<typeof setTimeout> | undefined
142
+ }
143
+
144
+ const connectionStates = ["Disconnected", "Connecting", "Connected", "Recovering", "Closing", "Closed"] as const
145
+
146
+ function connectionState(value: unknown): value is ConnectionState {
147
+ return typeof value === "string" && connectionStates.includes(value as ConnectionState)
148
+ }
149
+
150
+ /** Top-level fields of a ClientDiagnostics snapshot, which a diagnostics message must carry exactly */
151
+ const diagnosticsKeys: readonly (keyof ClientDiagnostics)[] = [
152
+ "state",
153
+ "gatewayLatencyMs",
154
+ "shards",
155
+ "rest",
156
+ "uploads",
157
+ "gatewayRequests",
158
+ "events",
159
+ "caches",
160
+ "counters",
161
+ ]
162
+
163
+ /** Freeze a snapshot received over IPC, which Node has already copied, so status readers cannot change it */
164
+ function deepFreeze<T>(value: T): T {
165
+ if (typeof value === "object" && value !== null) {
166
+ for (const entry of Object.values(value)) deepFreeze(entry)
167
+ Object.freeze(value)
168
+ }
169
+ return value
170
+ }
171
+
172
+ interface IdentifyRequest {
173
+ readonly slot: ChildSlot
174
+ readonly generation: number
175
+ readonly requestId: number
176
+ readonly shardId: number
177
+ }
178
+
179
+ /** A member request counted against Fluxer's account limit, from its grant or from when it reached a socket */
180
+ interface CountedMemberRequest {
181
+ readonly at: number
182
+ /** The child request holding a granted slot that it has not reported as sent or withdrawn */
183
+ readonly holder?: { readonly slot: ChildSlot; readonly generation: number; readonly requestId: number }
184
+ }
185
+
186
+ interface OutstandingIdentify extends IdentifyRequest {
187
+ /** Acknowledgement deadline, set once the grant is sent */
188
+ timer: ReturnType<typeof setTimeout> | undefined
189
+ /** Aborts the identify coordinator's permit while the parent still waits for it */
190
+ permit: AbortController | undefined
191
+ stalled: boolean
192
+ }
193
+
194
+ /**
195
+ * Split every shard of a plan into contiguous blocks, one per child, named process-0, process-1 and so on.
196
+ * Processes get sizes that differ by at most one, and shardsPerProcess leaves the remainder to the last child
197
+ */
198
+ function splitShards(totalShards: number, split: ProcessSplit): readonly ChildConfiguration[] {
199
+ const count =
200
+ "processes" in split ? Math.min(split.processes, totalShards) : Math.ceil(totalShards / split.shardsPerProcess)
201
+ const children: ChildConfiguration[] = []
202
+ let next = 0
203
+ for (let index = 0; index < count; index += 1) {
204
+ const size =
205
+ "processes" in split
206
+ ? Math.floor(totalShards / count) + (index < totalShards % count ? 1 : 0)
207
+ : Math.min(split.shardsPerProcess, totalShards - next)
208
+ const shardIds = Array.from({ length: size }, (_, offset) => next + offset)
209
+ next += size
210
+ children.push(
211
+ Object.freeze({
212
+ id: `process-${index}`,
213
+ assignment: Object.freeze({ totalShards, shardIds: Object.freeze(shardIds) }),
214
+ }),
215
+ )
216
+ }
217
+ return Object.freeze(children)
218
+ }
219
+
220
+ function hasOnlyKeys(value: Record<string, unknown>, keys: readonly string[]): boolean {
221
+ return Object.keys(value).every((key) => keys.includes(key))
222
+ }
223
+
224
+ function hasExactKeys(value: Record<string, unknown>, keys: readonly string[]): boolean {
225
+ return hasOnlyKeys(value, keys) && keys.every((key) => key in value)
226
+ }
227
+
228
+ function positiveTimer(value: unknown): value is number {
229
+ return safeInteger(value) && value > 0 && value <= maximumTimerMs
230
+ }
231
+
232
+ function childEntry(value: unknown): string | undefined {
233
+ if (typeof value === "string") return isAbsolute(value) ? value : undefined
234
+ // Read the URL fields outside the parse guard, so a throwing getter stays an application fault
235
+ if (!record(value) || value.protocol !== "file:") return undefined
236
+ const href = value.href
237
+ if (typeof href !== "string") return undefined
238
+ try {
239
+ const path = fileURLToPath(href)
240
+ return isAbsolute(path) ? path : undefined
241
+ } catch {
242
+ // allow-silent: An unusable entry becomes the typed ConfigurationError returned by the caller
243
+ return undefined
244
+ }
245
+ }
246
+
247
+ function filteredExecArguments(values: readonly string[]): string[] {
248
+ const result: string[] = []
249
+ for (let index = 0; index < values.length; index += 1) {
250
+ const argument = values[index]!
251
+ // Child processes resolve the shipped output, so neither Node spelling may retain the source-test condition
252
+ if ((argument === "--conditions" || argument === "-C") && values[index + 1] === "fluxerly-source") {
253
+ index += 1
254
+ continue
255
+ }
256
+ if (argument === "--conditions=fluxerly-source") continue
257
+ result.push(argument)
258
+ }
259
+ return result
260
+ }
261
+
262
+ /** Copy a caller string array once, then validate the copy. A sparse entry copies as undefined and fails */
263
+ function stringArray(value: unknown, field: string): readonly string[] | ConfigurationError {
264
+ const copied = snapshotArray(value, maximumArgumentEntries)
265
+ if (copied === undefined)
266
+ return new ConfigurationError(
267
+ field as never,
268
+ `The supervisor option ${JSON.stringify(field)} must be an array of at most ${maximumArgumentEntries} strings`,
269
+ )
270
+ if (copied.some((entry) => typeof entry !== "string" || entry.length > maximumArgumentLength))
271
+ return new ConfigurationError(
272
+ field as never,
273
+ `The supervisor option ${JSON.stringify(field)} must contain only strings of at most ${maximumArgumentLength.toLocaleString("en-US")} characters, with no empty slots`,
274
+ )
275
+ return copied as readonly string[]
276
+ }
277
+
278
+ /** Copy caller shard IDs once, then validate the copy, so the validated IDs are the ones assigned */
279
+ function assignment(value: unknown, totalShards: number): readonly number[] | undefined {
280
+ const copied = snapshotArray(value, totalShards)
281
+ if (copied === undefined || copied.length === 0) return undefined
282
+ const seen = new Set<number>()
283
+ for (const shardId of copied) {
284
+ if (!safeInteger(shardId) || shardId < 0 || shardId >= totalShards || seen.has(shardId)) return undefined
285
+ seen.add(shardId)
286
+ }
287
+ return copied as readonly number[]
288
+ }
289
+
290
+ function childEnvironment(value: unknown): readonly (readonly [string, string])[] | ConfigurationError {
291
+ if (value === undefined) return Object.freeze([])
292
+ if (!record(value) || Object.getOwnPropertySymbols(value).length > 0)
293
+ return new ConfigurationError(
294
+ "childEnvironment",
295
+ 'The supervisor option "childEnvironment" must be an object of environment variable names and string values',
296
+ )
297
+ const entries = Object.entries(value)
298
+ if (entries.length > maximumChildEnvironmentEntries)
299
+ return new ConfigurationError(
300
+ "childEnvironment",
301
+ `The supervisor option "childEnvironment" can have at most ${maximumChildEnvironmentEntries} entries`,
302
+ )
303
+ const copied: (readonly [string, string])[] = []
304
+ for (const [key, current] of entries) {
305
+ if (
306
+ !/^[A-Za-z_][A-Za-z0-9_]*$/.test(key) ||
307
+ typeof current !== "string" ||
308
+ current.length > maximumArgumentLength
309
+ )
310
+ return new ConfigurationError(
311
+ "childEnvironment",
312
+ `The supervisor option "childEnvironment" must use names of letters, digits and underscores that do not start with a digit, and string values of at most ${maximumArgumentLength.toLocaleString("en-US")} characters`,
313
+ )
314
+ copied.push(Object.freeze([key, current]))
315
+ }
316
+ return Object.freeze(copied)
317
+ }
318
+
319
+ /**
320
+ * Validate and snapshot supervisor configuration without creating a child process. Each caller field is read once, and
321
+ * only the reads of the options are marked as application input, so a fault in the surrounding validation or logger
322
+ * creation stays an SDK fault
323
+ */
324
+ function validateSupervisorConfiguration(
325
+ options: unknown,
326
+ native = false,
327
+ ): Effect.Effect<SupervisorConfiguration, ConfigurationError> {
328
+ return suspendMarked(() => supervisorSettings(options, native))
329
+ }
330
+
331
+ const supervisorOptionKeys: readonly string[] = [
332
+ "entry",
333
+ "totalShards",
334
+ "assignments",
335
+ "processes",
336
+ "shardsPerProcess",
337
+ "token",
338
+ "instance",
339
+ "transport",
340
+ "restart",
341
+ "identify",
342
+ "diagnosticsIntervalMs",
343
+ "startupTimeoutMs",
344
+ "shutdownTimeoutMs",
345
+ "childEnvironment",
346
+ "args",
347
+ "execArgv",
348
+ "childOutput",
349
+ "logging",
350
+ ]
351
+
352
+ /** Reject malformed supervisor option objects and suggest supported names before their values are read */
353
+ export function supervisorOptionError(
354
+ options: unknown,
355
+ supported: readonly string[],
356
+ field: ConfigurationError["field"],
357
+ label: string,
358
+ ): ConfigurationError | undefined {
359
+ if (!record(options)) return new ConfigurationError(field, `${label} must be an object`)
360
+ const unsupported = Object.keys(options).find((key) => !supported.includes(key))
361
+ return unsupported === undefined
362
+ ? undefined
363
+ : new ConfigurationError(
364
+ field,
365
+ `Unsupported option ${JSON.stringify(unsupported)} in the ${label.charAt(0).toLowerCase()}${label.slice(1)}`,
366
+ {
367
+ hint: unsupportedKeyHint(unsupported, supported),
368
+ },
369
+ )
370
+ }
371
+
372
+ function supervisorSettings(
373
+ options: unknown,
374
+ native: boolean,
375
+ ): Effect.Effect<SupervisorConfiguration, ConfigurationError> {
376
+ {
377
+ if (!record(options))
378
+ return Effect.fail(new ConfigurationError("supervisor", "Supervisor settings must be an object"))
379
+ const unsupported = readCaller(() => Object.keys(options)).find((key) => !supervisorOptionKeys.includes(key))
380
+ if (unsupported !== undefined)
381
+ return Effect.fail(
382
+ new ConfigurationError("supervisor", `Unsupported supervisor option ${JSON.stringify(unsupported)}`, {
383
+ hint: unsupportedKeyHint(unsupported, supervisorOptionKeys),
384
+ }),
385
+ )
386
+ const field = callerFields(options)
387
+ const entry = readCaller(() => childEntry(field("entry")))
388
+ if (!entry)
389
+ return Effect.fail(
390
+ new ConfigurationError("entry", 'The supervisor option "entry" must be an absolute path or a file URL'),
391
+ )
392
+ const totalShards = field("totalShards")
393
+ if (totalShards !== "auto" && (!safeInteger(totalShards) || totalShards < 1 || totalShards > maximumShardCount))
394
+ return Effect.fail(
395
+ new ConfigurationError(
396
+ "totalShards",
397
+ 'The supervisor option "totalShards" must be an integer from 1 through 16,384, or "auto"',
398
+ ),
399
+ )
400
+ const split = processSplit(field("assignments"), field("processes"), field("shardsPerProcess"), totalShards)
401
+ if (split instanceof ConfigurationError) return Effect.fail(split)
402
+ const counting = ["token", "instance", "transport"].map((key) => [key, field(key)] as const)
403
+ const automatic =
404
+ totalShards === "auto"
405
+ ? countingOptions(counting, field("logging"), split as ProcessSplit, native)
406
+ : undefined
407
+ if (automatic instanceof ConfigurationError) return Effect.fail(automatic)
408
+ if (totalShards !== "auto") {
409
+ const supplied = counting.find(([, value]) => value !== undefined)
410
+ if (supplied)
411
+ return Effect.fail(
412
+ new ConfigurationError(
413
+ supplied[0] as "token" | "instance" | "transport",
414
+ `The supervisor option ${JSON.stringify(supplied[0])} is used only to count the bot's communities when totalShards is "auto"`,
415
+ { hint: 'Remove it, or set totalShards to "auto" to size the plan at start' },
416
+ ),
417
+ )
418
+ }
419
+ const children =
420
+ totalShards === "auto"
421
+ ? Object.freeze([])
422
+ : split === undefined
423
+ ? readCaller(() => fixedAssignments(field("assignments"), totalShards))
424
+ : splitShards(totalShards, split)
425
+ if (children instanceof ConfigurationError) return Effect.fail(children)
426
+ const restart = field("restart")
427
+ let restartConfiguration: RestartConfiguration | undefined = defaultRestart
428
+ if (restart === false) restartConfiguration = undefined
429
+ else if (restart !== undefined) {
430
+ const configured = readCaller(() => restartSettings(restart))
431
+ if (configured instanceof ConfigurationError) return Effect.fail(configured)
432
+ restartConfiguration = configured
433
+ }
434
+ const identify = readCaller(() => identifySettings(field("identify")))
435
+ if (identify instanceof ConfigurationError) return Effect.fail(identify)
436
+ const diagnosticsInput = field("diagnosticsIntervalMs")
437
+ const diagnosticsIntervalMs = diagnosticsInput === undefined ? defaultDiagnosticsIntervalMs : diagnosticsInput
438
+ if (!positiveTimer(diagnosticsIntervalMs) || diagnosticsIntervalMs < 1_000)
439
+ return Effect.fail(
440
+ new ConfigurationError(
441
+ "diagnosticsIntervalMs",
442
+ 'The supervisor option "diagnosticsIntervalMs" must be an integer from 1,000 through 2,147,483,647 milliseconds',
443
+ ),
444
+ )
445
+ const startupInput = field("startupTimeoutMs")
446
+ const startupTimeoutMs = startupInput === undefined ? defaultStartupTimeoutMs : startupInput
447
+ if (!positiveTimer(startupTimeoutMs))
448
+ return Effect.fail(
449
+ new ConfigurationError(
450
+ "startupTimeoutMs",
451
+ 'The supervisor option "startupTimeoutMs" must be an integer from 1 through 2,147,483,647 milliseconds',
452
+ ),
453
+ )
454
+ const shutdownInput = field("shutdownTimeoutMs")
455
+ const shutdownTimeoutMs = shutdownInput === undefined ? defaultShutdownTimeoutMs : shutdownInput
456
+ if (!positiveTimer(shutdownTimeoutMs))
457
+ return Effect.fail(
458
+ new ConfigurationError(
459
+ "shutdownTimeoutMs",
460
+ 'The supervisor option "shutdownTimeoutMs" must be an integer from 1 through 2,147,483,647 milliseconds',
461
+ ),
462
+ )
463
+ const childEnvironmentOverrides = readCaller(() => childEnvironment(field("childEnvironment")))
464
+ if (childEnvironmentOverrides instanceof ConfigurationError) return Effect.fail(childEnvironmentOverrides)
465
+ const environment = new Map<string, string>()
466
+ for (const [key, value] of Object.entries(process.env)) {
467
+ if (typeof value === "string") environment.set(key, value)
468
+ }
469
+ for (const [key, value] of childEnvironmentOverrides) environment.set(key, value)
470
+ const argsInput = field("args")
471
+ const args = argsInput === undefined ? Object.freeze([]) : readCaller(() => stringArray(argsInput, "args"))
472
+ if (args instanceof ConfigurationError) return Effect.fail(args)
473
+ const execArgvOption = field("execArgv")
474
+ const execArgv = readCaller(() =>
475
+ stringArray(execArgvOption === undefined ? process.execArgv : execArgvOption, "execArgv"),
476
+ )
477
+ if (execArgv instanceof ConfigurationError) return Effect.fail(execArgv)
478
+ const childOutputInput = field("childOutput")
479
+ const childOutput = childOutputInput === undefined ? "prefix" : childOutputInput
480
+ if (childOutput !== "prefix" && childOutput !== "inherit" && childOutput !== "ignore")
481
+ return Effect.fail(
482
+ new ConfigurationError(
483
+ "childOutput",
484
+ 'The supervisor option "childOutput" must be "prefix", "inherit" or "ignore"',
485
+ ),
486
+ )
487
+ const logger = loggingConfiguration(field("logging"), native)
488
+ if (logger instanceof ConfigurationError) return Effect.fail(logger)
489
+ return Effect.succeed(
490
+ Object.freeze({
491
+ entry,
492
+ children,
493
+ automatic,
494
+ restart: restartConfiguration,
495
+ minimumSpacingMs: identify.minimumSpacingMs,
496
+ coordinator: identify.coordinator,
497
+ diagnosticsIntervalMs,
498
+ startupTimeoutMs,
499
+ shutdownTimeoutMs,
500
+ environment: Object.freeze([...environment].map((entry) => Object.freeze(entry))),
501
+ args,
502
+ execArgv: Object.freeze(filteredExecArguments(execArgv)),
503
+ childOutput,
504
+ logger,
505
+ }),
506
+ )
507
+ }
508
+ }
509
+
510
+ /**
511
+ * Choose how children are formed: undefined for explicit assignments, otherwise the processes or shardsPerProcess
512
+ * split. Exactly one of the three must be present, and an automatic total needs a split
513
+ */
514
+ function processSplit(
515
+ assignments: unknown,
516
+ processes: unknown,
517
+ shardsPerProcess: unknown,
518
+ totalShards: number | "auto",
519
+ ): ProcessSplit | undefined | ConfigurationError {
520
+ const chosen = [assignments, processes, shardsPerProcess].filter((value) => value !== undefined).length
521
+ if (chosen !== 1)
522
+ return new ConfigurationError(
523
+ chosen === 0 ? "assignments" : "supervisor",
524
+ chosen === 0
525
+ ? 'The supervisor needs one of the options "assignments", "processes" or "shardsPerProcess"'
526
+ : 'The supervisor options "assignments", "processes" and "shardsPerProcess" cannot be combined',
527
+ {
528
+ hint: "Use processes to split every shard evenly across that many children, or assignments to choose each child's shards",
529
+ },
530
+ )
531
+ if (assignments !== undefined) {
532
+ if (totalShards === "auto")
533
+ return new ConfigurationError(
534
+ "assignments",
535
+ 'The supervisor option "assignments" needs a numeric totalShards, because fixed shard IDs depend on the total',
536
+ { hint: 'Use processes or shardsPerProcess with totalShards "auto"' },
537
+ )
538
+ return undefined
539
+ }
540
+ const name = processes !== undefined ? "processes" : "shardsPerProcess"
541
+ const value = processes ?? shardsPerProcess
542
+ if (!safeInteger(value) || value < 1 || value > maximumShardCount)
543
+ return new ConfigurationError(name, `The supervisor option "${name}" must be an integer from 1 through 16,384`)
544
+ if (name === "processes" && totalShards !== "auto" && value > totalShards)
545
+ return new ConfigurationError(
546
+ "processes",
547
+ 'The supervisor option "processes" can be at most totalShards, because each child needs at least one shard',
548
+ )
549
+ return name === "processes" ? { processes: value } : { shardsPerProcess: value }
550
+ }
551
+
552
+ /** Validate the settings of the transient client that counts communities for totalShards "auto" */
553
+ function countingOptions(
554
+ counting: readonly (readonly [string, unknown])[],
555
+ logging: unknown,
556
+ split: ProcessSplit,
557
+ native: boolean,
558
+ ): AutomaticPlan | ConfigurationError {
559
+ const clientOptions: Record<string, unknown> = {}
560
+ for (const [key, value] of counting) if (value !== undefined) clientOptions[key] = value
561
+ if (logging !== undefined) clientOptions.logging = logging
562
+ if (clientOptions.token === undefined)
563
+ return new ConfigurationError("token", 'The supervisor option "token" is required when totalShards is "auto"', {
564
+ hint: "Pass the bot token, such as process.env.FLUXER_BOT_TOKEN, so the supervisor can count the bot's communities",
565
+ })
566
+ const validated = Effect.runSyncExit(validateConfiguration(clientOptions, native))
567
+ if (Exit.isFailure(validated)) {
568
+ const failure = validated.cause.reasons.find((reason) => reason._tag === "Fail")
569
+ if (failure?._tag === "Fail") return failure.error
570
+ throw Cause.squash(validated.cause)
571
+ }
572
+ return Object.freeze({ split, clientOptions: Object.freeze(clientOptions) })
573
+ }
574
+
575
+ /** Copy and validate explicit assignments for a numeric total */
576
+ function fixedAssignments(value: unknown, totalShards: number): readonly ChildConfiguration[] | ConfigurationError {
577
+ const assignments = snapshotArray(value, totalShards)
578
+ if (assignments === undefined || assignments.length === 0)
579
+ return new ConfigurationError(
580
+ "assignments",
581
+ `The supervisor option "assignments" must be a non-empty array with at most ${totalShards} entries, one per child`,
582
+ )
583
+ const seenIds = new Set<string>()
584
+ const seenShards = new Set<number>()
585
+ const children: ChildConfiguration[] = []
586
+ for (const current of assignments) {
587
+ if (!record(current))
588
+ return new ConfigurationError(
589
+ "assignments",
590
+ "Each supervisor assignment must be an object with id and shardIds",
591
+ )
592
+ const invalidKeys = supervisorOptionError(
593
+ current,
594
+ ["id", "shardIds"],
595
+ "assignments",
596
+ "Supervisor assignment options",
597
+ )
598
+ if (invalidKeys) return invalidKeys
599
+ if (!hasExactKeys(current, ["id", "shardIds"]))
600
+ return new ConfigurationError(
601
+ "assignments",
602
+ "Each supervisor assignment must contain exactly id and shardIds",
603
+ )
604
+ const id = current.id
605
+ if (typeof id === "string" && seenIds.has(id))
606
+ return new ConfigurationError(
607
+ "childId",
608
+ `Supervisor assignment ID ${JSON.stringify(id)} is used more than once`,
609
+ )
610
+ if (typeof id !== "string" || id.trim().length === 0 || id.length > maximumChildIdLength)
611
+ return new ConfigurationError(
612
+ "childId",
613
+ `Supervisor assignment IDs must be non-blank strings of at most ${maximumChildIdLength} characters`,
614
+ )
615
+ const shardIds = assignment(current.shardIds, totalShards)
616
+ if (!shardIds)
617
+ return new ConfigurationError(
618
+ "shardIds",
619
+ `The shardIds of supervisor assignment ${JSON.stringify(id)} must be a non-empty array of unique integers from 0 through ${totalShards - 1}`,
620
+ )
621
+ for (const shardId of shardIds) {
622
+ if (seenShards.has(shardId))
623
+ return new ConfigurationError(
624
+ "shardIds",
625
+ `Shard ${shardId} is assigned to more than one supervisor child`,
626
+ )
627
+ seenShards.add(shardId)
628
+ }
629
+ seenIds.add(id)
630
+ children.push(
631
+ Object.freeze({ id, assignment: Object.freeze({ totalShards, shardIds: Object.freeze([...shardIds]) }) }),
632
+ )
633
+ }
634
+ return Object.freeze(children)
635
+ }
636
+
637
+ /** Validate a supplied restart object, filling each omitted setting with its default */
638
+ function restartSettings(restart: unknown): RestartConfiguration | ConfigurationError {
639
+ if (!record(restart))
640
+ return new ConfigurationError("restart", 'The supervisor option "restart" must be an object or false')
641
+ const restartKeys = ["maxAttempts", "minDelayMs", "maxDelayMs", "healthyResetMs"]
642
+ const unsupportedRestart = Object.keys(restart).find((key) => !restartKeys.includes(key))
643
+ if (unsupportedRestart !== undefined)
644
+ return new ConfigurationError("restart", `Unsupported restart setting ${JSON.stringify(unsupportedRestart)}`, {
645
+ hint: unsupportedKeyHint(unsupportedRestart, restartKeys, "settings"),
646
+ })
647
+ const restartField = callerFields(restart)
648
+ const orDefault = (key: keyof RestartConfiguration) => {
649
+ const value = restartField(key)
650
+ return value === undefined ? defaultRestart[key] : value
651
+ }
652
+ const maxAttempts = orDefault("maxAttempts")
653
+ const minDelayMs = orDefault("minDelayMs")
654
+ const maxDelayMs = orDefault("maxDelayMs")
655
+ const healthyResetMs = orDefault("healthyResetMs")
656
+ if (!safeInteger(maxAttempts) || maxAttempts < 0 || maxAttempts > maximumAttempts)
657
+ return new ConfigurationError(
658
+ "maxAttempts",
659
+ `The supervisor option "restart.maxAttempts" must be an integer from 0 through ${maximumAttempts}`,
660
+ )
661
+ if (!positiveTimer(minDelayMs) || !positiveTimer(maxDelayMs) || minDelayMs > maxDelayMs)
662
+ return new ConfigurationError(
663
+ "restart",
664
+ 'The supervisor options "restart.minDelayMs" and "restart.maxDelayMs" must be integers from 1 through 2,147,483,647 milliseconds, with minDelayMs no larger than maxDelayMs',
665
+ )
666
+ if (!positiveTimer(healthyResetMs))
667
+ return new ConfigurationError(
668
+ "healthyResetMs",
669
+ 'The supervisor option "restart.healthyResetMs" must be an integer from 1 through 2,147,483,647 milliseconds',
670
+ )
671
+ return Object.freeze({ maxAttempts, minDelayMs, maxDelayMs, healthyResetMs })
672
+ }
673
+
674
+ /** Validate Identify pacing: Parent spacing, or an application coordinator that replaces it */
675
+ function identifySettings(
676
+ identify: unknown,
677
+ ): { readonly minimumSpacingMs: number; readonly coordinator: CoordinatorPermit | undefined } | ConfigurationError {
678
+ if (identify !== undefined && !record(identify))
679
+ return new ConfigurationError("identify", "Supervisor Identify options must be an object")
680
+ if (identify !== undefined) {
681
+ const invalidKeys = supervisorOptionError(
682
+ identify,
683
+ ["minimumSpacingMs", "coordinator"],
684
+ "identify",
685
+ "Supervisor Identify options",
686
+ )
687
+ if (invalidKeys) return invalidKeys
688
+ }
689
+ const spacing = identify?.minimumSpacingMs
690
+ const coordinator = identify?.coordinator
691
+ if (coordinator !== undefined) {
692
+ if (spacing !== undefined)
693
+ return new ConfigurationError(
694
+ "identify",
695
+ 'The supervisor options "identify.minimumSpacingMs" and "identify.coordinator" cannot be combined, because the coordinator owns Identify pacing',
696
+ { hint: "Space the permits inside the coordinator instead" },
697
+ )
698
+ const permit = record(coordinator) ? coordinator.permit : undefined
699
+ if (typeof permit !== "function")
700
+ return new ConfigurationError(
701
+ "identify",
702
+ 'The supervisor option "identify.coordinator" must be an object with a permit function',
703
+ )
704
+ return { minimumSpacingMs: 0, coordinator: permit.bind(coordinator) as CoordinatorPermit }
705
+ }
706
+ const minimumSpacingMs = spacing === undefined ? 1_000 : spacing
707
+ if (!positiveTimer(minimumSpacingMs) || minimumSpacingMs < 1_000)
708
+ return new ConfigurationError(
709
+ "minimumSpacingMs",
710
+ 'The supervisor option "identify.minimumSpacingMs" must be an integer from 1,000 through 2,147,483,647 milliseconds',
711
+ )
712
+ return { minimumSpacingMs, coordinator: undefined }
713
+ }
714
+
715
+ /** Label for one child's forwarded output lines, naming its shard when it owns exactly one */
716
+ function outputLabel(configuration: ChildConfiguration) {
717
+ const shards = configuration.assignment.shardIds
718
+ return shards.length === 1 ? `[shard ${shards[0]}]` : `[child ${configuration.id}]`
719
+ }
720
+
721
+ /** Longest forwarded line in characters. Longer lines are cut with a marker so one child cannot grow parent memory */
722
+ export const maximumForwardedLineLength = 262_144
723
+ const truncationMarker = " … [line truncated by the supervisor]"
724
+
725
+ /** One child line in the parent's JSON Lines output. An SDK record gains a fields.child entry, another JSON object
726
+ * passes through unchanged, and any other text becomes a supervisor.childOutput record, so the output stays valid
727
+ */
728
+ function jsonOutputLine(line: string, configuration: ChildConfiguration, stream: "stdout" | "stderr"): string {
729
+ try {
730
+ const value = JSON.parse(line) as unknown
731
+ if (record(value)) {
732
+ if (typeof value.level !== "string" || typeof value.code !== "string" || typeof value.category !== "string")
733
+ return line
734
+ const fields = record(value.fields) ? value.fields : {}
735
+ return JSON.stringify({ ...value, fields: { ...fields, child: configuration.id } })
736
+ }
737
+ } catch {
738
+ // allow-silent: A line that is not JSON is wrapped as a supervisor.childOutput record below
739
+ }
740
+ return JSON.stringify({
741
+ time: new Date().toISOString(),
742
+ level: stream === "stderr" ? "warn" : "info",
743
+ category: "supervisor",
744
+ code: "supervisor.childOutput",
745
+ message: maskText(line),
746
+ fields: { child: configuration.id, shards: configuration.assignment.shardIds.join(","), stream },
747
+ })
748
+ }
749
+
750
+ /**
751
+ * Forward each line from a child stream in the parent's format for that stream: Labelled text for pretty output,
752
+ * or JSON Lines for json output. Lines longer than maximumForwardedLineLength are truncated with a marker, the child
753
+ * stream pauses while the parent stream applies backpressure, and a partial final line is forwarded at the end.
754
+ * The done callback runs once the child stream has ended or closed
755
+ */
756
+ function forwardLines(
757
+ stream: Readable | null,
758
+ target: Writable,
759
+ name: "stdout" | "stderr",
760
+ configuration: ChildConfiguration,
761
+ logger: ClientLogger,
762
+ done: () => void,
763
+ ) {
764
+ if (!stream) return done()
765
+ const label = outputLabel(configuration)
766
+ const json = logger.consoleFormat(name).format === "json"
767
+ let pending = ""
768
+ let skipping = false
769
+ let finished = false
770
+ const emit = (line: string) => {
771
+ const text = json ? jsonOutputLine(line, configuration, name) : `${label} ${line}`
772
+ if (!target.write(`${text}\n`) && !stream.isPaused()) {
773
+ stream.pause()
774
+ target.once("drain", () => stream.resume())
775
+ }
776
+ }
777
+ stream.setEncoding("utf8")
778
+ stream.on("data", (chunk: string) => {
779
+ let start = 0
780
+ while (start < chunk.length) {
781
+ const end = chunk.indexOf("\n", start)
782
+ const piece = chunk.slice(start, end === -1 ? chunk.length : end)
783
+ start = end === -1 ? chunk.length : end + 1
784
+ if (!skipping) {
785
+ pending += piece
786
+ if (pending.length > maximumForwardedLineLength) {
787
+ emit(`${pending.slice(0, maximumForwardedLineLength)}${truncationMarker}`)
788
+ pending = ""
789
+ skipping = true
790
+ }
791
+ }
792
+ if (end !== -1) {
793
+ if (!skipping) emit(pending.endsWith("\r") ? pending.slice(0, -1) : pending)
794
+ pending = ""
795
+ skipping = false
796
+ }
797
+ }
798
+ })
799
+ const finish = () => {
800
+ if (finished) return
801
+ finished = true
802
+ if (pending !== "" && !skipping) emit(pending)
803
+ pending = ""
804
+ done()
805
+ }
806
+ stream.once("end", finish)
807
+ stream.once("close", finish)
808
+ // A read error ends forwarding of this stream while the child can keep running, so the error is recorded. The child's
809
+ // exit is still observed and logged separately
810
+ stream.once("error", (error) => {
811
+ logger.log({
812
+ level: "warn",
813
+ category: "supervisor",
814
+ code: "supervisor.outputFailed",
815
+ message: `Reading the ${name === "stdout" ? "standard output" : "standard error"} of child ${configuration.id} failed, so the supervisor stops forwarding it`,
816
+ error,
817
+ fields: { child: configuration.id, shards: configuration.assignment.shardIds.join(","), stream: name },
818
+ })
819
+ finish()
820
+ })
821
+ }
822
+
823
+ /** Owns only processes forked from one local supervisor instance */
824
+ function childSlot(configuration: ChildConfiguration): ChildSlot {
825
+ return {
826
+ configuration,
827
+ generation: 0,
828
+ restarts: 0,
829
+ child: undefined,
830
+ hello: false,
831
+ ready: false,
832
+ readyAt: undefined,
833
+ connectionState: null,
834
+ diagnostics: null,
835
+ state: "idle",
836
+ restartTimer: undefined,
837
+ startupTimer: undefined,
838
+ stopTimer: undefined,
839
+ disconnectTimer: undefined,
840
+ }
841
+ }
842
+
843
+ export class SupervisorOwner {
844
+ /** One slot per assignment. Empty for an automatic plan until its count completes */
845
+ #slots: ChildSlot[]
846
+ /** The running community count for totalShards "auto" */
847
+ #counting: Fiber.Fiber<void> | undefined
848
+ /** Whether the count finished, which can happen before runFork returns its fiber */
849
+ #countSettled = false
850
+ /** Times of moves to a larger automatic plan, for the hourly limit */
851
+ readonly #reshards: number[] = []
852
+ /** The plan being replaced while its children stop and the communities are counted again */
853
+ #resharding: { readonly previousTotalShards: number; readonly childId: string } | undefined
854
+ readonly #native: boolean
855
+ readonly #startup = Deferred.makeUnsafe<void, SupervisorError>()
856
+ readonly #terminal = Deferred.makeUnsafe<void, SupervisorError>()
857
+ readonly #stopped = Deferred.makeUnsafe<void>()
858
+ #readiness = Deferred.makeUnsafe<void, SupervisorError>()
859
+ #readyObserved = false
860
+ #configuration: SupervisorConfiguration | undefined
861
+ #state: SupervisorState = "idle"
862
+ #stopping = false
863
+ #failed = false
864
+ #failure: SupervisorError | undefined
865
+ #pending: IdentifyRequest[] = []
866
+ #outstanding: OutstandingIdentify | undefined
867
+ #lastIdentifyAt = -Infinity
868
+ #grantTimer: ReturnType<typeof setTimeout> | undefined
869
+ /** Host time at which the latest global rate-limit pause a child reported ends. Fluxer pauses the whole account */
870
+ #globalPauseUntil = 0
871
+ /**
872
+ * Member requests of every child counted against Fluxer's account limit, oldest first. Only the latest
873
+ * memberRequestLimit decide admission, so no more are kept
874
+ */
875
+ #memberRequests: CountedMemberRequest[] = []
876
+
877
+ constructor(configuration: SupervisorConfiguration, native = false) {
878
+ this.#configuration = configuration
879
+ this.#native = native
880
+ this.#slots = configuration.children.map(childSlot)
881
+ }
882
+
883
+ start(): Effect.Effect<void, SupervisorError> {
884
+ const owner = this
885
+ return Effect.uninterruptibleMask((restore) =>
886
+ Effect.suspend(() => {
887
+ if (owner.#state === "closed" || owner.#state === "failed" || owner.#state === "stopping")
888
+ return Effect.fail(new SupervisorError(null, "closed"))
889
+ owner.#beginStart()
890
+ return restore(Deferred.await(owner.#startup)).pipe(Effect.onInterrupt(() => owner.shutdown()))
891
+ }),
892
+ )
893
+ }
894
+
895
+ waitForClose(): Effect.Effect<void, SupervisorError> {
896
+ return Deferred.await(this.#terminal)
897
+ }
898
+
899
+ waitForReady(): Effect.Effect<void, SupervisorError> {
900
+ return Effect.suspend(() => {
901
+ if (this.#state === "idle" || this.#state === "closed" || this.#state === "stopping")
902
+ return Effect.fail(new SupervisorError(null, "closed"))
903
+ if (this.#state === "failed") return Effect.fail(this.#failure ?? new SupervisorError(null, "closed"))
904
+ if (this.#allConnected()) return Effect.void
905
+ return Deferred.await(this.#readiness)
906
+ })
907
+ }
908
+
909
+ status(): SupervisorStatus {
910
+ return Object.freeze({
911
+ state: this.#state,
912
+ children: Object.freeze(
913
+ this.#slots.map((slot) =>
914
+ Object.freeze({
915
+ id: slot.configuration.id,
916
+ assignment: slot.configuration.assignment,
917
+ generation: slot.generation,
918
+ pid: typeof slot.child?.pid === "number" ? slot.child.pid : null,
919
+ restarts: slot.restarts,
920
+ state: slot.state,
921
+ connectionState: slot.connectionState,
922
+ diagnostics: slot.diagnostics,
923
+ }),
924
+ ),
925
+ ),
926
+ })
927
+ }
928
+
929
+ shutdown(): Effect.Effect<void> {
930
+ return Effect.uninterruptible(
931
+ Effect.sync(() => this.#beginShutdown()).pipe(Effect.andThen(Deferred.await(this.#stopped))),
932
+ )
933
+ }
934
+
935
+ /** Whether every child reported Connected. An automatic plan that is still counting has no children yet */
936
+ #allConnected() {
937
+ return this.#slots.length > 0 && this.#slots.every((slot) => slot.connectionState === "Connected")
938
+ }
939
+
940
+ #beginStart() {
941
+ if (this.#state !== "idle") return
942
+ this.#state = "starting"
943
+ const automatic = this.#configuration!.automatic
944
+ if (automatic) return this.#startCount(automatic)
945
+ this.#spawnAll()
946
+ }
947
+
948
+ /** Count the communities in the background, for the first plan or, while resharding, a larger one */
949
+ #startCount(automatic: AutomaticPlan) {
950
+ this.#countSettled = false
951
+ const counting = this.#countPlan(automatic)
952
+ const context = this.#configuration!.logger.context
953
+ const fiber = (context ? Effect.runForkWith(context) : Effect.runFork)(counting)
954
+ if (!this.#countSettled) this.#counting = fiber
955
+ }
956
+
957
+ /**
958
+ * Answer a child's 4011 (sharding required) closure under an automatic plan: Stop every child, then count the
959
+ * communities again and start a larger plan once all have exited. Beyond the hourly limit the supervisor fails, as a
960
+ * client with sharding "auto" ends. A second report during the move joins it
961
+ */
962
+ #reshard(slot: ChildSlot) {
963
+ if (this.#resharding !== undefined) return
964
+ const previousTotalShards = slot.configuration.assignment.totalShards
965
+ const refused = admitReshard(this.#reshards, performance.now(), previousTotalShards)
966
+ if (refused !== undefined) {
967
+ this.#log(
968
+ "error",
969
+ "supervisor.resharded",
970
+ `Fluxer closed a shard of child ${slot.configuration.id} with close code 4011 (sharding required), but the supervisor cannot move to a larger plan because ${refused}, so the supervisor shuts down`,
971
+ slot,
972
+ { fields: { totalShards: previousTotalShards } },
973
+ )
974
+ this.#fail(new SupervisorError(slot.configuration.id, "closed"))
975
+ return
976
+ }
977
+ this.#resharding = { previousTotalShards, childId: slot.configuration.id }
978
+ if (this.#grantTimer) clearTimeout(this.#grantTimer)
979
+ this.#grantTimer = undefined
980
+ this.#pending = []
981
+ // A granted Identify can still reach Fluxer before its child stops. It stays outstanding until the child reports
982
+ // it sent or exits, so the larger plan's first Identify keeps the spacing after it
983
+ if (this.#outstanding?.timer === undefined) this.#clearOutstanding()
984
+ for (const current of this.#slots) {
985
+ if (current.restartTimer) clearTimeout(current.restartTimer)
986
+ current.restartTimer = undefined
987
+ if (current.startupTimer) clearTimeout(current.startupTimer)
988
+ current.startupTimer = undefined
989
+ if (current.child) this.#requestStop(current)
990
+ else current.state = "closed"
991
+ }
992
+ this.#continueReshard()
993
+ }
994
+
995
+ /** Count again once every child of the old plan has exited */
996
+ #continueReshard() {
997
+ if (this.#resharding === undefined || this.#counting || this.#slots.some((slot) => slot.child !== undefined))
998
+ return
999
+ this.#startCount(this.#configuration!.automatic!)
1000
+ }
1001
+
1002
+ #spawnAll() {
1003
+ for (const slot of this.#slots) {
1004
+ this.#spawn(slot)
1005
+ if (this.#failed) break
1006
+ }
1007
+ }
1008
+
1009
+ /**
1010
+ * Count the bot's communities with a transient client, then split the resulting plan into children and start them.
1011
+ * Shutdown interrupts the count, and cleanup completes only after the transient client has closed
1012
+ */
1013
+ #countPlan(automatic: AutomaticPlan): Effect.Effect<void> {
1014
+ const owner = this
1015
+ const configuration = this.#configuration!
1016
+ const count = Effect.scoped(
1017
+ Effect.gen(function* () {
1018
+ const scope = yield* Effect.scope
1019
+ const client = yield* makeClient(automatic.clientOptions, scope, owner.#native)
1020
+ yield* Effect.addFinalizer(() => client.shutdown())
1021
+ return yield* client.countGuilds(configuration.startupTimeoutMs)
1022
+ }),
1023
+ )
1024
+ // onExit also runs when shutdown interrupts the count, so shutdown can finish after the client has closed
1025
+ return count.pipe(
1026
+ Effect.onExit((exit) => Effect.sync(() => owner.#planned(exit, automatic.split))),
1027
+ // allow-silent: #planned turns a failed count into the SupervisorError that start and waitForClose return
1028
+ Effect.ignore,
1029
+ )
1030
+ }
1031
+
1032
+ #planned(exit: Exit.Exit<number, unknown>, split: ProcessSplit) {
1033
+ this.#counting = undefined
1034
+ this.#countSettled = true
1035
+ if (this.#stopping || this.#failed) return this.#checkStopped()
1036
+ if (Exit.isFailure(exit)) {
1037
+ const failure = exit.cause.reasons.find((reason) => reason._tag === "Fail")
1038
+ const cause = failure?._tag === "Fail" ? failure.error : Cause.squash(exit.cause)
1039
+ return this.#fail(new SupervisorError(null, "shardCount", { cause }))
1040
+ }
1041
+ const guilds = exit.value
1042
+ const resharding = this.#resharding
1043
+ this.#resharding = undefined
1044
+ if (resharding !== undefined) {
1045
+ const { totalShards } = largerShardPlan(guilds, resharding.previousTotalShards)
1046
+ this.#slots = splitShards(totalShards, split).map(childSlot)
1047
+ this.#log(
1048
+ "warn",
1049
+ "supervisor.resharded",
1050
+ `Fluxer closed a shard of child ${resharding.childId} with close code 4011 (sharding required), so the supervisor moved from ${resharding.previousTotalShards} to ${totalShards} shards for ${guilds} communit${guilds === 1 ? "y" : "ies"}, split across ${this.#slots.length} child process${this.#slots.length === 1 ? "" : "es"}. Every shard starts a new session, so events sent during the move are missed`,
1051
+ undefined,
1052
+ {
1053
+ fields: {
1054
+ guilds,
1055
+ previousTotalShards: resharding.previousTotalShards,
1056
+ totalShards,
1057
+ children: this.#slots.length,
1058
+ },
1059
+ },
1060
+ )
1061
+ return this.#spawnAll()
1062
+ }
1063
+ const { totalShards } = automaticShardPlan(guilds)
1064
+ this.#slots = splitShards(totalShards, split).map(childSlot)
1065
+ this.#log(
1066
+ "info",
1067
+ "supervisor.automaticSharding",
1068
+ `The supervisor chose ${totalShards} shard${totalShards === 1 ? "" : "s"} for ${guilds} communit${guilds === 1 ? "y" : "ies"}, aiming for at most ${guildsPerShard} per shard on average, split across ${this.#slots.length} child process${this.#slots.length === 1 ? "" : "es"}`,
1069
+ undefined,
1070
+ { fields: { guilds, totalShards, guildsPerShard, children: this.#slots.length } },
1071
+ )
1072
+ this.#spawnAll()
1073
+ }
1074
+
1075
+ #spawn(slot: ChildSlot) {
1076
+ if (this.#stopping || this.#failed) return
1077
+ this.#clearDisconnectTimer(slot)
1078
+ slot.generation += 1
1079
+ slot.hello = false
1080
+ slot.ready = false
1081
+ slot.readyAt = undefined
1082
+ slot.connectionState = null
1083
+ slot.diagnostics = null
1084
+ slot.state = "starting"
1085
+ let child: ChildProcess
1086
+ const generation = slot.generation
1087
+ const output = this.#configuration!.childOutput
1088
+ const stdio = output === "prefix" ? "pipe" : output
1089
+ // Prefixed children write into pipes, so they receive the parent's console format and color rather than
1090
+ // choosing JSON for a non-terminal output. Explicit environment values still win
1091
+ const inherited =
1092
+ output === "prefix"
1093
+ ? (() => {
1094
+ const { format, color } = this.#configuration!.logger.consoleFormat("stdout")
1095
+ return { FLUXERLY_LOG_FORMAT: format, FLUXERLY_LOG_COLOR: color ? "1" : "0" }
1096
+ })()
1097
+ : {}
1098
+ try {
1099
+ child = fork(this.#configuration!.entry, [...this.#configuration!.args], {
1100
+ env: { ...inherited, ...Object.fromEntries(this.#configuration!.environment) },
1101
+ execArgv: [...this.#configuration!.execArgv],
1102
+ stdio: ["ignore", stdio, stdio, "ipc"],
1103
+ windowsHide: true,
1104
+ } as unknown as Parameters<typeof fork>[2])
1105
+ } catch (error) {
1106
+ slot.state = "failed"
1107
+ this.#log("error", "supervisor.spawnFailed", `Could not start child ${slot.configuration.id}`, slot, {
1108
+ error,
1109
+ })
1110
+ this.#fail(new SupervisorError(slot.configuration.id, "spawn", { cause: error }))
1111
+ return
1112
+ }
1113
+ // Exit is handled after forwarded output has drained, so a crash stack trace printed just before exit is kept.
1114
+ // A grandchild holding a pipe open cannot delay exit handling beyond a bounded grace period
1115
+ let openStreams = output === "prefix" ? 2 : 0
1116
+ let exited: [number | null, NodeJS.Signals | null] | undefined
1117
+ let grace: ReturnType<typeof setTimeout> | undefined
1118
+ const settle = (force = false) => {
1119
+ if (!exited || (openStreams > 0 && !force)) return
1120
+ const [code, signal] = exited
1121
+ exited = undefined
1122
+ if (grace) clearTimeout(grace)
1123
+ this.#exit(slot, child, generation, code, signal)
1124
+ }
1125
+ if (output === "prefix") {
1126
+ const drained = () => {
1127
+ openStreams -= 1
1128
+ settle()
1129
+ }
1130
+ const logger = this.#configuration!.logger
1131
+ forwardLines(child.stdout, process.stdout, "stdout", slot.configuration, logger, drained)
1132
+ forwardLines(child.stderr, process.stderr, "stderr", slot.configuration, logger, drained)
1133
+ }
1134
+ this.#log(
1135
+ "info",
1136
+ "supervisor.spawn",
1137
+ `Started child ${slot.configuration.id}${typeof child.pid === "number" ? ` (pid ${child.pid})` : ""} for ${slot.configuration.assignment.shardIds.length === 1 ? "shard" : "shards"} ${slot.configuration.assignment.shardIds.join(", ")}`,
1138
+ slot,
1139
+ { fields: { generation: slot.generation } },
1140
+ )
1141
+ slot.child = child
1142
+ const startupTimeoutMs = this.#configuration!.startupTimeoutMs
1143
+ slot.startupTimer = setTimeout(() => {
1144
+ if (slot.child !== child || slot.generation !== generation || slot.ready) return
1145
+ this.#log(
1146
+ "error",
1147
+ "supervisor.startupTimeout",
1148
+ `Child ${slot.configuration.id} did not become ready within ${startupTimeoutMs} ms (startupTimeoutMs), so the supervisor shuts down`,
1149
+ slot,
1150
+ { fields: { startupTimeoutMs } },
1151
+ )
1152
+ this.#fail(new SupervisorError(slot.configuration.id, "startupTimeout"))
1153
+ }, startupTimeoutMs)
1154
+ child.on("message", (message: unknown) => this.#message(slot, child, generation, message))
1155
+ child.once("disconnect", () => this.#disconnect(slot, child, generation))
1156
+ child.once("error", (error) => this.#childError(slot, child, generation, error))
1157
+ child.once("exit", (code, signal) => {
1158
+ exited = [code, signal]
1159
+ if (openStreams > 0) grace = setTimeout(() => settle(true), outputDrainGraceMs)
1160
+ settle()
1161
+ })
1162
+ }
1163
+
1164
+ #log(
1165
+ level: "info" | "warn" | "error",
1166
+ code: LogCode,
1167
+ message: string,
1168
+ slot: ChildSlot | undefined,
1169
+ extra: {
1170
+ readonly error?: unknown
1171
+ readonly origin?: "application"
1172
+ readonly fields?: Record<string, string | number | boolean | null>
1173
+ } = {},
1174
+ ) {
1175
+ this.#configuration?.logger.log({
1176
+ level,
1177
+ category: "supervisor",
1178
+ code,
1179
+ message,
1180
+ ...(extra.error === undefined ? {} : { error: extra.error }),
1181
+ ...(extra.origin === undefined ? {} : { origin: extra.origin }),
1182
+ fields: {
1183
+ ...(slot === undefined
1184
+ ? {}
1185
+ : { child: slot.configuration.id, shards: slot.configuration.assignment.shardIds.join(",") }),
1186
+ ...extra.fields,
1187
+ },
1188
+ })
1189
+ }
1190
+
1191
+ #childError(slot: ChildSlot, child: ChildProcess, generation: number, error?: unknown) {
1192
+ if (slot.child !== child || slot.generation !== generation) return
1193
+ slot.state = "failed"
1194
+ this.#log(
1195
+ "error",
1196
+ "supervisor.spawnFailed",
1197
+ `Child ${slot.configuration.id} failed to start, or the supervisor could not send it a message`,
1198
+ slot,
1199
+ {
1200
+ error,
1201
+ },
1202
+ )
1203
+ this.#fail(new SupervisorError(slot.configuration.id, "spawn", { cause: error }))
1204
+ if (typeof child.pid !== "number") {
1205
+ if (slot.stopTimer) clearTimeout(slot.stopTimer)
1206
+ slot.stopTimer = undefined
1207
+ this.#clearDisconnectTimer(slot)
1208
+ slot.child = undefined
1209
+ this.#checkStopped()
1210
+ return
1211
+ }
1212
+ this.#requestStop(slot)
1213
+ }
1214
+
1215
+ #disconnect(slot: ChildSlot, child: ChildProcess, generation: number) {
1216
+ if (slot.child !== child || slot.generation !== generation) return
1217
+ slot.connectionState = null
1218
+ this.#refreshReadiness()
1219
+ if (this.#stopping || this.#failed || slot.disconnectTimer) return
1220
+ if (slot.startupTimer) clearTimeout(slot.startupTimer)
1221
+ slot.startupTimer = undefined
1222
+ this.#pending = this.#pending.filter((request) => request.slot !== slot || request.generation !== generation)
1223
+ if (this.#outstanding?.slot === slot && this.#outstanding.generation === generation) {
1224
+ if (this.#outstanding.timer) clearTimeout(this.#outstanding.timer)
1225
+ this.#outstanding.permit?.abort()
1226
+ }
1227
+ // A normal process exit closes IPC just before its exit event. Reuse the configured graceful deadline
1228
+ // before classifying a still-running current child as a terminal supervisor failure
1229
+ const shutdownTimeoutMs = this.#configuration!.shutdownTimeoutMs
1230
+ slot.disconnectTimer = setTimeout(() => {
1231
+ slot.disconnectTimer = undefined
1232
+ if (
1233
+ this.#stopping ||
1234
+ this.#failed ||
1235
+ slot.child !== child ||
1236
+ slot.generation !== generation ||
1237
+ child.exitCode !== null ||
1238
+ child.signalCode !== null
1239
+ )
1240
+ return
1241
+ // The observation window is the disconnected child's only graceful exit window. Do not give it a
1242
+ // second shutdown timeout after terminal coordination loss, while sibling children still receive
1243
+ // their normal graceful stop request
1244
+ this.#log(
1245
+ "error",
1246
+ "supervisor.terminated",
1247
+ `Child ${slot.configuration.id} lost its message channel to the supervisor and was still running ${shutdownTimeoutMs} ms later (shutdownTimeoutMs), so the supervisor shuts down and force-terminates it`,
1248
+ slot,
1249
+ { fields: { shutdownTimeoutMs } },
1250
+ )
1251
+ this.#fail(new SupervisorError(slot.configuration.id, "closed"))
1252
+ this.#requestStop(slot, true)
1253
+ }, shutdownTimeoutMs)
1254
+ }
1255
+
1256
+ #message(slot: ChildSlot, child: ChildProcess, generation: number, message: unknown) {
1257
+ if (slot.child !== child || slot.generation !== generation || slot.disconnectTimer) return
1258
+ // Children that drain during a shutdown still share the account limits, so they never wait for an answer
1259
+ if (this.#accountLimitMessage(slot, generation, message)) return
1260
+ if (this.#stopping || this.#failed) return
1261
+ if (!record(message) || typeof message.type !== "string")
1262
+ return this.#fail(new SupervisorError(slot.configuration.id, "protocol"))
1263
+ if ("generation" in message && message.generation !== generation) return
1264
+ if (message.type === "hello") {
1265
+ if (!hasExactKeys(message, ["type"]) || slot.hello)
1266
+ return this.#fail(new SupervisorError(slot.configuration.id, "protocol"))
1267
+ slot.hello = true
1268
+ const { diagnosticsIntervalMs, shutdownTimeoutMs } = this.#configuration!
1269
+ this.#send(slot, {
1270
+ type: "assignment",
1271
+ generation,
1272
+ assignment: slot.configuration.assignment,
1273
+ diagnosticsIntervalMs,
1274
+ // A stopping child lets running work finish, keeping a reserve of shutdownTimeoutMs to close
1275
+ drainMs: Math.max(0, shutdownTimeoutMs - childCloseReserveMs),
1276
+ })
1277
+ // A new or restarted child starts with the account's running global pause
1278
+ const waitMs = Math.ceil(this.#globalPauseUntil - performance.now())
1279
+ if (waitMs > 0) this.#send(slot, { type: "globalPause", generation, waitMs })
1280
+ return
1281
+ }
1282
+ if (
1283
+ message.type === "diagnostics" &&
1284
+ hasExactKeys(message, ["type", "generation", "diagnostics"]) &&
1285
+ slot.ready &&
1286
+ record(message.diagnostics) &&
1287
+ hasExactKeys(message.diagnostics, diagnosticsKeys)
1288
+ ) {
1289
+ slot.diagnostics = Object.freeze({
1290
+ receivedAt: Date.now(),
1291
+ client: deepFreeze(message.diagnostics as unknown as ClientDiagnostics),
1292
+ })
1293
+ return
1294
+ }
1295
+ if (
1296
+ message.type === "state" &&
1297
+ hasExactKeys(message, ["type", "generation", "state"]) &&
1298
+ slot.hello &&
1299
+ !slot.ready &&
1300
+ connectionState(message.state)
1301
+ )
1302
+ return
1303
+ if (message.type === "ready" && hasExactKeys(message, ["type", "generation"]) && slot.hello && !slot.ready) {
1304
+ slot.ready = true
1305
+ slot.readyAt = performance.now()
1306
+ slot.state = "running"
1307
+ if (slot.startupTimer) clearTimeout(slot.startupTimer)
1308
+ slot.startupTimer = undefined
1309
+ if (this.#slots.every((current) => current.ready)) {
1310
+ this.#state = "running"
1311
+ Deferred.doneUnsafe(this.#startup, Effect.void)
1312
+ }
1313
+ return
1314
+ }
1315
+ if (
1316
+ message.type === "state" &&
1317
+ hasExactKeys(message, ["type", "generation", "state"]) &&
1318
+ slot.hello &&
1319
+ slot.ready &&
1320
+ connectionState(message.state)
1321
+ ) {
1322
+ slot.connectionState = message.state
1323
+ this.#refreshReadiness()
1324
+ return
1325
+ }
1326
+ if (
1327
+ message.type === "identify" &&
1328
+ hasExactKeys(message, ["type", "generation", "requestId", "shardId"]) &&
1329
+ safeInteger(message.requestId) &&
1330
+ message.requestId >= 0 &&
1331
+ safeInteger(message.shardId) &&
1332
+ slot.hello &&
1333
+ slot.ready &&
1334
+ slot.configuration.assignment.shardIds.includes(message.shardId)
1335
+ ) {
1336
+ // Every child stops during a reshard, so its request stays unanswered until stopping withdraws it
1337
+ if (this.#resharding !== undefined) return
1338
+ if (
1339
+ this.#pending.some(
1340
+ (request) =>
1341
+ request.slot === slot &&
1342
+ request.generation === generation &&
1343
+ request.requestId === message.requestId,
1344
+ ) ||
1345
+ (this.#outstanding?.slot === slot &&
1346
+ this.#outstanding.generation === generation &&
1347
+ this.#outstanding.requestId === message.requestId)
1348
+ )
1349
+ return this.#fail(new SupervisorError(slot.configuration.id, "protocol"))
1350
+ this.#pending.push({ slot, generation, requestId: message.requestId, shardId: message.shardId })
1351
+ this.#scheduleGrant()
1352
+ return
1353
+ }
1354
+ if (
1355
+ message.type === "cancel" &&
1356
+ hasExactKeys(message, ["type", "generation", "requestId"]) &&
1357
+ safeInteger(message.requestId) &&
1358
+ message.requestId >= 0
1359
+ ) {
1360
+ if (
1361
+ this.#outstanding?.slot === slot &&
1362
+ this.#outstanding.generation === generation &&
1363
+ this.#outstanding.requestId === message.requestId
1364
+ ) {
1365
+ if (this.#outstanding.stalled) return
1366
+ this.#clearOutstanding()
1367
+ this.#send(slot, { type: "cancelled", generation, requestId: message.requestId })
1368
+ this.#scheduleGrant()
1369
+ return
1370
+ }
1371
+ this.#pending = this.#pending.filter(
1372
+ (request) =>
1373
+ !(
1374
+ request.slot === slot &&
1375
+ request.generation === generation &&
1376
+ request.requestId === message.requestId
1377
+ ),
1378
+ )
1379
+ this.#send(slot, { type: "cancelled", generation, requestId: message.requestId })
1380
+ return
1381
+ }
1382
+ if (
1383
+ message.type === "sent" &&
1384
+ hasExactKeys(message, ["type", "generation", "requestId"]) &&
1385
+ safeInteger(message.requestId) &&
1386
+ this.#outstanding?.slot === slot &&
1387
+ this.#outstanding.generation === generation &&
1388
+ this.#outstanding.requestId === message.requestId &&
1389
+ // A send before the grant, while the coordinator is still deciding, is a protocol failure
1390
+ this.#outstanding.timer !== undefined
1391
+ ) {
1392
+ if (this.#outstanding.stalled) return
1393
+ this.#clearOutstanding()
1394
+ this.#lastIdentifyAt = performance.now()
1395
+ this.#scheduleGrant()
1396
+ return
1397
+ }
1398
+ if (
1399
+ (message.type === "closed" || message.type === "failed") &&
1400
+ hasExactKeys(
1401
+ message,
1402
+ message.type === "closed" ? ["type", "generation"] : ["type", "generation", "reason"],
1403
+ ) &&
1404
+ slot.hello
1405
+ ) {
1406
+ if (
1407
+ message.type === "failed" &&
1408
+ message.reason !== "client" &&
1409
+ message.reason !== "configure" &&
1410
+ message.reason !== "sharding"
1411
+ )
1412
+ return this.#fail(new SupervisorError(slot.configuration.id, "protocol"))
1413
+ // An explicit total is the application's plan, so its 4011 closure is an ordinary child failure
1414
+ if (message.type === "failed" && message.reason === "sharding" && this.#configuration!.automatic)
1415
+ return this.#reshard(slot)
1416
+ this.#requestStop(slot)
1417
+ return
1418
+ }
1419
+ this.#fail(new SupervisorError(slot.configuration.id, "protocol"))
1420
+ }
1421
+
1422
+ /**
1423
+ * Handle a child message about Fluxer's account-wide limits, in every supervisor state. Returns false for any other
1424
+ * message, including a malformed one, which the caller then treats like other messages
1425
+ */
1426
+ #accountLimitMessage(slot: ChildSlot, generation: number, message: unknown): boolean {
1427
+ if (!record(message) || message.generation !== generation || !slot.hello) return false
1428
+ const { type, requestId } = message
1429
+ const request = safeInteger(requestId) && requestId >= 0 ? requestId : undefined
1430
+ const exact = (keys: readonly string[]) => hasExactKeys(message, ["type", "generation", ...keys])
1431
+ if (type === "globalPause" && exact(["waitMs"]) && positiveTimer(message.waitMs)) {
1432
+ this.#relayGlobalPause(slot, message.waitMs)
1433
+ return true
1434
+ }
1435
+ if (type === "memberRequest" && exact(["requestId"]) && request !== undefined) {
1436
+ const now = performance.now()
1437
+ this.#memberRequests = this.#memberRequests.filter(({ at }) => at > now - memberRequestWindowMs)
1438
+ if (this.#memberRequests.length >= memberRequestLimit) {
1439
+ const oldest = this.#memberRequests[this.#memberRequests.length - memberRequestLimit]!
1440
+ this.#send(slot, {
1441
+ type: "memberDenied",
1442
+ generation,
1443
+ requestId: request,
1444
+ retryAfterMs: Math.max(1, Math.ceil(oldest.at + memberRequestWindowMs - now)),
1445
+ })
1446
+ return true
1447
+ }
1448
+ this.#countMemberRequest({ at: now, holder: { slot, generation, requestId: request } })
1449
+ this.#send(slot, { type: "memberGrant", generation, requestId: request })
1450
+ return true
1451
+ }
1452
+ // A sent report without requestId is a member request that had no grant, such as one from gateway.send
1453
+ if (type === "memberSent" && (exact([]) || (exact(["requestId"]) && request !== undefined))) {
1454
+ if (request !== undefined) this.#releaseMemberRequest(slot, generation, request)
1455
+ this.#countMemberRequest({ at: performance.now() })
1456
+ return true
1457
+ }
1458
+ if (type === "memberWithdrawn" && exact(["requestId"]) && request !== undefined) {
1459
+ this.#releaseMemberRequest(slot, generation, request)
1460
+ return true
1461
+ }
1462
+ return false
1463
+ }
1464
+
1465
+ /** Record a global pause one child learned and pass it to every other child, unless a running pause ends later */
1466
+ #relayGlobalPause(source: ChildSlot, waitMs: number) {
1467
+ const until = performance.now() + waitMs
1468
+ if (until <= this.#globalPauseUntil) return
1469
+ this.#globalPauseUntil = until
1470
+ for (const slot of this.#slots)
1471
+ if (slot !== source && slot.hello && slot.child?.connected && !slot.disconnectTimer)
1472
+ this.#send(slot, { type: "globalPause", generation: slot.generation, waitMs })
1473
+ }
1474
+
1475
+ /** Count a member request as the latest, keeping only the latest memberRequestLimit */
1476
+ #countMemberRequest(request: CountedMemberRequest) {
1477
+ this.#memberRequests.push(request)
1478
+ if (this.#memberRequests.length > memberRequestLimit) this.#memberRequests.shift()
1479
+ }
1480
+
1481
+ /** Stop counting a child's granted request from its grant. It has been withdrawn, or is counted again as sent */
1482
+ #releaseMemberRequest(slot: ChildSlot, generation: number, requestId: number) {
1483
+ const index = this.#memberRequests.findIndex(
1484
+ ({ holder }) => holder?.slot === slot && holder.generation === generation && holder.requestId === requestId,
1485
+ )
1486
+ if (index !== -1) this.#memberRequests.splice(index, 1)
1487
+ }
1488
+
1489
+ #scheduleGrant() {
1490
+ if (this.#grantTimer || this.#outstanding || this.#stopping || this.#failed || this.#pending.length === 0)
1491
+ return
1492
+ const delay = Math.max(0, this.#lastIdentifyAt + this.#configuration!.minimumSpacingMs - performance.now())
1493
+ if (delay === 0) return this.#grant()
1494
+ this.#grantTimer = setTimeout(() => {
1495
+ this.#grantTimer = undefined
1496
+ this.#scheduleGrant()
1497
+ }, Math.ceil(delay))
1498
+ }
1499
+
1500
+ #refreshReadiness() {
1501
+ const ready = this.#allConnected()
1502
+ if (ready && !this.#readyObserved) {
1503
+ this.#readyObserved = true
1504
+ Deferred.doneUnsafe(this.#readiness, Effect.void)
1505
+ } else if (!ready && this.#readyObserved) {
1506
+ this.#readyObserved = false
1507
+ this.#readiness = Deferred.makeUnsafe<void, SupervisorError>()
1508
+ }
1509
+ }
1510
+
1511
+ #grant() {
1512
+ if (this.#stopping || this.#failed || this.#outstanding) return
1513
+ while (this.#pending.length) {
1514
+ const request = this.#pending.shift()!
1515
+ if (request.slot.child === undefined || request.slot.generation !== request.generation) continue
1516
+ const outstanding: OutstandingIdentify = { ...request, timer: undefined, permit: undefined, stalled: false }
1517
+ this.#outstanding = outstanding
1518
+ const coordinator = this.#configuration!.coordinator
1519
+ if (coordinator) this.#askCoordinator(outstanding, coordinator)
1520
+ else this.#sendGrant(outstanding)
1521
+ return
1522
+ }
1523
+ }
1524
+
1525
+ /**
1526
+ * Wait for the application coordinator before granting. The request stays outstanding meanwhile, so no other child
1527
+ * is granted, and a cancel, exit or shutdown aborts the permit signal
1528
+ */
1529
+ #askCoordinator(outstanding: OutstandingIdentify, coordinator: CoordinatorPermit) {
1530
+ const controller = new AbortController()
1531
+ outstanding.permit = controller
1532
+ const slot = outstanding.slot
1533
+ const totalShards = slot.configuration.assignment.totalShards
1534
+ let permit: Promise<unknown>
1535
+ try {
1536
+ permit = Promise.resolve(coordinator(outstanding.shardId, totalShards, controller.signal))
1537
+ } catch (error) {
1538
+ permit = Promise.reject(error)
1539
+ }
1540
+ permit.then(
1541
+ () => {
1542
+ if (controller.signal.aborted || this.#outstanding !== outstanding) return
1543
+ outstanding.permit = undefined
1544
+ this.#sendGrant(outstanding)
1545
+ },
1546
+ (error: unknown) => {
1547
+ // A rejection after this supervisor aborted the permit answers its own cancellation
1548
+ if (controller.signal.aborted || this.#outstanding !== outstanding) return
1549
+ outstanding.permit = undefined
1550
+ this.#log(
1551
+ "error",
1552
+ "supervisor.identifyPermitFailed",
1553
+ `The identify coordinator (identify.coordinator) failed to grant shard ${outstanding.shardId} permission to start a new session, so child ${slot.configuration.id} retries the connection as after a network failure`,
1554
+ slot,
1555
+ { error, origin: "application", fields: { shardId: outstanding.shardId } },
1556
+ )
1557
+ this.#clearOutstanding()
1558
+ this.#send(slot, {
1559
+ type: "denied",
1560
+ generation: outstanding.generation,
1561
+ requestId: outstanding.requestId,
1562
+ })
1563
+ this.#scheduleGrant()
1564
+ },
1565
+ )
1566
+ }
1567
+
1568
+ #sendGrant(outstanding: OutstandingIdentify) {
1569
+ outstanding.timer = setTimeout(() => {
1570
+ if (this.#outstanding === outstanding) {
1571
+ outstanding.stalled = true
1572
+ this.#log(
1573
+ "warn",
1574
+ "supervisor.identifyUnacknowledged",
1575
+ `Child ${outstanding.slot.configuration.id} did not confirm sending Identify for shard ${outstanding.shardId} within ${grantAcknowledgementMs} ms of its permission, so the supervisor stops it`,
1576
+ outstanding.slot,
1577
+ { fields: { shardId: outstanding.shardId } },
1578
+ )
1579
+ this.#requestStop(outstanding.slot)
1580
+ }
1581
+ }, grantAcknowledgementMs)
1582
+ if (
1583
+ !this.#send(outstanding.slot, {
1584
+ type: "grant",
1585
+ generation: outstanding.generation,
1586
+ requestId: outstanding.requestId,
1587
+ })
1588
+ )
1589
+ this.#requestStop(outstanding.slot)
1590
+ }
1591
+
1592
+ #clearOutstanding() {
1593
+ if (!this.#outstanding) return
1594
+ if (this.#outstanding.timer) clearTimeout(this.#outstanding.timer)
1595
+ this.#outstanding.permit?.abort()
1596
+ this.#outstanding = undefined
1597
+ }
1598
+
1599
+ #send(slot: ChildSlot, message: object): boolean {
1600
+ const child = slot.child
1601
+ if (!child || !child.connected) {
1602
+ // Parent-initiated shutdown remains successful when a child has already lost IPC. The owned process
1603
+ // still follows the normal stop deadline and verified-exit path
1604
+ if (!this.#stopping && !this.#failed && !slot.disconnectTimer)
1605
+ this.#fail(new SupervisorError(slot.configuration.id, "spawn"))
1606
+ return false
1607
+ }
1608
+ try {
1609
+ child.send(message, undefined, undefined, (error) => {
1610
+ // A child exiting on its own can fail a stop request with EPIPE before IPC reports the disconnect.
1611
+ // The stop deadline and verified exit still complete a shutdown or the stop of one child, so a failed
1612
+ // send cannot fail either
1613
+ if (
1614
+ error &&
1615
+ slot.child === child &&
1616
+ !this.#stopping &&
1617
+ slot.state !== "stopping" &&
1618
+ !slot.disconnectTimer
1619
+ )
1620
+ this.#childError(slot, child, slot.generation, error)
1621
+ })
1622
+ return true
1623
+ } catch (error) {
1624
+ if ((this.#stopping && !child.connected) || slot.disconnectTimer) return false
1625
+ this.#childError(slot, child, slot.generation, error)
1626
+ return false
1627
+ }
1628
+ }
1629
+
1630
+ #exit(
1631
+ slot: ChildSlot,
1632
+ child: ChildProcess,
1633
+ generation: number,
1634
+ code: number | null = null,
1635
+ signal: NodeJS.Signals | null = null,
1636
+ ) {
1637
+ if (slot.child !== child || slot.generation !== generation) return
1638
+ const expected = this.#stopping || slot.state === "stopping"
1639
+ this.#log(
1640
+ expected ? "info" : "warn",
1641
+ "supervisor.exit",
1642
+ `Child ${slot.configuration.id} exited${signal === null ? ` with code ${code ?? "unknown"}` : ` after signal ${signal}`}${expected ? "" : " unexpectedly"}`,
1643
+ slot,
1644
+ { fields: { exitCode: code, signal } },
1645
+ )
1646
+ slot.child = undefined
1647
+ slot.connectionState = null
1648
+ slot.diagnostics = null
1649
+ this.#refreshReadiness()
1650
+ if (slot.startupTimer) clearTimeout(slot.startupTimer)
1651
+ slot.startupTimer = undefined
1652
+ if (slot.stopTimer) clearTimeout(slot.stopTimer)
1653
+ slot.stopTimer = undefined
1654
+ this.#clearDisconnectTimer(slot)
1655
+ this.#pending = this.#pending.filter((request) => request.slot !== slot || request.generation !== generation)
1656
+ if (this.#outstanding?.slot === slot && this.#outstanding.generation === generation) {
1657
+ this.#clearOutstanding()
1658
+ // The child might have sent after the parent lost IPC, so start a fresh full interval only after verified exit
1659
+ this.#lastIdentifyAt = performance.now()
1660
+ }
1661
+ // A granted member request the child never reported may have reached Fluxer just before the exit, so it counts
1662
+ // from the exit
1663
+ const exited = ({ holder }: CountedMemberRequest) => holder?.slot === slot && holder.generation === generation
1664
+ const held = this.#memberRequests.filter(exited).length
1665
+ this.#memberRequests = this.#memberRequests.filter((request) => !exited(request))
1666
+ for (let index = 0; index < held; index++) this.#countMemberRequest({ at: performance.now() })
1667
+ if (this.#stopping || this.#failed) {
1668
+ slot.state = this.#failed ? "failed" : "closed"
1669
+ this.#checkStopped()
1670
+ return
1671
+ }
1672
+ if (this.#resharding !== undefined) {
1673
+ slot.state = "closed"
1674
+ return this.#continueReshard()
1675
+ }
1676
+ const restart = this.#configuration!.restart
1677
+ if (!restart) {
1678
+ slot.state = "failed"
1679
+ this.#log(
1680
+ "error",
1681
+ "supervisor.crash",
1682
+ `Child ${slot.configuration.id} stopped unexpectedly, and the supervisor option restart is false, so the supervisor shuts down`,
1683
+ slot,
1684
+ {
1685
+ fields: { exitCode: code, signal },
1686
+ },
1687
+ )
1688
+ this.#fail(new SupervisorError(slot.configuration.id, "closed"))
1689
+ return
1690
+ }
1691
+ // Only consecutive crashes count: A child that ran long enough after readiness failed on its own, not in a loop
1692
+ const budgetReset =
1693
+ slot.restarts > 0 &&
1694
+ slot.readyAt !== undefined &&
1695
+ performance.now() - slot.readyAt >= restart.healthyResetMs
1696
+ if (budgetReset) slot.restarts = 0
1697
+ if (slot.restarts >= restart.maxAttempts) {
1698
+ slot.state = "failed"
1699
+ this.#log(
1700
+ "error",
1701
+ "supervisor.crash",
1702
+ `Child ${slot.configuration.id} stopped again after using all ${restart.maxAttempts} restarts (restart.maxAttempts), so the supervisor shuts down`,
1703
+ slot,
1704
+ { fields: { exitCode: code, signal, restarts: slot.restarts } },
1705
+ )
1706
+ this.#fail(new SupervisorError(slot.configuration.id, "restartLimit"))
1707
+ return
1708
+ }
1709
+ slot.restarts += 1
1710
+ slot.state = "restarting"
1711
+ const delay = Math.min(restart.maxDelayMs, restart.minDelayMs * 2 ** (slot.restarts - 1))
1712
+ this.#log(
1713
+ "warn",
1714
+ "supervisor.restart",
1715
+ `Restarting child ${slot.configuration.id} in ${delay} ms (restart ${slot.restarts} of ${restart.maxAttempts}${budgetReset ? ", count reset after a healthy run" : ""})`,
1716
+ slot,
1717
+ { fields: { restarts: slot.restarts, delayMs: delay, budgetReset } },
1718
+ )
1719
+ slot.restartTimer = setTimeout(() => {
1720
+ slot.restartTimer = undefined
1721
+ this.#spawn(slot)
1722
+ }, delay)
1723
+ this.#scheduleGrant()
1724
+ }
1725
+
1726
+ #requestStop(slot: ChildSlot, force = false) {
1727
+ const child = slot.child
1728
+ if (!child) return
1729
+ if (force) {
1730
+ if (slot.stopTimer) clearTimeout(slot.stopTimer)
1731
+ slot.stopTimer = undefined
1732
+ slot.state = "stopping"
1733
+ try {
1734
+ // The disconnected child has already consumed its configured observation window
1735
+ child.kill("SIGKILL")
1736
+ } catch (error) {
1737
+ this.#childError(slot, child, slot.generation, error)
1738
+ }
1739
+ return
1740
+ }
1741
+ if (slot.stopTimer) return
1742
+ slot.state = "stopping"
1743
+ const generation = slot.generation
1744
+ const shutdownTimeoutMs = this.#configuration!.shutdownTimeoutMs
1745
+ slot.stopTimer = setTimeout(() => {
1746
+ if (slot.child !== child || slot.generation !== generation) return
1747
+ this.#log(
1748
+ "warn",
1749
+ "supervisor.terminated",
1750
+ `Child ${slot.configuration.id} did not exit within ${shutdownTimeoutMs} ms (shutdownTimeoutMs) of the stop request, so the supervisor force-terminates it`,
1751
+ slot,
1752
+ { fields: { shutdownTimeoutMs } },
1753
+ )
1754
+ try {
1755
+ // Only this exact ChildProcess is force-terminated. Completion still waits for its exit event
1756
+ child.kill("SIGKILL")
1757
+ } catch (error) {
1758
+ this.#childError(slot, child, generation, error)
1759
+ }
1760
+ }, shutdownTimeoutMs)
1761
+ this.#send(slot, { type: "shutdown", generation })
1762
+ }
1763
+
1764
+ #fail(error: SupervisorError) {
1765
+ if (this.#failed) return
1766
+ this.#failed = true
1767
+ this.#state = "failed"
1768
+ this.#failure = error
1769
+ this.#beginShutdown()
1770
+ }
1771
+
1772
+ #beginShutdown() {
1773
+ if (this.#stopping) return
1774
+ this.#stopping = true
1775
+ if (!this.#failed) this.#state = "stopping"
1776
+ if (this.#grantTimer) clearTimeout(this.#grantTimer)
1777
+ this.#grantTimer = undefined
1778
+ this.#pending = []
1779
+ if (this.#outstanding?.timer) clearTimeout(this.#outstanding.timer)
1780
+ this.#outstanding?.permit?.abort()
1781
+ // The count's own cleanup closes its transient client, and #planned then completes the shutdown
1782
+ if (this.#counting) Effect.runFork(Fiber.interrupt(this.#counting))
1783
+ for (const slot of this.#slots) {
1784
+ if (slot.restartTimer) clearTimeout(slot.restartTimer)
1785
+ slot.restartTimer = undefined
1786
+ if (slot.startupTimer) clearTimeout(slot.startupTimer)
1787
+ slot.startupTimer = undefined
1788
+ this.#clearDisconnectTimer(slot)
1789
+ if (slot.child) this.#requestStop(slot)
1790
+ else {
1791
+ slot.state = this.#failed ? "failed" : "closed"
1792
+ slot.connectionState = null
1793
+ }
1794
+ }
1795
+ this.#checkStopped()
1796
+ }
1797
+
1798
+ #clearDisconnectTimer(slot: ChildSlot) {
1799
+ if (slot.disconnectTimer) clearTimeout(slot.disconnectTimer)
1800
+ slot.disconnectTimer = undefined
1801
+ }
1802
+
1803
+ #checkStopped() {
1804
+ if (this.#counting || this.#slots.some((slot) => slot.child !== undefined)) return
1805
+ this.#clearOutstanding()
1806
+ if (this.#failed) {
1807
+ Deferred.doneUnsafe(this.#startup, Effect.fail(this.#failure!))
1808
+ Deferred.doneUnsafe(this.#terminal, Effect.fail(this.#failure!))
1809
+ Deferred.doneUnsafe(this.#readiness, Effect.fail(this.#failure!))
1810
+ } else {
1811
+ this.#state = "closed"
1812
+ Deferred.doneUnsafe(this.#startup, Effect.fail(new SupervisorError(null, "closed")))
1813
+ Deferred.doneUnsafe(this.#terminal, Effect.void)
1814
+ Deferred.doneUnsafe(this.#readiness, Effect.fail(new SupervisorError(null, "closed")))
1815
+ }
1816
+ this.#configuration = undefined
1817
+ Deferred.doneUnsafe(this.#stopped, Effect.void)
1818
+ }
1819
+ }
1820
+
1821
+ /** The failure of a session start that the supervisor can no longer grant, because it stopped this child or lost contact */
1822
+ function supervisorStopped(): ConnectionError {
1823
+ return new ConnectionError("gateway", "closed", null, {
1824
+ details: { detail: "the supervisor stopped this child or lost contact with it" },
1825
+ })
1826
+ }
1827
+
1828
+ interface PendingPermit {
1829
+ readonly send: () => void
1830
+ readonly resume: (effect: Effect.Effect<void, ConnectionError>) => void
1831
+ }
1832
+
1833
+ const unreachable: MemberRequestSlot = Object.freeze({ kind: "unreachable" })
1834
+
1835
+ /** Child-side IPC bridge. It owns no process signals and reports no child output */
1836
+ export class ChildBridge {
1837
+ readonly #assignment = Deferred.makeUnsafe<SupervisorAssignment, SupervisorChildError>()
1838
+ readonly #stop = Deferred.makeUnsafe<void, SupervisorChildError>()
1839
+ readonly #pending = new Map<number, PendingPermit>()
1840
+ readonly #cancelled = new Set<number>()
1841
+ /** Member request slots waiting for the parent's answer, by request ID */
1842
+ readonly #memberAnswers = new Map<number, (slot: MemberRequestSlot) => void>()
1843
+ /** Host time at which the latest global pause the parent relayed ends */
1844
+ #globalPauseUntil = 0
1845
+ #onGlobalPause: ((waitMs: number) => void) | undefined
1846
+ #generation: number | undefined
1847
+ #diagnosticsIntervalMs = defaultDiagnosticsIntervalMs
1848
+ #drainMs = 0
1849
+ #diagnosticsTimer: ReturnType<typeof setInterval> | undefined
1850
+ #nextRequestId = 0
1851
+ #stopping = false
1852
+ #ended = false
1853
+ #cleaned = false
1854
+ readonly #abort = new AbortController()
1855
+
1856
+ readonly signal: AbortSignal = this.#abort.signal
1857
+
1858
+ readonly identifyGate: IdentifyGate = {
1859
+ permit: (shardId, send) => this.#permit(shardId, send),
1860
+ }
1861
+
1862
+ readonly accountLimits: AccountLimits = {
1863
+ shareGlobalPause: (waitMs) => {
1864
+ if (!this.#ended && this.#generation !== undefined && positiveTimer(waitMs))
1865
+ this.#send({ type: "globalPause", generation: this.#generation, waitMs })
1866
+ },
1867
+ onGlobalPause: (listener) => {
1868
+ this.#onGlobalPause = listener
1869
+ const waitMs = Math.ceil(this.#globalPauseUntil - performance.now())
1870
+ if (waitMs > 0) listener(waitMs)
1871
+ },
1872
+ members: {
1873
+ request: () => this.#memberRequest(),
1874
+ sent: () => {
1875
+ if (!this.#ended && this.#generation !== undefined)
1876
+ this.#send({ type: "memberSent", generation: this.#generation })
1877
+ },
1878
+ },
1879
+ }
1880
+
1881
+ private readonly onMessage = (message: unknown) => this.#message(message)
1882
+ private readonly onDisconnect = () => this.#disconnect()
1883
+
1884
+ private constructor() {
1885
+ process.on("message", this.onMessage)
1886
+ process.once("disconnect", this.onDisconnect)
1887
+ if (!this.#send({ type: "hello" })) this.#disconnect()
1888
+ }
1889
+
1890
+ static open(): Effect.Effect<ChildBridge, SupervisorChildError> {
1891
+ return Effect.suspend(() => {
1892
+ if (typeof process.send !== "function" || !process.connected)
1893
+ return Effect.fail(new SupervisorChildError("disconnected"))
1894
+ return Effect.succeed(new ChildBridge())
1895
+ })
1896
+ }
1897
+
1898
+ waitForAssignment(): Effect.Effect<SupervisorAssignment, SupervisorChildError> {
1899
+ return Deferred.await(this.#assignment)
1900
+ }
1901
+
1902
+ waitForStop(): Effect.Effect<void, SupervisorChildError> {
1903
+ return Deferred.await(this.#stop)
1904
+ }
1905
+
1906
+ ready() {
1907
+ if (!this.#ended && this.#generation !== undefined) this.#send({ type: "ready", generation: this.#generation })
1908
+ }
1909
+
1910
+ state(state: ConnectionState) {
1911
+ if (!this.#ended && this.#generation !== undefined)
1912
+ this.#send({ type: "state", generation: this.#generation, state })
1913
+ }
1914
+
1915
+ /** How long a stop requested by the parent lets running work finish, within the parent's shutdownTimeoutMs */
1916
+ get drainMs() {
1917
+ return this.#drainMs
1918
+ }
1919
+
1920
+ failed(reason: "client" | "configure" | "sharding") {
1921
+ if (!this.#ended && this.#generation !== undefined)
1922
+ this.#send({ type: "failed", generation: this.#generation, reason })
1923
+ }
1924
+
1925
+ /**
1926
+ * Send the client's diagnostics now and then at the parent's interval until this bridge closes. The timer does not
1927
+ * keep the process alive
1928
+ */
1929
+ reportDiagnostics(read: () => ClientDiagnostics) {
1930
+ if (this.#diagnosticsTimer || this.#ended) return
1931
+ const report = () => {
1932
+ if (!this.#ended && this.#generation !== undefined)
1933
+ this.#send({ type: "diagnostics", generation: this.#generation, diagnostics: read() })
1934
+ }
1935
+ report()
1936
+ this.#diagnosticsTimer = setInterval(report, this.#diagnosticsIntervalMs)
1937
+ this.#diagnosticsTimer.unref()
1938
+ }
1939
+
1940
+ close() {
1941
+ if (!this.#ended) {
1942
+ this.#ended = true
1943
+ this.#abort.abort()
1944
+ if (this.#generation !== undefined) this.#send({ type: "closed", generation: this.#generation })
1945
+ }
1946
+ Deferred.doneUnsafe(this.#stop, Effect.void)
1947
+ this.#cleanup(true)
1948
+ }
1949
+
1950
+ #permit(shardId: number, send: () => void): Effect.Effect<void, ConnectionError> {
1951
+ const bridge = this
1952
+ return Effect.callback<void, ConnectionError>((resume) => {
1953
+ const generation = bridge.#generation
1954
+ const requestId = bridge.#nextRequestId++
1955
+ if (bridge.#ended || bridge.#stopping || generation === undefined) {
1956
+ resume(Effect.fail(supervisorStopped()))
1957
+ return
1958
+ }
1959
+ bridge.#pending.set(requestId, { send, resume })
1960
+ if (!bridge.#send({ type: "identify", generation, requestId, shardId })) {
1961
+ bridge.#pending.delete(requestId)
1962
+ resume(Effect.fail(supervisorStopped()))
1963
+ return
1964
+ }
1965
+ return Effect.sync(() => {
1966
+ if (bridge.#pending.delete(requestId)) {
1967
+ bridge.#cancelled.add(requestId)
1968
+ bridge.#send({ type: "cancel", generation, requestId })
1969
+ }
1970
+ })
1971
+ })
1972
+ }
1973
+
1974
+ /**
1975
+ * Ask the parent for a member request slot. The answer is unreachable at once without a channel, when the channel
1976
+ * closes, or after memberAnswerMs without an answer, so a child never waits on a parent that cannot answer.
1977
+ * Interruption or a missed answer withdraws the request, so a late grant frees its slot again
1978
+ */
1979
+ #memberRequest(): Effect.Effect<MemberRequestSlot> {
1980
+ const bridge = this
1981
+ return Effect.callback<MemberRequestSlot>((resume) => {
1982
+ const generation = bridge.#generation
1983
+ if (bridge.#ended || generation === undefined) {
1984
+ resume(Effect.succeed(unreachable))
1985
+ return
1986
+ }
1987
+ const requestId = bridge.#nextRequestId++
1988
+ const withdraw = () => bridge.#send({ type: "memberWithdrawn", generation, requestId })
1989
+ const timer = setTimeout(() => {
1990
+ if (!bridge.#memberAnswers.delete(requestId)) return
1991
+ withdraw()
1992
+ resume(Effect.succeed(unreachable))
1993
+ }, memberAnswerMs)
1994
+ bridge.#memberAnswers.set(requestId, (slot) => {
1995
+ clearTimeout(timer)
1996
+ resume(Effect.succeed(slot))
1997
+ })
1998
+ if (!bridge.#send({ type: "memberRequest", generation, requestId })) {
1999
+ bridge.#memberAnswers.delete(requestId)
2000
+ clearTimeout(timer)
2001
+ resume(Effect.succeed(unreachable))
2002
+ return
2003
+ }
2004
+ return Effect.sync(() => {
2005
+ if (!bridge.#memberAnswers.delete(requestId)) return
2006
+ clearTimeout(timer)
2007
+ withdraw()
2008
+ })
2009
+ })
2010
+ }
2011
+
2012
+ /** A granted slot that reports exactly once whether its request reached the socket */
2013
+ #grantedMember(generation: number, requestId: number): MemberRequestSlot {
2014
+ let reported = false
2015
+ const report = (type: "memberSent" | "memberWithdrawn") => {
2016
+ if (reported) return
2017
+ reported = true
2018
+ if (!this.#ended) this.#send({ type, generation, requestId })
2019
+ }
2020
+ return { kind: "granted", sent: () => report("memberSent"), withdraw: () => report("memberWithdrawn") }
2021
+ }
2022
+
2023
+ #message(message: unknown) {
2024
+ if (this.#ended) return
2025
+ if (!record(message) || typeof message.type !== "string") return this.#protocol()
2026
+ if (
2027
+ (message.type === "memberGrant" || message.type === "memberDenied") &&
2028
+ hasExactKeys(
2029
+ message,
2030
+ message.type === "memberGrant"
2031
+ ? ["type", "generation", "requestId"]
2032
+ : ["type", "generation", "requestId", "retryAfterMs"],
2033
+ ) &&
2034
+ safeInteger(message.generation) &&
2035
+ message.generation === this.#generation &&
2036
+ safeInteger(message.requestId) &&
2037
+ (message.type === "memberGrant" || positiveTimer(message.retryAfterMs))
2038
+ ) {
2039
+ const answer = this.#memberAnswers.get(message.requestId)
2040
+ // An answer after this child stopped waiting is ignored. The child withdrew that request then
2041
+ if (!answer) return
2042
+ this.#memberAnswers.delete(message.requestId)
2043
+ answer(
2044
+ message.type === "memberGrant"
2045
+ ? this.#grantedMember(message.generation, message.requestId)
2046
+ : { kind: "refused", retryAfterMs: message.retryAfterMs as number },
2047
+ )
2048
+ return
2049
+ }
2050
+ if (
2051
+ message.type === "globalPause" &&
2052
+ hasExactKeys(message, ["type", "generation", "waitMs"]) &&
2053
+ message.generation === this.#generation &&
2054
+ positiveTimer(message.waitMs)
2055
+ ) {
2056
+ const until = performance.now() + message.waitMs
2057
+ if (until > this.#globalPauseUntil) {
2058
+ this.#globalPauseUntil = until
2059
+ this.#onGlobalPause?.(message.waitMs)
2060
+ }
2061
+ return
2062
+ }
2063
+ if (
2064
+ message.type === "assignment" &&
2065
+ hasExactKeys(message, ["type", "generation", "assignment", "diagnosticsIntervalMs", "drainMs"]) &&
2066
+ safeInteger(message.generation) &&
2067
+ message.generation > 0 &&
2068
+ positiveTimer(message.diagnosticsIntervalMs) &&
2069
+ safeInteger(message.drainMs) &&
2070
+ message.drainMs >= 0 &&
2071
+ message.drainMs <= maximumTimerMs &&
2072
+ record(message.assignment) &&
2073
+ hasExactKeys(message.assignment, ["totalShards", "shardIds"]) &&
2074
+ safeInteger(message.assignment.totalShards) &&
2075
+ message.assignment.totalShards > 0
2076
+ ) {
2077
+ if (this.#generation !== undefined) return this.#protocol()
2078
+ const shardIds = assignment(message.assignment.shardIds, message.assignment.totalShards)
2079
+ if (!shardIds) return this.#protocol()
2080
+ this.#generation = message.generation
2081
+ this.#diagnosticsIntervalMs = message.diagnosticsIntervalMs
2082
+ this.#drainMs = message.drainMs
2083
+ Deferred.doneUnsafe(
2084
+ this.#assignment,
2085
+ Effect.succeed(
2086
+ Object.freeze({
2087
+ totalShards: message.assignment.totalShards,
2088
+ shardIds: Object.freeze([...shardIds]),
2089
+ }),
2090
+ ),
2091
+ )
2092
+ return
2093
+ }
2094
+ if (
2095
+ message.type === "grant" &&
2096
+ hasExactKeys(message, ["type", "generation", "requestId"]) &&
2097
+ message.generation === this.#generation &&
2098
+ safeInteger(message.requestId)
2099
+ ) {
2100
+ const pending = this.#pending.get(message.requestId)
2101
+ if (!pending) {
2102
+ if (this.#cancelled.delete(message.requestId)) return
2103
+ return this.#protocol()
2104
+ }
2105
+ this.#pending.delete(message.requestId)
2106
+ const generation = this.#generation
2107
+ pending.resume(
2108
+ Effect.uninterruptible(
2109
+ Effect.try({
2110
+ try: () => {
2111
+ if (this.#stopping || this.#ended) throw new Error("closed")
2112
+ pending.send()
2113
+ if (
2114
+ generation === undefined ||
2115
+ !this.#send({ type: "sent", generation, requestId: message.requestId })
2116
+ )
2117
+ throw new Error("closed")
2118
+ },
2119
+ catch: () => supervisorStopped(),
2120
+ }),
2121
+ ),
2122
+ )
2123
+ return
2124
+ }
2125
+ if (
2126
+ message.type === "cancelled" &&
2127
+ hasExactKeys(message, ["type", "generation", "requestId"]) &&
2128
+ message.generation === this.#generation &&
2129
+ safeInteger(message.requestId)
2130
+ ) {
2131
+ this.#cancelled.delete(message.requestId)
2132
+ return
2133
+ }
2134
+ if (
2135
+ message.type === "denied" &&
2136
+ hasExactKeys(message, ["type", "generation", "requestId"]) &&
2137
+ message.generation === this.#generation &&
2138
+ safeInteger(message.requestId)
2139
+ ) {
2140
+ const pending = this.#pending.get(message.requestId)
2141
+ if (!pending) {
2142
+ if (this.#cancelled.delete(message.requestId)) return
2143
+ return this.#protocol()
2144
+ }
2145
+ this.#pending.delete(message.requestId)
2146
+ // The parent logged the coordinator's failure. The client retries this like a network failure
2147
+ pending.resume(
2148
+ Effect.fail(
2149
+ new ConnectionError("gateway", "network", null, {
2150
+ details: {
2151
+ detail: "the supervisor's identify coordinator did not grant permission to start a new session",
2152
+ },
2153
+ hint: "Check the supervisor's records with code supervisor.identifyPermitFailed and the permit function of its identify.coordinator",
2154
+ }),
2155
+ ),
2156
+ )
2157
+ return
2158
+ }
2159
+ if (
2160
+ message.type === "shutdown" &&
2161
+ hasExactKeys(message, ["type", "generation"]) &&
2162
+ message.generation === this.#generation
2163
+ ) {
2164
+ this.#stopping = true
2165
+ this.#abort.abort()
2166
+ Deferred.doneUnsafe(this.#stop, Effect.void)
2167
+ return
2168
+ }
2169
+ this.#protocol()
2170
+ }
2171
+
2172
+ #disconnect() {
2173
+ if (this.#ended) return this.#cleanup(false)
2174
+ this.#ended = true
2175
+ this.#stopping = true
2176
+ this.#abort.abort()
2177
+ Deferred.doneUnsafe(this.#assignment, Effect.fail(new SupervisorChildError("disconnected")))
2178
+ Deferred.doneUnsafe(this.#stop, Effect.fail(new SupervisorChildError("disconnected")))
2179
+ this.#cleanup(false)
2180
+ }
2181
+
2182
+ #protocol() {
2183
+ if (this.#ended) return this.#cleanup(false)
2184
+ this.#ended = true
2185
+ this.#stopping = true
2186
+ Deferred.doneUnsafe(this.#assignment, Effect.fail(new SupervisorChildError("protocol")))
2187
+ Deferred.doneUnsafe(this.#stop, Effect.fail(new SupervisorChildError("protocol")))
2188
+ this.#cleanup(false)
2189
+ }
2190
+
2191
+ #cleanup(notifyCancellation: boolean) {
2192
+ if (this.#cleaned) return
2193
+ this.#cleaned = true
2194
+ if (this.#diagnosticsTimer) clearInterval(this.#diagnosticsTimer)
2195
+ this.#diagnosticsTimer = undefined
2196
+ process.off("message", this.onMessage)
2197
+ process.off("disconnect", this.onDisconnect)
2198
+ for (const [requestId, pending] of this.#pending) {
2199
+ if (notifyCancellation && this.#generation !== undefined)
2200
+ this.#send({ type: "cancel", generation: this.#generation, requestId })
2201
+ pending.resume(Effect.fail(supervisorStopped()))
2202
+ }
2203
+ this.#pending.clear()
2204
+ this.#cancelled.clear()
2205
+ const answers = [...this.#memberAnswers.values()]
2206
+ this.#memberAnswers.clear()
2207
+ for (const answer of answers) answer(unreachable)
2208
+ this.#onGlobalPause = undefined
2209
+ }
2210
+
2211
+ #send(message: object): boolean {
2212
+ try {
2213
+ if (!process.connected || typeof process.send !== "function") return false
2214
+ process.send(message, undefined, undefined, (error) => {
2215
+ if (error) this.#disconnect()
2216
+ })
2217
+ return true
2218
+ } catch {
2219
+ // allow-silent: A false return makes the child treat the parent as disconnected and stop
2220
+ return false
2221
+ }
2222
+ }
2223
+ }
2224
+
2225
+ /**
2226
+ * The failure reason a child reports for its stopped client: Sharding when Fluxer closed a shard with 4011 (sharding
2227
+ * required), so a supervisor with totalShards "auto" can move to a larger plan, otherwise client
2228
+ */
2229
+ export function childFailureReason(error: unknown): "client" | "sharding" {
2230
+ // Tags rather than classes, so a failure from another copy of the SDK module graph is still recognized
2231
+ const failure = record(error) && error._tag === "ShardConnectionError" ? error.failure : error
2232
+ return record(failure) &&
2233
+ failure._tag === "ConnectionError" &&
2234
+ failure.phase === "gateway" &&
2235
+ failure.status === CloseCode.shardingRequired
2236
+ ? "sharding"
2237
+ : "client"
2238
+ }
2239
+
2240
+ export function createSupervisor(
2241
+ options: SupervisorOptions,
2242
+ native = false,
2243
+ ): Effect.Effect<SupervisorOwner, ConfigurationError> {
2244
+ return validateSupervisorConfiguration(options, native).pipe(
2245
+ Effect.tap((configuration) =>
2246
+ Effect.withFiber((fiber) => {
2247
+ if (native) configuration.logger.context = fiber.context
2248
+ return Effect.void
2249
+ }),
2250
+ ),
2251
+ Effect.map((configuration) => new SupervisorOwner(configuration, native)),
2252
+ )
2253
+ }