rivetkit 2.0.9 → 2.0.10

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 (123) hide show
  1. package/dist/tsup/{chunk-APHV6WXU.js → chunk-346X2XU4.js} +2 -2
  2. package/dist/tsup/{chunk-DLPIL3VC.js → chunk-7E5K3375.js} +2 -2
  3. package/dist/tsup/{chunk-SOC4HWCG.cjs → chunk-CA3X5M6H.cjs} +92 -39
  4. package/dist/tsup/{chunk-VVCL5DXN.js.map → chunk-CA3X5M6H.cjs.map} +1 -1
  5. package/dist/tsup/{chunk-2MJYYF2Q.cjs → chunk-DVPXSB4B.cjs} +12 -12
  6. package/dist/tsup/{chunk-2MJYYF2Q.cjs.map → chunk-DVPXSB4B.cjs.map} +1 -1
  7. package/dist/tsup/{chunk-U2IXX6DY.cjs → chunk-GIFHYL7A.cjs} +5 -6
  8. package/dist/tsup/chunk-GIFHYL7A.cjs.map +1 -0
  9. package/dist/tsup/{chunk-KHZ2QSQ4.js → chunk-H7E2UU23.js} +32 -10
  10. package/dist/tsup/chunk-H7E2UU23.js.map +1 -0
  11. package/dist/tsup/{chunk-E63WU5PL.js → chunk-HI55LHM3.js} +5 -6
  12. package/dist/tsup/chunk-HI55LHM3.js.map +1 -0
  13. package/dist/tsup/{chunk-SDXTJDDR.cjs → chunk-I3FB346I.cjs} +58 -14
  14. package/dist/tsup/chunk-I3FB346I.cjs.map +1 -0
  15. package/dist/tsup/{chunk-WBSPHV5V.js → chunk-KGDZYQYE.js} +2 -2
  16. package/dist/tsup/{chunk-A44TWAS5.cjs → chunk-KH5WFDUK.cjs} +6 -6
  17. package/dist/tsup/{chunk-A44TWAS5.cjs.map → chunk-KH5WFDUK.cjs.map} +1 -1
  18. package/dist/tsup/{chunk-YR2VY4XS.js → chunk-KL4V2ULR.js} +5 -4
  19. package/dist/tsup/chunk-KL4V2ULR.js.map +1 -0
  20. package/dist/tsup/{chunk-R7OP5N25.js → chunk-MLQIYKAZ.js} +53 -9
  21. package/dist/tsup/chunk-MLQIYKAZ.js.map +1 -0
  22. package/dist/tsup/{chunk-F2YZNUPU.js → chunk-N3A5GYJU.js} +3 -3
  23. package/dist/tsup/{chunk-4YV6RDZL.cjs → chunk-PDFL7FBL.cjs} +698 -358
  24. package/dist/tsup/chunk-PDFL7FBL.cjs.map +1 -0
  25. package/dist/tsup/{chunk-DZZQG7VH.cjs → chunk-PPLR53PP.cjs} +3 -3
  26. package/dist/tsup/{chunk-DZZQG7VH.cjs.map → chunk-PPLR53PP.cjs.map} +1 -1
  27. package/dist/tsup/{chunk-7OMMIAWP.cjs → chunk-PSCDCEXM.cjs} +17 -12
  28. package/dist/tsup/chunk-PSCDCEXM.cjs.map +1 -0
  29. package/dist/tsup/{chunk-VVCL5DXN.js → chunk-QRFXXTLG.js} +96 -43
  30. package/dist/tsup/chunk-QRFXXTLG.js.map +1 -0
  31. package/dist/tsup/{chunk-WRSWUDFA.js → chunk-R2S45MO6.js} +14 -9
  32. package/dist/tsup/chunk-R2S45MO6.js.map +1 -0
  33. package/dist/tsup/{chunk-QGRYH6TU.cjs → chunk-SIWYIRXP.cjs} +7 -6
  34. package/dist/tsup/chunk-SIWYIRXP.cjs.map +1 -0
  35. package/dist/tsup/{chunk-FZP2IBIX.js → chunk-VJRXZPTT.js} +579 -239
  36. package/dist/tsup/chunk-VJRXZPTT.js.map +1 -0
  37. package/dist/tsup/{chunk-4PSLOAXR.cjs → chunk-VZMXAZKC.cjs} +226 -204
  38. package/dist/tsup/chunk-VZMXAZKC.cjs.map +1 -0
  39. package/dist/tsup/{chunk-DL7TPF63.cjs → chunk-YKVTF7MP.cjs} +7 -7
  40. package/dist/tsup/{chunk-DL7TPF63.cjs.map → chunk-YKVTF7MP.cjs.map} +1 -1
  41. package/dist/tsup/client/mod.cjs +9 -9
  42. package/dist/tsup/client/mod.d.cts +2 -2
  43. package/dist/tsup/client/mod.d.ts +2 -2
  44. package/dist/tsup/client/mod.js +8 -8
  45. package/dist/tsup/common/log.cjs +3 -3
  46. package/dist/tsup/common/log.js +2 -2
  47. package/dist/tsup/common/websocket.cjs +4 -4
  48. package/dist/tsup/common/websocket.js +3 -3
  49. package/dist/tsup/{conn-CEh3WKbA.d.cts → conn-Cc9WHuN4.d.cts} +196 -191
  50. package/dist/tsup/{conn-Bt8rkUzm.d.ts → conn-DfPG71FA.d.ts} +196 -191
  51. package/dist/tsup/driver-helpers/mod.cjs +5 -5
  52. package/dist/tsup/driver-helpers/mod.cjs.map +1 -1
  53. package/dist/tsup/driver-helpers/mod.d.cts +1 -1
  54. package/dist/tsup/driver-helpers/mod.d.ts +1 -1
  55. package/dist/tsup/driver-helpers/mod.js +6 -6
  56. package/dist/tsup/driver-test-suite/mod.cjs +116 -102
  57. package/dist/tsup/driver-test-suite/mod.cjs.map +1 -1
  58. package/dist/tsup/driver-test-suite/mod.d.cts +3 -2
  59. package/dist/tsup/driver-test-suite/mod.d.ts +3 -2
  60. package/dist/tsup/driver-test-suite/mod.js +61 -47
  61. package/dist/tsup/driver-test-suite/mod.js.map +1 -1
  62. package/dist/tsup/inspector/mod.cjs +6 -6
  63. package/dist/tsup/inspector/mod.d.cts +6 -6
  64. package/dist/tsup/inspector/mod.d.ts +6 -6
  65. package/dist/tsup/inspector/mod.js +5 -5
  66. package/dist/tsup/mod.cjs +10 -10
  67. package/dist/tsup/mod.d.cts +8 -39
  68. package/dist/tsup/mod.d.ts +8 -39
  69. package/dist/tsup/mod.js +9 -9
  70. package/dist/tsup/test/mod.cjs +11 -11
  71. package/dist/tsup/test/mod.d.cts +1 -1
  72. package/dist/tsup/test/mod.d.ts +1 -1
  73. package/dist/tsup/test/mod.js +10 -10
  74. package/dist/tsup/utils.cjs +2 -2
  75. package/dist/tsup/utils.d.cts +2 -1
  76. package/dist/tsup/utils.d.ts +2 -1
  77. package/dist/tsup/utils.js +1 -1
  78. package/package.json +4 -5
  79. package/src/actor/driver.ts +2 -2
  80. package/src/actor/protocol/serde.ts +75 -3
  81. package/src/actor/router-endpoints.ts +6 -6
  82. package/src/actor/router.ts +2 -2
  83. package/src/client/actor-conn.ts +24 -3
  84. package/src/client/config.ts +18 -25
  85. package/src/driver-helpers/mod.ts +4 -1
  86. package/src/driver-test-suite/mod.ts +65 -43
  87. package/src/driver-test-suite/utils.ts +4 -1
  88. package/src/drivers/default.ts +11 -9
  89. package/src/drivers/engine/actor-driver.ts +40 -39
  90. package/src/drivers/engine/config.ts +9 -22
  91. package/src/drivers/engine/mod.ts +9 -8
  92. package/src/drivers/file-system/global-state.ts +4 -4
  93. package/src/engine-process/log.ts +5 -0
  94. package/src/engine-process/mod.ts +316 -0
  95. package/src/inspector/utils.ts +6 -4
  96. package/src/manager/driver.ts +2 -2
  97. package/src/manager/gateway.ts +29 -11
  98. package/src/manager/router-schema.ts +20 -0
  99. package/src/manager/router.ts +105 -23
  100. package/src/registry/mod.ts +145 -119
  101. package/src/registry/run-config.ts +116 -47
  102. package/src/registry/serve.ts +3 -1
  103. package/src/serde.ts +3 -3
  104. package/src/test/config.ts +2 -2
  105. package/src/test/mod.ts +6 -3
  106. package/src/utils.ts +2 -0
  107. package/dist/tsup/chunk-4PSLOAXR.cjs.map +0 -1
  108. package/dist/tsup/chunk-4YV6RDZL.cjs.map +0 -1
  109. package/dist/tsup/chunk-7OMMIAWP.cjs.map +0 -1
  110. package/dist/tsup/chunk-E63WU5PL.js.map +0 -1
  111. package/dist/tsup/chunk-FZP2IBIX.js.map +0 -1
  112. package/dist/tsup/chunk-KHZ2QSQ4.js.map +0 -1
  113. package/dist/tsup/chunk-QGRYH6TU.cjs.map +0 -1
  114. package/dist/tsup/chunk-R7OP5N25.js.map +0 -1
  115. package/dist/tsup/chunk-SDXTJDDR.cjs.map +0 -1
  116. package/dist/tsup/chunk-SOC4HWCG.cjs.map +0 -1
  117. package/dist/tsup/chunk-U2IXX6DY.cjs.map +0 -1
  118. package/dist/tsup/chunk-WRSWUDFA.js.map +0 -1
  119. package/dist/tsup/chunk-YR2VY4XS.js.map +0 -1
  120. /package/dist/tsup/{chunk-APHV6WXU.js.map → chunk-346X2XU4.js.map} +0 -0
  121. /package/dist/tsup/{chunk-DLPIL3VC.js.map → chunk-7E5K3375.js.map} +0 -0
  122. /package/dist/tsup/{chunk-WBSPHV5V.js.map → chunk-KGDZYQYE.js.map} +0 -0
  123. /package/dist/tsup/{chunk-F2YZNUPU.js.map → chunk-N3A5GYJU.js.map} +0 -0
