Skip to content

Commit 10ce69d

Browse files
committed
fix(sdk): guard envvars.update() outside task context (#4264)
1 parent 8b72e6c commit 10ce69d

3 files changed

Lines changed: 102 additions & 1 deletion

File tree

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,5 @@
1+
---
2+
"@trigger.dev/sdk": patch
3+
---
4+
5+
`envvars.update()`: calling it outside a task run no longer throws `ReferenceError: name is not defined`. The variable name is now resolved from the positional arguments, matching the other env var methods, and a missing name raises a descriptive `name is required` error instead.
Lines changed: 92 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,92 @@
1+
import { taskContext } from "@trigger.dev/core/v3";
2+
import { createServer, type Server } from "node:http";
3+
import type { AddressInfo } from "node:net";
4+
import { afterEach, beforeEach, describe, expect, it } from "vitest";
5+
import { update } from "./envvars.js";
6+
7+
describe("envvars.update outside a task context", () => {
8+
let server: Server | undefined;
9+
let requests: { method?: string; url?: string; body: string }[];
10+
let previousApiUrl: string | undefined;
11+
let previousSecretKey: string | undefined;
12+
let previousAccessToken: string | undefined;
13+
14+
beforeEach(async () => {
15+
requests = [];
16+
previousApiUrl = process.env.TRIGGER_API_URL;
17+
previousSecretKey = process.env.TRIGGER_SECRET_KEY;
18+
previousAccessToken = process.env.TRIGGER_ACCESS_TOKEN;
19+
20+
delete process.env.TRIGGER_SECRET_KEY;
21+
22+
server = createServer((req, res) => {
23+
let body = "";
24+
req.on("data", (chunk) => {
25+
body += chunk;
26+
});
27+
req.on("end", () => {
28+
requests.push({ method: req.method, url: req.url, body });
29+
res.writeHead(200, { "content-type": "application/json" });
30+
res.end(JSON.stringify({ success: true }));
31+
});
32+
});
33+
34+
await new Promise<void>((resolve) => server!.listen(0, "127.0.0.1", resolve));
35+
36+
const { port } = server!.address() as AddressInfo;
37+
process.env.TRIGGER_API_URL = `http://127.0.0.1:${port}`;
38+
process.env.TRIGGER_ACCESS_TOKEN = "tr_test_token";
39+
});
40+
41+
afterEach(async () => {
42+
if (previousApiUrl === undefined) {
43+
delete process.env.TRIGGER_API_URL;
44+
} else {
45+
process.env.TRIGGER_API_URL = previousApiUrl;
46+
}
47+
48+
if (previousSecretKey === undefined) {
49+
delete process.env.TRIGGER_SECRET_KEY;
50+
} else {
51+
process.env.TRIGGER_SECRET_KEY = previousSecretKey;
52+
}
53+
54+
if (previousAccessToken === undefined) {
55+
delete process.env.TRIGGER_ACCESS_TOKEN;
56+
} else {
57+
process.env.TRIGGER_ACCESS_TOKEN = previousAccessToken;
58+
}
59+
60+
const running = server;
61+
server = undefined;
62+
63+
if (running) {
64+
await new Promise<void>((resolve, reject) =>
65+
running.close((error) => (error ? reject(error) : resolve()))
66+
);
67+
}
68+
});
69+
70+
it("sends a PUT for the named variable (regression #4264)", async () => {
71+
expect(taskContext.ctx).toBeUndefined();
72+
73+
await expect(update("proj_xxx", "staging", "MY_VAR", { value: "hello" })).resolves.toEqual({
74+
success: true,
75+
});
76+
77+
expect(requests).toHaveLength(1);
78+
expect(requests[0]?.method).toBe("PUT");
79+
expect(requests[0]?.url).toBe("/api/v1/projects/proj_xxx/envvars/staging/MY_VAR");
80+
expect(JSON.parse(requests[0]?.body ?? "")).toEqual({ value: "hello" });
81+
});
82+
83+
it("throws a descriptive error when name is missing", () => {
84+
expect(taskContext.ctx).toBeUndefined();
85+
86+
expect(() =>
87+
update("proj_xxx", "staging", undefined as unknown as string, { value: "hello" })
88+
).toThrow("name is required");
89+
90+
expect(requests).toHaveLength(0);
91+
});
92+
});

‎packages/trigger-sdk/src/v3/envvars.ts‎

Lines changed: 5 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -332,13 +332,17 @@ export function update(
332332
throw new Error("projectRef is required");
333333
}
334334

335+
if (typeof nameOrRequestOptions !== "string" || !nameOrRequestOptions) {
336+
throw new Error("name is required");
337+
}
338+
335339
if (!params) {
336340
throw new Error("params is required");
337341
}
338342

339343
$projectRef = projectRefOrName;
340344
$slug = slugOrParams;
341-
$name = name!;
345+
$name = nameOrRequestOptions;
342346
$params = params;
343347
}
344348

0 commit comments

Comments
 (0)