Skip to content
118 linesCodeBlameRaw

Pick any line to see why it is the way it is: the commit, the pull request and issue it came from, and what the agent was thinking.

Billing and Usage reconcile: own-provider runs leave Billing's at-price total, and Usage's not-charged part is at price less charged1/**
Guardrails no longer restrict the network: every sandbox on g1t's machines reaches the internet, as a GitHub-hosted runner does, and the settings for it are gone at every level, the workspace's defaults and each project's overrides: Only allowed hosts (restrict_network), the package registries, allowed domains and workflow-only domains. Guardrails are now the time caps on checks, the merge queue and merge checks, and nothing else.2 * Guardrails, as the runner applies them to a sandbox: how long a run may
3 * take, and the outbound handlers its requests may pass.
Billing and Usage reconcile: own-provider runs leave Billing's at-price total, and Usage's not-charged part is at price less charged4 *
5 * - The time cap is enforced twice: by the harness, and by the sandbox's
6 * own alarm here, which stops the whole sandbox a little after.
Guardrails no longer restrict the network: every sandbox on g1t's machines reaches the internet, as a GitHub-hosted runner does, and the settings for it are gone at every level, the workspace's defaults and each project's overrides: Only allowed hosts (restrict_network), the package registries, allowed domains and workflow-only domains. Guardrails are now the time caps on checks, the merge queue and merge checks, and nothing else.7 * - Every sandbox reaches the internet directly. A workflow job that may
8 * be given brokered secrets sends its HTTP and HTTPS through `egress`
9 * below, which fills them in and sends everything on, to any host.
10 * - A sandbox's report that it stopped itself for mining comes to `abuse`.
Billing and Usage reconcile: own-provider runs leave Billing's at-price total, and Usage's not-charged part is at price less charged11 */
12import type { OutboundHandlerContext } from "@cloudflare/containers";
13
14import { type RepoPath, type RunKind, type ServiceBinding, guardrailsClient } from "@g1t/contracts";
15
Guardrails no longer restrict the network: every sandbox on g1t's machines reaches the internet, as a GitHub-hosted runner does, and the settings for it are gone at every level, the workspace's defaults and each project's overrides: Only allowed hosts (restrict_network), the package registries, allowed domains and workflow-only domains. Guardrails are now the time caps on checks, the merge queue and merge checks, and nothing else.16import { ABUSE_HOST, type RunGuard, sandboxNamespace } from "./egress";
Merge brokered secrets: a secret a job uses only to call an API can be tied to the hosts it is for, and the job gets a stand-in in its place, which g1t fills in on the way out to those hosts and nowhere else, so the value never enters the sandbox; and a request to an allowed host that fails upstream is retried when it can be, or answered with a 502 that says why, rather than reset.17import { type BrokeredParams, brokered } from "./broker-egress.ts";
18import { forward } from "./forward.ts";
Billing and Usage reconcile: own-provider runs leave Billing's at-price total, and Usage's not-charged part is at price less charged19
20export {
21 ABUSE_EXIT_CODE,
22 ABUSE_HOST,
23 ABUSE_MESSAGE,
24 SANDBOX_BINDINGS,
Merge branch 'main' into actions-toolkit-oidc-artifacts25 dockerFor,
Billing and Usage reconcile: own-provider runs leave Billing's at-price total, and Usage's not-charged part is at price less charged26 harnessEnv,
27 sandboxNamespace,
Guardrails no longer restrict the network: every sandbox on g1t's machines reaches the internet, as a GitHub-hosted runner does, and the settings for it are gone at every level, the workspace's defaults and each project's overrides: Only allowed hosts (restrict_network), the package registries, allowed domains and workflow-only domains. Guardrails are now the time caps on checks, the merge queue and merge checks, and nothing else.28 throughWorker,
Billing and Usage reconcile: own-provider runs leave Billing's at-price total, and Usage's not-charged part is at price less charged29 timeCapMessage,
30 withPlanLimits,
31} from "./egress";
Guardrails no longer restrict the network: every sandbox on g1t's machines reaches the internet, as a GitHub-hosted runner does, and the settings for it are gone at every level, the workspace's defaults and each project's overrides: Only allowed hosts (restrict_network), the package registries, allowed domains and workflow-only domains. Guardrails are now the time caps on checks, the merge queue and merge checks, and nothing else.32export type { PlanLimits, RunGuard } from "./egress";
Billing and Usage reconcile: own-provider runs leave Billing's at-price total, and Usage's not-charged part is at price less charged33
Guardrails no longer restrict the network: every sandbox on g1t's machines reaches the internet, as a GitHub-hosted runner does, and the settings for it are gone at every level, the workspace's defaults and each project's overrides: Only allowed hosts (restrict_network), the package registries, allowed domains and workflow-only domains. Guardrails are now the time caps on checks, the merge queue and merge checks, and nothing else.34/** What the outbound handler is given: what brokered secrets need (broker-egress.ts). */
35export type EgressParams = BrokeredParams;
Billing and Usage reconcile: own-provider runs leave Billing's at-price total, and Usage's not-charged part is at price less charged36
37/** The stop by the sandbox's alarm comes this long after the harness's own. */
38export const ALARM_GRACE_SECONDS = 3 * 60;
39
40/**
41 * The guardrails of a run in `repo`. Throws when they cannot be read: a
42 * sandbox is not started without them.
43 */
44export async function guardFor(work: ServiceBinding, repo: RepoPath, kind: RunKind): Promise<RunGuard> {
45 const found = await guardrailsClient(work).runGuardrails(repo);
46 if (!found.ok) throw new Error(`g1t could not read this project's guardrails: ${found.error.message}`);
47 const policy = found.value;
48 return { policy, minutes: policy.minutes[kind] ?? 60 };
49}
50
51/**
Guardrails no longer restrict the network: every sandbox on g1t's machines reaches the internet, as a GitHub-hosted runner does, and the settings for it are gone at every level, the workspace's defaults and each project's overrides: Only allowed hosts (restrict_network), the package registries, allowed domains and workflow-only domains. Guardrails are now the time caps on checks, the merge queue and merge checks, and nothing else.52 * The guardrails of a workflow job, deploy build or update: the time cap it
53 * was given, which is all a build's guardrails are.
Billing and Usage reconcile: own-provider runs leave Billing's at-price total, and Usage's not-charged part is at price less charged54 */
Guardrails no longer restrict the network: every sandbox on g1t's machines reaches the internet, as a GitHub-hosted runner does, and the settings for it are gone at every level, the workspace's defaults and each project's overrides: Only allowed hosts (restrict_network), the package registries, allowed domains and workflow-only domains. Guardrails are now the time caps on checks, the merge queue and merge checks, and nothing else.55export function buildGuard(minutes: number): RunGuard {
56 return { policy: { minutes: {} }, minutes };
Billing and Usage reconcile: own-provider runs leave Billing's at-price total, and Usage's not-charged part is at price less charged57}
58
59/**
Guardrails no longer restrict the network: every sandbox on g1t's machines reaches the internet, as a GitHub-hosted runner does, and the settings for it are gone at every level, the workspace's defaults and each project's overrides: Only allowed hosts (restrict_network), the package registries, allowed domains and workflow-only domains. Guardrails are now the time caps on checks, the merge queue and merge checks, and nothing else.60 * The outbound handler of a sandbox whose HTTP and HTTPS pass the Worker
61 * (a workflow job that may be given brokered secrets): every request it
62 * makes, to any host. Its brokered secrets are filled in first, if it has
63 * any, and the request is sent on with `forward`'s retries.
Billing and Usage reconcile: own-provider runs leave Billing's at-price total, and Usage's not-charged part is at price less charged64 */
65export async function egress(
66 request: Request,
Merge brokered secrets: a secret a job uses only to call an API can be tied to the hosts it is for, and the job gets a stand-in in its place, which g1t fills in on the way out to those hosts and nowhere else, so the value never enters the sandbox; and a request to an allowed host that fails upstream is retried when it can be, or answered with a 502 that says why, rather than reset.67 env: { SANDBOX: DurableObjectNamespace; ACTIONS?: ServiceBinding },
Billing and Usage reconcile: own-provider runs leave Billing's at-price total, and Usage's not-charged part is at price less charged68 ctx: OutboundHandlerContext<EgressParams>,
69): Promise<Response> {
70 const host = new URL(request.url).host;
71 // A sandbox reporting that it stopped itself for mining.
72 if (host === ABUSE_HOST) return abuse(request, env, ctx);
Guardrails no longer restrict the network: every sandbox on g1t's machines reaches the internet, as a GitHub-hosted runner does, and the settings for it are gone at every level, the workspace's defaults and each project's overrides: Only allowed hosts (restrict_network), the package registries, allowed domains and workflow-only domains. Guardrails are now the time caps on checks, the merge queue and merge checks, and nothing else.73 return (await brokered(request, env, ctx)) ?? forward(request);
Billing and Usage reconcile: own-provider runs leave Billing's at-price total, and Usage's not-charged part is at price less charged74}
75
76/**
77 * A sandbox's report that it stopped itself for mining (crates/runner
Guardrails no longer restrict the network: every sandbox on g1t's machines reaches the internet, as a GitHub-hosted runner does, and the settings for it are gone at every level, the workspace's defaults and each project's overrides: Only allowed hosts (restrict_network), the package registries, allowed domains and workflow-only domains. Guardrails are now the time caps on checks, the merge queue and merge checks, and nothing else.78 * abuse.rs), handed to its Durable Object. The handler for `ABUSE_HOST`
79 * on every sandbox, and reached through `egress` for one whose requests
80 * pass the Worker.
Billing and Usage reconcile: own-provider runs leave Billing's at-price total, and Usage's not-charged part is at price less charged81 */
82export async function abuse(
83 request: Request,
84 env: { SANDBOX: DurableObjectNamespace },
85 ctx: OutboundHandlerContext<unknown>,
86): Promise<Response> {
87 let verdict: unknown = null;
88 try {
89 verdict = ((await request.json()) as { verdict?: unknown }).verdict ?? null;
90 } catch {
91 // A report without its metrics still stops the run.
92 }
93 try {
94 const namespace = sandboxNamespace(env, ctx.className);
95 const sandbox = namespace.get(namespace.idFromString(ctx.containerId)) as unknown as {
96 flagAbuse(verdict: unknown): Promise<void>;
97 };
98 await sandbox.flagAbuse(verdict);
99 } catch (error) {
100 console.log("abuse report not handled", String(error));
101 }
102 return new Response("noted\n");
103}
104
105/** Adds a step to a run, with its token. Never fails the caller. */
106export async function reportRun(
107 work: ServiceBinding,
108 tracked: { runId: string; token: string },
109 report: { steps?: string[]; halt?: "budget" | "time" | "abuse"; error?: string },
110): Promise<void> {
111 await work
112 .fetch("https://service/rpc/report_run", {
113 method: "POST",
114 headers: { "content-type": "application/json" },
115 body: JSON.stringify({ runId: tracked.runId, token: tracked.token, ...report }),
116 })
117 .catch((error: unknown) => console.log("run report failed", tracked.runId, String(error)));
118}

This file's history is long; its oldest lines are credited to the oldest commit read.