@@ -11,9 +11,9 @@ import { createMiddleware } from "hono/factory";
11
11
  import { streamSSE } from "hono/streaming";
12
12
  import invariant from "invariant";
13
13
  import { z } from "zod";
14
- import { ActorNotFound, Unsupported } from "@/actor/errors";
14
+ import { ActorNotFound, InvalidRequest, Unsupported } from "@/actor/errors";
15
15
  import { serializeActorKey } from "@/actor/keys";
16
- import type { Encoding, Transport } from "@/client/mod";
16
+ import type { Client, Encoding, Transport } from "@/client/mod";
17
17
  import {
18
18
  WS_PROTOCOL_ACTOR,
19
19
  WS_PROTOCOL_CONN_ID,
@@ -28,7 +28,12 @@ import {
28
28
  handleRouteNotFound,
29
29
  loggerMiddleware,
30
30
  } from "@/common/router";
31
- import { deconstructError, noopNext, stringifyError } from "@/common/utils";
31
+ import {
32
+ assertUnreachable,
33
+ deconstructError,
34
+ noopNext,
35
+ stringifyError,
36
+ } from "@/common/utils";
32
37
  import { type ActorDriver, HEADER_ACTOR_ID } from "@/driver-helpers/mod";
33
38
  import type {
34
39
  TestInlineDriverCallRequest,
@@ -50,11 +55,14 @@ import {
50
55
  type Actor as ApiActor,
51
56
  } from "@/manager-api/actors";
52
57
  import { RivetIdSchema } from "@/manager-api/common";
58
+ import type { AnyClient } from "@/mod";
53
59
  import type { RegistryConfig } from "@/registry/config";
54
- import type { RunConfig } from "@/registry/run-config";
60
+ import type { DriverConfig, RunnerConfig } from "@/registry/run-config";
61
+ import { VERSION } from "@/utils";
55
62
  import type { ActorOutput, ManagerDriver } from "./driver";
56
63
  import { actorGateway, createTestWebSocketProxy } from "./gateway";
57
64
  import { logger } from "./log";
65
+ import { ServerlessStartHeadersSchema } from "./router-schema";
58
66
 
59
67
  function buildOpenApiResponses<T>(schema: T) {
60
68
  return {
@@ -77,9 +85,10 @@ function buildOpenApiResponses<T>(schema: T) {
77
85
 
78
86
  export function createManagerRouter(
79
87
  registryConfig: RegistryConfig,
80
- runConfig: RunConfig,
88
+ runConfig: RunnerConfig,
81
89
  managerDriver: ManagerDriver,
82
- serverlessActorDriverBuilder: (() => ActorDriver) | undefined,
90
+ driverConfig: DriverConfig,
91
+ client: AnyClient,
83
92
  ): { router: Hono; openapi: OpenAPIHono } {
84
93
  const router = new OpenAPIHono({ strict: false }).basePath(
85
94
  runConfig.basePath,
@@ -87,10 +96,38 @@ export function createManagerRouter(
87
96
 
88
97
  router.use("*", loggerMiddleware(logger()));
89
98
 
90
- if (serverlessActorDriverBuilder) {
91
- addServerlessRoutes(runConfig, serverlessActorDriverBuilder, router);
92
- } else {
99
+ // HACK: Add Sec-WebSocket-Protocol header to fix KIT-339
100
+ //
101
+ // Some Deno WebSocket providers do not auto-set the protocol, which
102
+ // will cause some WebSocket clients to fail
103
+ router.use(
104
+ "*",
105
+ createMiddleware(async (c, next) => {
106
+ const upgrade = c.req.header("upgrade");
107
+ const isWebSocket = upgrade?.toLowerCase() === "websocket";
108
+ const isGet = c.req.method === "GET";
109
+
110
+ if (isGet && isWebSocket) {
111
+ c.header("Sec-WebSocket-Protocol", "rivet");
112
+ }
113
+
114
+ await next();
115
+ }),
116
+ );
117
+
118
+ if (runConfig.runnerKind === "serverless") {
119
+ addServerlessRoutes(
120
+ driverConfig,
121
+ registryConfig,
122
+ runConfig,
123
+ managerDriver,
124
+ client,
125
+ router,
126
+ );
127
+ } else if (runConfig.runnerKind === "normal") {
93
128
  addManagerRoutes(registryConfig, runConfig, managerDriver, router);
129
+ } else {
130
+ assertUnreachable(runConfig.runnerKind);
94
131
  }
95
132
 
96
133
  // Error handling
@@ -101,11 +138,11 @@ export function createManagerRouter(
101
138
  }
102
139
 
103
140
  function addServerlessRoutes(
104
- runConfig: RunConfig,
105
- serverlessActorDriverBuilder: (
106
- token: string | undefined,
107
- totalSlots: number | undefined,
108
- ) => ActorDriver,
141
+ driverConfig: DriverConfig,
142
+ registryConfig: RegistryConfig,
143
+ runConfig: RunnerConfig,
144
+ managerDriver: ManagerDriver,
145
+ client: AnyClient,
109
146
  router: OpenAPIHono,
110
147
  ) {
111
148
  // Apply CORS
@@ -120,28 +157,68 @@ function addServerlessRoutes(
120
157
 
121
158
  // Serverless start endpoint
122
159
  router.get("/start", async (c) => {
123
- const token = c.req.header("x-rivet-token");
124
- let totalSlots: number | undefined = parseInt(
125
- c.req.header("x-rivetkit-total-slots") as any,
126
- );
127
- if (isNaN(totalSlots)) totalSlots = undefined;
160
+ // Parse headers
161
+ const parseResult = ServerlessStartHeadersSchema.safeParse({
162
+ endpoint: c.req.header("x-rivet-endpoint"),
163
+ token: c.req.header("x-rivet-token") ?? undefined,
164
+ totalSlots: c.req.header("x-rivet-total-slots"),
165
+ runnerName: c.req.header("x-rivet-runner-name"),
166
+ namespace: c.req.header("x-rivet-namespace-id"),
167
+ });
168
+ if (!parseResult.success) {
169
+ throw new InvalidRequest(
170
+ parseResult.error.issues[0]?.message ??
171
+ "invalid serverless start headers",
172
+ );
173
+ }
174
+ const { endpoint, token, totalSlots, runnerName, namespace } =
175
+ parseResult.data;
176
+
177
+ logger().debug({
178
+ msg: "received serverless runner start request",
179
+ endpoint,
180
+ totalSlots,
181
+ runnerName,
182
+ namespace,
183
+ });
128
184
 
129
- const actorDriver = serverlessActorDriverBuilder(token, totalSlots);
185
+ // Override config
186
+ //
187
+ // We can't do a structuredClone here since this holds functions
188
+ const newRunConfig = Object.assign({}, runConfig);
189
+ newRunConfig.endpoint = endpoint;
190
+ newRunConfig.token = token;
191
+ newRunConfig.totalSlots = totalSlots;
192
+ newRunConfig.runnerName = runnerName;
193
+ newRunConfig.namespace = namespace;
194
+
195
+ // Create new actor driver with updated config
196
+ const actorDriver = driverConfig.actor(
197
+ registryConfig,
198
+ newRunConfig,
199
+ managerDriver,
200
+ client,
201
+ );
130
202
  invariant(
131
203
  actorDriver.serverlessHandleStart,
132
204
  "missing serverlessHandleStart on ActorDriver",
133
205
  );
206
+
134
207
  return await actorDriver.serverlessHandleStart(c);
135
208
  });
136
209
 
137
210
  router.get("/health", (c) => {
138
- return c.text("ok");
211
+ return c.json({
212
+ status: "ok",
213
+ runtime: "rivetkit",
214
+ version: VERSION,
215
+ });
139
216
  });
140
217
  }
141
218
 
142
219
  function addManagerRoutes(
143
220
  registryConfig: RegistryConfig,
144
- runConfig: RunConfig,
221
+ runConfig: RunnerConfig,
145
222
  managerDriver: ManagerDriver,
146
223
  router: OpenAPIHono,
147
224
  ) {
@@ -564,7 +641,12 @@ function addManagerRoutes(
564
641
  }
565
642
 
566
643
  router.get("/health", (c) => {
567
- return c.text("ok");
644
+ return c.json({
645
+ status: "ok",
646
+ rivetkit: {
647
+ version: VERSION,
648
+ },
649
+ });
568
650
  });
569
651
 
570
652
  managerDriver.modifyManagerRouter?.(
@@ -1,7 +1,9 @@
1
+ import invariant from "invariant";
1
2
  import { type Client, createClientWithDriver } from "@/client/client";
2
3
  import { configureBaseLogger, configureDefaultLogger } from "@/common/log";
3
4
  import type { ActorDriver } from "@/driver-helpers/mod";
4
5
  import { chooseDefaultDriver } from "@/drivers/default";
6
+ import { ENGINE_ENDPOINT, ensureEngineProcess } from "@/engine-process/mod";
5
7
  import {
6
8
  configureInspectorAccessToken,
7
9
  getInspectorUrl,
@@ -18,12 +20,16 @@ import {
18
20
  import { logger } from "./log";
19
21
  import {
20
22
  type DriverConfig,
21
- type RunConfig,
22
- type RunConfigInput,
23
- RunConfigSchema,
23
+ type RunnerConfig,
24
+ type RunnerConfigInput,
25
+ RunnerConfigSchema,
24
26
  } from "./run-config";
25
27
  import { crossPlatformServe } from "./serve";
26
28
 
29
+ export type ServerlessActorDriverBuilder = (
30
+ updateConfig: (config: RunnerConfig) => void,
31
+ ) => ActorDriver;
32
+
27
33
  interface ServerOutput<A extends Registry<any>> {
28
34
  /** Client to communicate with the actors. */
29
35
  client: Client<A>;
@@ -45,8 +51,48 @@ export class Registry<A extends RegistryActors> {
45
51
  /**
46
52
  * Runs the registry for a server.
47
53
  */
48
- public start(inputConfig?: RunConfigInput): ServerOutput<this> {
49
- const config = RunConfigSchema.parse(inputConfig);
54
+ public start(inputConfig?: RunnerConfigInput): ServerOutput<this> {
55
+ const config = RunnerConfigSchema.parse(inputConfig);
56
+
57
+ // Validate autoConfigureServerless is only used with serverless runner
58
+ if (config.autoConfigureServerless && config.runnerKind !== "serverless") {
59
+ throw new Error(
60
+ "autoConfigureServerless can only be configured when runnerKind is 'serverless'",
61
+ );
62
+ }
63
+
64
+ // Promise for any async operations we need to wait to complete
65
+ const readyPromises = [];
66
+
67
+ // Start engine
68
+ if (config.runEngine) {
69
+ logger().debug({
70
+ msg: "run engine requested",
71
+ version: config.runEngineVersion,
72
+ });
73
+
74
+ // Set config to point to the engine
75
+ invariant(
76
+ config.endpoint === undefined,
77
+ "cannot specify 'endpoint' with 'runEngine'",
78
+ );
79
+ config.endpoint = ENGINE_ENDPOINT;
80
+ config.disableActorDriver = true;
81
+
82
+ // Start the engine
83
+ const engineProcessPromise = ensureEngineProcess({
84
+ version: config.runEngineVersion,
85
+ });
86
+
87
+ // Chain ready promise
88
+ readyPromises.push(engineProcessPromise);
89
+ }
90
+
91
+ // Configure for serverless
92
+ if (config.runnerKind === "serverless") {
93
+ config.defaultServerPort = 8080;
94
+ config.overrideServerAddress = config.endpoint;
95
+ }
50
96
 
51
97
  // Configure logger
52
98
  if (config.logging?.baseLogger) {
@@ -61,14 +107,18 @@ export class Registry<A extends RegistryActors> {
61
107
  // Choose the driver based on configuration
62
108
  const driver = chooseDefaultDriver(config);
63
109
 
64
- // TODO: Find cleaner way of disabling by default
110
+ // Set defaults based on the driver
65
111
  if (driver.name === "engine") {
66
112
  config.inspector.enabled = { manager: false, actor: true };
67
- config.disableServer = true;
113
+
114
+ // We need to leave the default server enabled for dev
115
+ if (config.runnerKind !== "serverless") {
116
+ config.disableDefaultServer = true;
117
+ }
68
118
  }
69
119
  if (driver.name === "cloudflare-workers") {
70
120
  config.inspector.enabled = { manager: false, actor: true };
71
- config.disableServer = true;
121
+ config.disableDefaultServer = true;
72
122
  config.disableActorDriver = true;
73
123
  config.noWelcome = true;
74
124
  }
@@ -102,7 +152,15 @@ export class Registry<A extends RegistryActors> {
102
152
  const displayInfo = managerDriver.displayInformation();
103
153
  console.log();
104
154
  console.log(` RivetKit ${pkg.version} (${displayInfo.name})`);
105
- console.log(` - Endpoint: http://127.0.0.1:6420`);
155
+ if (!config.disableDefaultServer) {
156
+ console.log(` - Endpoint: ${config.endpoint}`);
157
+ } else if (config.overrideServerAddress) {
158
+ console.log(` - Endpoint: ${config.overrideServerAddress}`);
159
+ }
160
+ if (config.runEngine) {
161
+ const padding = " ".repeat(Math.max(0, 13 - "Engine".length));
162
+ console.log(` - Engine:${padding}v${config.runEngineVersion}`);
163
+ }
106
164
  for (const [k, v] of Object.entries(displayInfo.properties)) {
107
165
  const padding = " ".repeat(Math.max(0, 13 - k.length));
108
166
  console.log(` - ${k}:${padding}${v}`);
@@ -116,27 +174,32 @@ export class Registry<A extends RegistryActors> {
116
174
  // HACK: We need to find a better way to let the driver itself decide when to start the actor driver
117
175
  // Create runner
118
176
  //
119
- // Even though we do not use the return value, this is required to start the code that will handle incoming actors
177
+ // Even though we do not use the returned ActorDriver, this is required to start the code that will handle incoming actors
120
178
  if (!config.disableActorDriver) {
121
- const _actorDriver = driver.actor(
122
- this.#config,
123
- config,
124
- managerDriver,
125
- client,
126
- );
179
+ Promise.all(readyPromises).then(async () => {
180
+ driver.actor(this.#config, config, managerDriver, client);
181
+ });
182
+ }
183
+
184
+ // Configure serverless runner if enabled when actor driver is disabled
185
+ if (config.runnerKind === "serverless" && config.autoConfigureServerless) {
186
+ Promise.all(readyPromises).then(async () => {
187
+ await configureServerlessRunner(config);
188
+ });
127
189
  }
128
190
 
129
191
  const { router: hono } = createManagerRouter(
130
192
  this.#config,
131
193
  config,
132
194
  managerDriver,
133
- undefined,
195
+ driver,
196
+ client,
134
197
  );
135
198
 
136
199
  // Start server
137
- if (!config.disableServer) {
200
+ if (!config.disableDefaultServer) {
138
201
  (async () => {
139
- const out = await crossPlatformServe(hono, undefined);
202
+ const out = await crossPlatformServe(config, hono, undefined);
140
203
  upgradeWebSocket = out.upgradeWebSocket;
141
204
  })();
142
205
  }
@@ -146,116 +209,79 @@ export class Registry<A extends RegistryActors> {
146
209
  fetch: hono.fetch.bind(hono),
147
210
  };
148
211
  }
212
+ }
149
213
 
150
- public startServerless(inputConfig?: RunConfigInput): ServerOutput<this> {
151
- const config = RunConfigSchema.parse(inputConfig);
152
-
153
- // Configure logger
154
- if (config.logging?.baseLogger) {
155
- // Use provided base logger
156
- configureBaseLogger(config.logging.baseLogger);
157
- } else {
158
- // Configure default logger with log level from config
159
- // getPinoLevel will handle env variable priority
160
- configureDefaultLogger(config.logging?.level);
161
- }
162
-
163
- // Choose the driver based on configuration
164
- const driver = chooseDefaultDriver(config);
165
-
166
- // TODO: Find cleaner way of disabling by default
167
- if (driver.name === "engine") {
168
- config.inspector.enabled = false;
169
- config.disableServer = true;
170
- config.disableActorDriver = true;
214
+ async function configureServerlessRunner(config: RunnerConfig): Promise<void> {
215
+ try {
216
+ // Ensure we have required config values
217
+ if (!config.runnerName) {
218
+ throw new Error("runnerName is required for serverless configuration");
171
219
  }
172
- if (driver.name === "cloudflare-workers") {
173
- config.inspector.enabled = false;
174
- config.disableServer = true;
175
- config.disableActorDriver = true;
176
- config.noWelcome = true;
220
+ if (!config.namespace) {
221
+ throw new Error("namespace is required for serverless configuration");
177
222
  }
178
-
179
- // Configure getUpgradeWebSocket lazily so we can assign it in crossPlatformServe
180
- let upgradeWebSocket: any;
181
- if (!config.getUpgradeWebSocket) {
182
- config.getUpgradeWebSocket = () => upgradeWebSocket!;
223
+ if (!config.endpoint) {
224
+ throw new Error("endpoint is required for serverless configuration");
183
225
  }
184
226
 
185
- // Create router
186
- const managerDriver = driver.manager(this.#config, config);
227
+ // Prepare the configuration
228
+ const customConfig =
229
+ typeof config.autoConfigureServerless === "object"
230
+ ? config.autoConfigureServerless
231
+ : {};
232
+
233
+ // Build the request body
234
+ const requestBody = {
235
+ serverless: {
236
+ url:
237
+ customConfig.url ||
238
+ `http://localhost:${config.defaultServerPort}/start`,
239
+ headers: customConfig.headers || {},
240
+ max_runners: customConfig.maxRunners ?? 100,
241
+ min_runners: customConfig.minRunners ?? 0,
242
+ request_lifespan: customConfig.requestLifespan ?? 15 * 60,
243
+ runners_margin: customConfig.runnersMargin ?? 0,
244
+ slots_per_runner:
245
+ customConfig.slotsPerRunner ?? config.totalSlots ?? 1000,
246
+ },
247
+ };
187
248
 
188
- // Create client
189
- const client = createClientWithDriver<this>(managerDriver, config);
249
+ // Make the request to configure the serverless runner
250
+ const configUrl = `${config.endpoint}/runner-configs/${config.runnerName}?namespace=${config.namespace}`;
190
251
 
191
- const driverLog = managerDriver.extraStartupLog?.() ?? {};
192
- logger().info({
193
- msg: "rivetkit ready",
194
- driver: driver.name,
195
- definitions: Object.keys(this.#config.use).length,
196
- ...driverLog,
252
+ logger().debug({
253
+ msg: "configuring serverless runner",
254
+ url: configUrl,
255
+ config: requestBody.serverless,
197
256
  });
198
- if (config.inspector?.enabled && managerDriver.inspector) {
199
- logger().info({ msg: "inspector ready", url: getInspectorUrl(config) });
200
- }
201
-
202
- // Print welcome information
203
- if (!config.noWelcome) {
204
- const displayInfo = managerDriver.displayInformation();
205
- console.log();
206
- console.log(` RivetKit ${pkg.version} (${displayInfo.name})`);
207
- console.log(` - Endpoint: http://127.0.0.1:6420`);
208
- for (const [k, v] of Object.entries(displayInfo.properties)) {
209
- const padding = " ".repeat(Math.max(0, 13 - k.length));
210
- console.log(` - ${k}:${padding}${v}`);
211
- }
212
- if (config.inspector?.enabled && managerDriver.inspector) {
213
- console.log(` - Inspector: ${getInspectorUrl(config)}`);
214
- }
215
- console.log();
216
- }
217
-
218
- let serverlessActorDriverBuilder:
219
- | ((token?: string, totalSlots?: number) => ActorDriver)
220
- | undefined = (
221
- token: string | undefined,
222
- totalSlots: number | undefined,
223
- ) => {
224
- // Override config
225
- if (token) config.token = token;
226
- if (totalSlots) config.totalSlots = totalSlots;
227
-
228
- return driver.actor(this.#config, config, managerDriver, client);
229
- };
230
-
231
- // HACK: We need to find a better way to let the driver itself decide when to start the actor driver
232
- // Create runner
233
- //
234
- // Even though we do not use the return value, this is required to start the code that will handle incoming actors
235
- if (!config.disableActorDriver) {
236
- const _actorDriver = serverlessActorDriverBuilder();
237
- serverlessActorDriverBuilder = undefined;
238
- }
239
257
 
240
- const { router: hono } = createManagerRouter(
241
- this.#config,
242
- config,
243
- managerDriver,
244
- serverlessActorDriverBuilder,
245
- );
258
+ const response = await fetch(configUrl, {
259
+ method: "PUT",
260
+ headers: {
261
+ "Content-Type": "application/json",
262
+ ...(config.token ? { Authorization: `Bearer ${config.token}` } : {}),
263
+ },
264
+ body: JSON.stringify(requestBody),
265
+ });
246
266
 
247
- // Start server
248
- if (!config.disableServer) {
249
- (async () => {
250
- const out = await crossPlatformServe(hono, undefined);
251
- upgradeWebSocket = out.upgradeWebSocket;
252
- })();
267
+ if (!response.ok) {
268
+ const errorText = await response.text();
269
+ throw new Error(
270
+ `failed to configure serverless runner: ${response.status} ${response.statusText} - ${errorText}`,
271
+ );
253
272
  }
254
273
 
255
- return {
256
- client,
257
- fetch: hono.fetch.bind(hono),
258
- };
274
+ logger().info({
275
+ msg: "serverless runner configured successfully",
276
+ runnerName: config.runnerName,
277
+ namespace: config.namespace,
278
+ });
279
+ } catch (error) {
280
+ logger().error({
281
+ msg: "failed to configure serverless runner",
282
+ error,
283
+ });
284
+ throw error;
259
285
  }
260
286
  }
261
287
 
@@ -269,8 +295,8 @@ export function setup<A extends RegistryActors>(
269
295
  export type {
270
296
  RegistryConfig,
271
297
  RegistryActors,
272
- RunConfig,
273
- RunConfigInput,
298
+ RunnerConfig as RunConfig,
299
+ RunnerConfigInput as RunConfigInput,
274
300
  DriverConfig,
275
301
  };
276
302
  export { RegistryConfigSchema };