Monorepo for Tangled
tangled.org
1import { Container } from "@cloudflare/containers";
2
3export interface Env {
4 BOBBIN: DurableObjectNamespace<BobbinContainer>;
5 BOBBIN_HYDRANT_URL: string;
6 BOBBIN_SLINGSHOT_URL: string;
7 BOBBIN_LOG: string;
8}
9
10export class BobbinContainer extends Container {
11 defaultPort = 8090;
12 enableInternet = true;
13 // Bobbin maintains an in-memory index rebuilt from Hydrant replay on every
14 // restart, so we want to avoid sleeping where possible. Override
15 // onActivityExpired() to keep the container alive indefinitely.
16 sleepAfter = "24h";
17
18 onActivityExpired(): boolean {
19 // Keep the container running; bobbin's in-memory index is expensive to rebuild.
20 return true;
21 }
22
23 onError(error: Error) {
24 console.error("bobbin container error:", error);
25 }
26}
27
28const INDEX = `This is bobbin, Tangled's stateless XRPC API service: https://tangled.org/tangled.org/core/tree/master/bobbin`;
29
30export default {
31 async fetch(request: Request, env: Env): Promise<Response> {
32 const url = new URL(request.url);
33 if (url.pathname === "/" || url.pathname === "") {
34 return new Response(INDEX, { headers: { "Content-Type": "text/plain" } });
35 }
36 const container = env.BOBBIN.getByName("primary");
37 await container.startAndWaitForPorts({
38 startOptions: {
39 envVars: {
40 BOBBIN_HYDRANT_URL: env.BOBBIN_HYDRANT_URL,
41 BOBBIN_SLINGSHOT_URL: env.BOBBIN_SLINGSHOT_URL,
42 BOBBIN_LOG: env.BOBBIN_LOG,
43 BOBBIN_LOG_FORMAT: "json",
44 },
45 },
46 });
47 return container.fetch(request);
48 },
49} satisfies ExportedHandler<Env>;