trigger.dev 0.0.0-v3-canary-20240325170325 → 0.0.0-v3-pnpm-fix-20240403154252
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.
package/dist/index.js
CHANGED
|
@@ -781,11 +781,12 @@ import { intro as intro3, log as log2, outro as outro3, spinner as spinner4 } fr
|
|
|
781
781
|
import { depot } from "@depot/cli";
|
|
782
782
|
import { context, trace as trace2 } from "@opentelemetry/api";
|
|
783
783
|
import {
|
|
784
|
+
TaskMetadataFailedToParseData,
|
|
784
785
|
detectDependencyVersion,
|
|
785
786
|
flattenAttributes as flattenAttributes2,
|
|
786
787
|
recordSpanException as recordSpanException4
|
|
787
788
|
} from "@trigger.dev/core/v3";
|
|
788
|
-
import
|
|
789
|
+
import chalk5 from "chalk";
|
|
789
790
|
import { Option as CommandOption } from "commander";
|
|
790
791
|
import { build as build2 } from "esbuild";
|
|
791
792
|
import { execa as execa2 } from "execa";
|
|
@@ -793,14 +794,14 @@ import { resolve as importResolve } from "import-meta-resolve";
|
|
|
793
794
|
import { createHash } from "node:crypto";
|
|
794
795
|
import { readFileSync as readFileSync2 } from "node:fs";
|
|
795
796
|
import { copyFile, mkdir, readFile as readFile2, writeFile as writeFile2 } from "node:fs/promises";
|
|
796
|
-
import { dirname, join as join4, relative as
|
|
797
|
+
import { dirname, join as join4, relative as relative3 } from "node:path";
|
|
797
798
|
import { setTimeout as setTimeout2 } from "node:timers/promises";
|
|
798
799
|
import terminalLink from "terminal-link";
|
|
799
800
|
import invariant from "tiny-invariant";
|
|
800
801
|
import { z as z4 } from "zod";
|
|
801
802
|
|
|
802
803
|
// package.json
|
|
803
|
-
var version = "0.0.0-v3-
|
|
804
|
+
var version = "0.0.0-v3-pnpm-fix-20240403154252";
|
|
804
805
|
var dependencies = {
|
|
805
806
|
"@clack/prompts": "^0.7.0",
|
|
806
807
|
"@depot/cli": "0.0.1-cli.2.55.0",
|
|
@@ -816,7 +817,7 @@ var dependencies = {
|
|
|
816
817
|
"@opentelemetry/sdk-trace-base": "^1.22.0",
|
|
817
818
|
"@opentelemetry/sdk-trace-node": "^1.22.0",
|
|
818
819
|
"@opentelemetry/semantic-conventions": "^1.22.0",
|
|
819
|
-
"@trigger.dev/core": "workspace:0.0.0-v3-
|
|
820
|
+
"@trigger.dev/core": "workspace:0.0.0-v3-pnpm-fix-20240403154252",
|
|
820
821
|
"@types/degit": "^2.8.3",
|
|
821
822
|
chalk: "^5.2.0",
|
|
822
823
|
chokidar: "^3.5.3",
|
|
@@ -840,6 +841,7 @@ var dependencies = {
|
|
|
840
841
|
"node-fetch": "^3.3.0",
|
|
841
842
|
"npm-check-updates": "^16.12.2",
|
|
842
843
|
"object-hash": "^3.0.0",
|
|
844
|
+
"p-debounce": "^4.0.0",
|
|
843
845
|
"p-throttle": "^6.1.0",
|
|
844
846
|
partysocket: "^0.0.17",
|
|
845
847
|
"proxy-agent": "^6.3.0",
|
|
@@ -1306,7 +1308,7 @@ var Logger = class {
|
|
|
1306
1308
|
const kind = LOGGER_LEVEL_FORMAT_TYPE_MAP[level];
|
|
1307
1309
|
if (kind) {
|
|
1308
1310
|
const [firstLine, ...otherLines] = message.split("\n");
|
|
1309
|
-
const notes = otherLines.length > 0 ? otherLines.map((
|
|
1311
|
+
const notes = otherLines.length > 0 ? otherLines.map((text3) => ({ text: text3 })) : void 0;
|
|
1310
1312
|
return formatMessagesSync([{ text: firstLine, notes }], {
|
|
1311
1313
|
color: true,
|
|
1312
1314
|
kind,
|
|
@@ -1321,6 +1323,58 @@ var logger = new Logger();
|
|
|
1321
1323
|
|
|
1322
1324
|
// src/cli/common.ts
|
|
1323
1325
|
import { outro } from "@clack/prompts";
|
|
1326
|
+
|
|
1327
|
+
// src/utilities/cliOutput.ts
|
|
1328
|
+
import chalk2 from "chalk";
|
|
1329
|
+
var green = "#4FFF54";
|
|
1330
|
+
var purple = "#735BF3";
|
|
1331
|
+
function chalkGreen(text3) {
|
|
1332
|
+
return chalk2.hex(green)(text3);
|
|
1333
|
+
}
|
|
1334
|
+
function chalkPurple(text3) {
|
|
1335
|
+
return chalk2.hex(purple)(text3);
|
|
1336
|
+
}
|
|
1337
|
+
function chalkGrey(text3) {
|
|
1338
|
+
return chalk2.hex("#878C99")(text3);
|
|
1339
|
+
}
|
|
1340
|
+
function chalkError(text3) {
|
|
1341
|
+
return chalk2.hex("#E11D48")(text3);
|
|
1342
|
+
}
|
|
1343
|
+
function chalkWarning(text3) {
|
|
1344
|
+
return chalk2.yellow(text3);
|
|
1345
|
+
}
|
|
1346
|
+
function chalkSuccess(text3) {
|
|
1347
|
+
return chalk2.hex("#28BF5C")(text3);
|
|
1348
|
+
}
|
|
1349
|
+
function chalkLink(text3) {
|
|
1350
|
+
return chalk2.underline.hex("#D7D9DD")(text3);
|
|
1351
|
+
}
|
|
1352
|
+
function chalkWorker(text3) {
|
|
1353
|
+
return chalk2.hex("#FFFF89")(text3);
|
|
1354
|
+
}
|
|
1355
|
+
function chalkTask(text3) {
|
|
1356
|
+
return chalk2.hex("#60A5FA")(text3);
|
|
1357
|
+
}
|
|
1358
|
+
function chalkRun(text3) {
|
|
1359
|
+
return chalk2.hex("#A78BFA")(text3);
|
|
1360
|
+
}
|
|
1361
|
+
function logo() {
|
|
1362
|
+
return `${chalk2.hex(green).bold("Trigger")}${chalk2.hex(purple).bold(".dev")}`;
|
|
1363
|
+
}
|
|
1364
|
+
function prettyPrintDate(date = /* @__PURE__ */ new Date()) {
|
|
1365
|
+
let formattedDate = new Intl.DateTimeFormat("en-US", {
|
|
1366
|
+
month: "short",
|
|
1367
|
+
day: "2-digit",
|
|
1368
|
+
hour: "2-digit",
|
|
1369
|
+
minute: "2-digit",
|
|
1370
|
+
second: "2-digit",
|
|
1371
|
+
hour12: false
|
|
1372
|
+
}).format(date);
|
|
1373
|
+
formattedDate += "." + ("00" + date.getMilliseconds()).slice(-3);
|
|
1374
|
+
return formattedDate;
|
|
1375
|
+
}
|
|
1376
|
+
|
|
1377
|
+
// src/cli/common.ts
|
|
1324
1378
|
var CommonCommandOptions = z.object({
|
|
1325
1379
|
apiUrl: z.string().optional(),
|
|
1326
1380
|
logLevel: z.enum(["debug", "info", "log", "warn", "error", "none"]).default("log"),
|
|
@@ -1330,7 +1384,7 @@ var CommonCommandOptions = z.object({
|
|
|
1330
1384
|
function commonOptions(command) {
|
|
1331
1385
|
return command.option("--profile <profile>", "The login profile to use", "default").option("-a, --api-url <value>", "Override the API URL", "https://api.trigger.dev").option(
|
|
1332
1386
|
"-l, --log-level <level>",
|
|
1333
|
-
"The log level to use (debug, info, log, warn, error, none)",
|
|
1387
|
+
"The CLI log level to use (debug, info, log, warn, error, none). This does not effect the log level of your trigger.dev tasks.",
|
|
1334
1388
|
"log"
|
|
1335
1389
|
).option("--skip-telemetry", "Opt-out of sending telemetry");
|
|
1336
1390
|
}
|
|
@@ -1376,7 +1430,7 @@ async function wrapCommandAction(name, schema, options, action) {
|
|
|
1376
1430
|
} else if (e instanceof SkipCommandError) {
|
|
1377
1431
|
} else {
|
|
1378
1432
|
recordSpanException(span, e);
|
|
1379
|
-
logger.
|
|
1433
|
+
logger.log(`${chalkError("X Error:")} ${e instanceof Error ? e.message : String(e)}`);
|
|
1380
1434
|
}
|
|
1381
1435
|
span.end();
|
|
1382
1436
|
throw e;
|
|
@@ -1534,6 +1588,11 @@ function readAuthConfigProfile(profile = "default") {
|
|
|
1534
1588
|
return void 0;
|
|
1535
1589
|
}
|
|
1536
1590
|
}
|
|
1591
|
+
function deleteAuthConfigProfile(profile = "default") {
|
|
1592
|
+
const existingConfig = readAuthConfigFile() || {};
|
|
1593
|
+
delete existingConfig[profile];
|
|
1594
|
+
writeAuthConfigFile(existingConfig);
|
|
1595
|
+
}
|
|
1537
1596
|
function readAuthConfigFile() {
|
|
1538
1597
|
try {
|
|
1539
1598
|
const authConfigFilePath = getAuthConfigFilePath();
|
|
@@ -1638,23 +1697,6 @@ import chalk3 from "chalk";
|
|
|
1638
1697
|
import supportsColor from "supports-color";
|
|
1639
1698
|
import checkForUpdate from "update-check";
|
|
1640
1699
|
|
|
1641
|
-
// src/utilities/colors.ts
|
|
1642
|
-
import chalk2 from "chalk";
|
|
1643
|
-
var green = "#4FFF54";
|
|
1644
|
-
var purple = "#735BF3";
|
|
1645
|
-
function chalkPurple(text2) {
|
|
1646
|
-
return chalk2.hex(purple)(text2);
|
|
1647
|
-
}
|
|
1648
|
-
function chalkGrey(text2) {
|
|
1649
|
-
return chalk2.hex("#666")(text2);
|
|
1650
|
-
}
|
|
1651
|
-
function chalkLink(text2) {
|
|
1652
|
-
return chalk2.underline.blue(text2);
|
|
1653
|
-
}
|
|
1654
|
-
function logo() {
|
|
1655
|
-
return `${chalk2.hex(green).bold("Trigger")}${chalk2.hex(purple).bold(".dev")}`;
|
|
1656
|
-
}
|
|
1657
|
-
|
|
1658
1700
|
// src/utilities/getVersion.ts
|
|
1659
1701
|
import path3 from "path";
|
|
1660
1702
|
function getVersion() {
|
|
@@ -1666,10 +1708,10 @@ function getVersion() {
|
|
|
1666
1708
|
// src/utilities/initialBanner.ts
|
|
1667
1709
|
async function printInitialBanner(performUpdateCheck = true) {
|
|
1668
1710
|
const packageVersion = getVersion();
|
|
1669
|
-
const
|
|
1711
|
+
const text3 = `
|
|
1670
1712
|
${logo()} ${chalkGrey(`(${packageVersion})`)}
|
|
1671
1713
|
`;
|
|
1672
|
-
logger.info(
|
|
1714
|
+
logger.info(text3);
|
|
1673
1715
|
let maybeNewVersion;
|
|
1674
1716
|
if (performUpdateCheck) {
|
|
1675
1717
|
const loadingSpinner = spinner();
|
|
@@ -1693,17 +1735,23 @@ After installation, run Trigger.dev with \`npx trigger.dev\`.`
|
|
|
1693
1735
|
}
|
|
1694
1736
|
async function printStandloneInitialBanner(performUpdateCheck = true) {
|
|
1695
1737
|
const packageVersion = getVersion();
|
|
1696
|
-
let
|
|
1738
|
+
let text3 = `
|
|
1697
1739
|
${logo()} ${chalkGrey("(v3 Developer Preview)")}`;
|
|
1698
1740
|
if (performUpdateCheck) {
|
|
1699
1741
|
const maybeNewVersion = await updateCheck();
|
|
1700
1742
|
if (maybeNewVersion !== void 0) {
|
|
1701
|
-
|
|
1743
|
+
text3 = `${text3} (update available ${chalk3.green(maybeNewVersion)})`;
|
|
1702
1744
|
}
|
|
1703
1745
|
}
|
|
1746
|
+
logger.log(text3 + "\n" + (supportsColor.stdout ? chalkGrey("-".repeat(54)) : "-".repeat(54)));
|
|
1747
|
+
}
|
|
1748
|
+
function printDevBanner() {
|
|
1704
1749
|
logger.log(
|
|
1705
|
-
|
|
1750
|
+
`${chalkGrey("Key:")} ${chalkWorker("Version")} ${chalkGrey("|")} ${chalkTask(
|
|
1751
|
+
"Task"
|
|
1752
|
+
)} ${chalkGrey("|")} ${chalkRun("Run")}`
|
|
1706
1753
|
);
|
|
1754
|
+
logger.log(chalkGrey("-".repeat(54)));
|
|
1707
1755
|
}
|
|
1708
1756
|
async function doUpdateCheck() {
|
|
1709
1757
|
let update = null;
|
|
@@ -1727,20 +1775,14 @@ async function installPackages(packages, options) {
|
|
|
1727
1775
|
const cwd = options?.cwd ?? process.cwd();
|
|
1728
1776
|
logger.debug("Installing packages", { packages });
|
|
1729
1777
|
await setPackageJsonDeps(join3(cwd, "package.json"), packages);
|
|
1730
|
-
|
|
1778
|
+
await execa(
|
|
1731
1779
|
"npm",
|
|
1732
1780
|
["install", "--install-strategy", "nested", "--ignore-scripts", "--no-audit", "--no-fund"],
|
|
1733
1781
|
{
|
|
1734
1782
|
cwd,
|
|
1735
|
-
stderr: "
|
|
1783
|
+
stderr: "pipe"
|
|
1736
1784
|
}
|
|
1737
1785
|
);
|
|
1738
|
-
await new Promise((res, rej) => {
|
|
1739
|
-
childProcess2.on("error", (e) => rej(e));
|
|
1740
|
-
childProcess2.on("close", () => res());
|
|
1741
|
-
});
|
|
1742
|
-
await childProcess2;
|
|
1743
|
-
return;
|
|
1744
1786
|
}
|
|
1745
1787
|
function detectPackageNameFromImportPath(path6) {
|
|
1746
1788
|
if (path6.startsWith("@")) {
|
|
@@ -2392,7 +2434,9 @@ async function isLoggedIn(profile = "default") {
|
|
|
2392
2434
|
// src/commands/whoami.ts
|
|
2393
2435
|
var WhoamiCommandOptions = CommonCommandOptions;
|
|
2394
2436
|
function configureWhoamiCommand(program2) {
|
|
2395
|
-
return commonOptions(
|
|
2437
|
+
return commonOptions(
|
|
2438
|
+
program2.command("whoami").description("display the current logged in user and project details")
|
|
2439
|
+
).action(async (options) => {
|
|
2396
2440
|
await handleTelemetry(async () => {
|
|
2397
2441
|
await printInitialBanner(false);
|
|
2398
2442
|
await whoAmICommand(options);
|
|
@@ -2415,7 +2459,9 @@ async function whoAmI(options, embedded = false) {
|
|
|
2415
2459
|
if (authentication.error === "fetch failed") {
|
|
2416
2460
|
loadingSpinner.stop("Fetch failed. Platform down?");
|
|
2417
2461
|
} else {
|
|
2418
|
-
loadingSpinner.stop(
|
|
2462
|
+
loadingSpinner.stop(
|
|
2463
|
+
`You must login first. Use \`trigger.dev login --profile ${options?.profile ?? "default"}\` to login.`
|
|
2464
|
+
);
|
|
2419
2465
|
}
|
|
2420
2466
|
return {
|
|
2421
2467
|
success: false,
|
|
@@ -2482,7 +2528,14 @@ async function login(options) {
|
|
|
2482
2528
|
}
|
|
2483
2529
|
const authConfig = readAuthConfigProfile(options?.profile);
|
|
2484
2530
|
if (authConfig && authConfig.accessToken) {
|
|
2485
|
-
const whoAmIResult = await whoAmI(
|
|
2531
|
+
const whoAmIResult = await whoAmI(
|
|
2532
|
+
{
|
|
2533
|
+
profile: options?.profile ?? "default",
|
|
2534
|
+
skipTelemetry: !span.isRecording(),
|
|
2535
|
+
logLevel: logger.loggerLevel
|
|
2536
|
+
},
|
|
2537
|
+
opts.embedded
|
|
2538
|
+
);
|
|
2486
2539
|
if (!whoAmIResult.success) {
|
|
2487
2540
|
throw new Error(whoAmIResult.error);
|
|
2488
2541
|
} else {
|
|
@@ -2565,8 +2618,18 @@ ${chalkLink(authorizationCodeResult.url)}`
|
|
|
2565
2618
|
}
|
|
2566
2619
|
);
|
|
2567
2620
|
getPersonalAccessTokenSpinner.stop(`Logged in with token ${indexResult.obfuscatedToken}`);
|
|
2568
|
-
writeAuthConfigProfile(
|
|
2569
|
-
|
|
2621
|
+
writeAuthConfigProfile(
|
|
2622
|
+
{ accessToken: indexResult.token, apiUrl: opts.defaultApiUrl },
|
|
2623
|
+
options?.profile
|
|
2624
|
+
);
|
|
2625
|
+
const whoAmIResult = await whoAmI(
|
|
2626
|
+
{
|
|
2627
|
+
profile: options?.profile ?? "default",
|
|
2628
|
+
skipTelemetry: !span.isRecording(),
|
|
2629
|
+
logLevel: logger.loggerLevel
|
|
2630
|
+
},
|
|
2631
|
+
opts.embedded
|
|
2632
|
+
);
|
|
2570
2633
|
if (!whoAmIResult.success) {
|
|
2571
2634
|
throw new Error(whoAmIResult.error);
|
|
2572
2635
|
}
|
|
@@ -2663,10 +2726,45 @@ ${authorizationCodeResult.error}`
|
|
|
2663
2726
|
});
|
|
2664
2727
|
}
|
|
2665
2728
|
|
|
2729
|
+
// src/commands/deploy.ts
|
|
2730
|
+
import { Glob } from "glob";
|
|
2731
|
+
|
|
2666
2732
|
// src/utilities/build.ts
|
|
2733
|
+
import { readFileSync } from "node:fs";
|
|
2667
2734
|
import { extname, isAbsolute } from "node:path";
|
|
2668
2735
|
import tsConfigPaths from "tsconfig-paths";
|
|
2669
|
-
|
|
2736
|
+
function bundleTriggerDevCore(buildIdentifier, tsconfigPath) {
|
|
2737
|
+
return {
|
|
2738
|
+
name: "trigger-bundle-core",
|
|
2739
|
+
setup(build3) {
|
|
2740
|
+
build3.onResolve({ filter: /.*/ }, (args) => {
|
|
2741
|
+
if (args.path !== "@trigger.dev/core/v3") {
|
|
2742
|
+
return void 0;
|
|
2743
|
+
}
|
|
2744
|
+
const triggerSdkPath = __require.resolve("@trigger.dev/sdk/v3", { paths: [process.cwd()] });
|
|
2745
|
+
logger.debug(`[${buildIdentifier}][trigger-bundle-core] Resolved @trigger.dev/sdk/v3`, {
|
|
2746
|
+
...args,
|
|
2747
|
+
triggerSdkPath
|
|
2748
|
+
});
|
|
2749
|
+
const resolvedPath = __require.resolve("@trigger.dev/core/v3", {
|
|
2750
|
+
paths: [triggerSdkPath]
|
|
2751
|
+
});
|
|
2752
|
+
logger.debug(
|
|
2753
|
+
`[${buildIdentifier}][trigger-bundle-core] Externalizing @trigger.dev/core/v3`,
|
|
2754
|
+
{
|
|
2755
|
+
...args,
|
|
2756
|
+
triggerSdkPath,
|
|
2757
|
+
resolvedPath
|
|
2758
|
+
}
|
|
2759
|
+
);
|
|
2760
|
+
return {
|
|
2761
|
+
path: resolvedPath,
|
|
2762
|
+
external: false
|
|
2763
|
+
};
|
|
2764
|
+
});
|
|
2765
|
+
}
|
|
2766
|
+
};
|
|
2767
|
+
}
|
|
2670
2768
|
function workerSetupImportConfigPlugin(configPath) {
|
|
2671
2769
|
return {
|
|
2672
2770
|
name: "trigger-worker-setup",
|
|
@@ -2693,8 +2791,8 @@ function workerSetupImportConfigPlugin(configPath) {
|
|
|
2693
2791
|
}
|
|
2694
2792
|
};
|
|
2695
2793
|
}
|
|
2696
|
-
function bundleDependenciesPlugin(
|
|
2697
|
-
const matchPath =
|
|
2794
|
+
function bundleDependenciesPlugin(buildIdentifier, dependenciesToBundle, tsconfigPath) {
|
|
2795
|
+
const matchPath = tsconfigPath ? createMatchPath(tsconfigPath) : void 0;
|
|
2698
2796
|
function resolvePath(id) {
|
|
2699
2797
|
if (!matchPath) {
|
|
2700
2798
|
return id;
|
|
@@ -2706,20 +2804,7 @@ function bundleDependenciesPlugin(config) {
|
|
|
2706
2804
|
setup(build3) {
|
|
2707
2805
|
build3.onResolve({ filter: /.*/ }, (args) => {
|
|
2708
2806
|
const resolvedPath = resolvePath(args.path);
|
|
2709
|
-
logger.ignore(`Checking if ${args.path} should be bundled or external`, {
|
|
2710
|
-
...args,
|
|
2711
|
-
resolvedPath
|
|
2712
|
-
});
|
|
2713
2807
|
if (!isBareModuleId(resolvedPath)) {
|
|
2714
|
-
logger.ignore(`Bundling ${args.path} because its not a bareModuleId`, {
|
|
2715
|
-
...args
|
|
2716
|
-
});
|
|
2717
|
-
return void 0;
|
|
2718
|
-
}
|
|
2719
|
-
if (args.path.startsWith("@trigger.dev/")) {
|
|
2720
|
-
logger.ignore(`Bundling ${args.path} because its a trigger.dev package`, {
|
|
2721
|
-
...args
|
|
2722
|
-
});
|
|
2723
2808
|
return void 0;
|
|
2724
2809
|
}
|
|
2725
2810
|
let loader;
|
|
@@ -2733,12 +2818,12 @@ function bundleDependenciesPlugin(config) {
|
|
|
2733
2818
|
if (loader === "file") {
|
|
2734
2819
|
return void 0;
|
|
2735
2820
|
}
|
|
2736
|
-
for (let pattern of
|
|
2821
|
+
for (let pattern of dependenciesToBundle ?? []) {
|
|
2737
2822
|
if (typeof pattern === "string" ? args.path === pattern : pattern.test(args.path)) {
|
|
2738
2823
|
return void 0;
|
|
2739
2824
|
}
|
|
2740
2825
|
}
|
|
2741
|
-
logger.ignore(`Externalizing ${args.path}`, {
|
|
2826
|
+
logger.ignore(`[${buildIdentifier}] Externalizing ${args.path}`, {
|
|
2742
2827
|
...args
|
|
2743
2828
|
});
|
|
2744
2829
|
return {
|
|
@@ -2826,8 +2911,151 @@ function getLoaderForFile(file) {
|
|
|
2826
2911
|
throw new Error(`Cannot get loader for file ${file}`);
|
|
2827
2912
|
}
|
|
2828
2913
|
|
|
2914
|
+
// src/utilities/deployErrors.ts
|
|
2915
|
+
import chalk4 from "chalk";
|
|
2916
|
+
import { relative as relative2 } from "node:path";
|
|
2917
|
+
import { groupTaskMetadataIssuesByTask } from "@trigger.dev/core/v3";
|
|
2918
|
+
function errorIsErrorLike(error) {
|
|
2919
|
+
return error instanceof Error || typeof error === "object" && error !== null && "message" in error;
|
|
2920
|
+
}
|
|
2921
|
+
function parseBuildErrorStack(error) {
|
|
2922
|
+
if (typeof error === "string") {
|
|
2923
|
+
return error;
|
|
2924
|
+
}
|
|
2925
|
+
if (errorIsErrorLike(error)) {
|
|
2926
|
+
if (typeof error.stack === "string") {
|
|
2927
|
+
const isErrRequireEsm = error.stack.includes("ERR_REQUIRE_ESM");
|
|
2928
|
+
let moduleName = null;
|
|
2929
|
+
if (isErrRequireEsm) {
|
|
2930
|
+
const moduleRegex = /node_modules\/(@[^\/]+\/[^\/]+|[^\/]+)\/[^\/]+\s/;
|
|
2931
|
+
const match = moduleRegex.exec(error.stack);
|
|
2932
|
+
if (match) {
|
|
2933
|
+
moduleName = match[1];
|
|
2934
|
+
return {
|
|
2935
|
+
type: "esm-require-error",
|
|
2936
|
+
moduleName
|
|
2937
|
+
};
|
|
2938
|
+
}
|
|
2939
|
+
}
|
|
2940
|
+
} else {
|
|
2941
|
+
return error.message;
|
|
2942
|
+
}
|
|
2943
|
+
}
|
|
2944
|
+
return "Unknown error";
|
|
2945
|
+
}
|
|
2946
|
+
function logESMRequireError(parsedError, resolvedConfig) {
|
|
2947
|
+
logger.log(
|
|
2948
|
+
`
|
|
2949
|
+
${chalkError("X Error:")} The ${chalkPurple(
|
|
2950
|
+
parsedError.moduleName
|
|
2951
|
+
)} module is being required even though it's ESM only, and builds only support CommonJS. There are two ${chalk4.underline(
|
|
2952
|
+
"possible"
|
|
2953
|
+
)} ways to fix this:`
|
|
2954
|
+
);
|
|
2955
|
+
logger.log(
|
|
2956
|
+
`
|
|
2957
|
+
${chalkGrey("\u25CB")} Dynamically import the module in your code: ${chalkGrey(
|
|
2958
|
+
`const myModule = await import("${parsedError.moduleName}");`
|
|
2959
|
+
)}`
|
|
2960
|
+
);
|
|
2961
|
+
if (resolvedConfig.status === "file") {
|
|
2962
|
+
const relativePath = relative2(resolvedConfig.config.projectDir, resolvedConfig.path).replace(
|
|
2963
|
+
/\\/g,
|
|
2964
|
+
"/"
|
|
2965
|
+
);
|
|
2966
|
+
logger.log(
|
|
2967
|
+
`${chalkGrey("\u25CB")} ${chalk4.underline("Or")} add ${chalkPurple(
|
|
2968
|
+
parsedError.moduleName
|
|
2969
|
+
)} to the ${chalkGreen("dependenciesToBundle")} array in your config file ${chalkGrey(
|
|
2970
|
+
`(${relativePath})`
|
|
2971
|
+
)}. This will bundle the module with your code.
|
|
2972
|
+
`
|
|
2973
|
+
);
|
|
2974
|
+
} else {
|
|
2975
|
+
logger.log(
|
|
2976
|
+
`${chalkGrey("\u25CB")} ${chalk4.underline("Or")} add ${chalkPurple(
|
|
2977
|
+
parsedError.moduleName
|
|
2978
|
+
)} to the ${chalkGreen("dependenciesToBundle")} array in your config file ${chalkGrey(
|
|
2979
|
+
"(you'll need to create one)"
|
|
2980
|
+
)}. This will bundle the module with your code.
|
|
2981
|
+
`
|
|
2982
|
+
);
|
|
2983
|
+
}
|
|
2984
|
+
}
|
|
2985
|
+
function parseNpmInstallError(error) {
|
|
2986
|
+
if (typeof error === "string") {
|
|
2987
|
+
return error;
|
|
2988
|
+
}
|
|
2989
|
+
if (error instanceof Error) {
|
|
2990
|
+
if (typeof error.stack === "string") {
|
|
2991
|
+
const isPackageNotFoundError = error.stack.includes("ERR! 404 Not Found") && error.stack.includes("is not in this registry");
|
|
2992
|
+
let packageName = null;
|
|
2993
|
+
if (isPackageNotFoundError) {
|
|
2994
|
+
const packageNameRegex = /'([^']+)' is not in this registry/;
|
|
2995
|
+
const match = packageNameRegex.exec(error.stack);
|
|
2996
|
+
if (match) {
|
|
2997
|
+
packageName = match[1];
|
|
2998
|
+
}
|
|
2999
|
+
}
|
|
3000
|
+
if (packageName) {
|
|
3001
|
+
return {
|
|
3002
|
+
type: "package-not-found-error",
|
|
3003
|
+
packageName
|
|
3004
|
+
};
|
|
3005
|
+
}
|
|
3006
|
+
const noMatchingVersionRegex = /No matching version found for ([^\s]+)\s/;
|
|
3007
|
+
const noMatchingVersionMatch = noMatchingVersionRegex.exec(error.stack);
|
|
3008
|
+
if (noMatchingVersionMatch) {
|
|
3009
|
+
return {
|
|
3010
|
+
type: "no-matching-version-error",
|
|
3011
|
+
packageName: noMatchingVersionMatch[1].replace(/.$/, "")
|
|
3012
|
+
};
|
|
3013
|
+
}
|
|
3014
|
+
return error.message;
|
|
3015
|
+
} else {
|
|
3016
|
+
return error.message;
|
|
3017
|
+
}
|
|
3018
|
+
}
|
|
3019
|
+
return "Unknown error";
|
|
3020
|
+
}
|
|
3021
|
+
function logTaskMetadataParseError(zodIssues, tasks) {
|
|
3022
|
+
logger.log(
|
|
3023
|
+
`
|
|
3024
|
+
${chalkError("X Error:")} Failed to start. The following ${zodIssues.length === 1 ? "task issue was" : "task issues were"} found:`
|
|
3025
|
+
);
|
|
3026
|
+
const groupedIssues = groupTaskMetadataIssuesByTask(tasks, zodIssues);
|
|
3027
|
+
for (const key in groupedIssues) {
|
|
3028
|
+
const taskWithIssues = groupedIssues[key];
|
|
3029
|
+
if (!taskWithIssues) {
|
|
3030
|
+
continue;
|
|
3031
|
+
}
|
|
3032
|
+
logger.log(
|
|
3033
|
+
`
|
|
3034
|
+
${chalkWarning("\u276F")} ${taskWithIssues.exportName} ${chalkGrey("in")} ${taskWithIssues.filePath}`
|
|
3035
|
+
);
|
|
3036
|
+
for (const issue of taskWithIssues.issues) {
|
|
3037
|
+
if (issue.path) {
|
|
3038
|
+
logger.log(` ${chalkError("x")} ${issue.path} ${chalkGrey(issue.message)}`);
|
|
3039
|
+
} else {
|
|
3040
|
+
logger.log(` ${chalkError("x")} ${chalkGrey(issue.message)}`);
|
|
3041
|
+
}
|
|
3042
|
+
}
|
|
3043
|
+
}
|
|
3044
|
+
}
|
|
3045
|
+
|
|
3046
|
+
// src/utilities/safeJsonParse.ts
|
|
3047
|
+
function safeJsonParse(json) {
|
|
3048
|
+
if (!json) {
|
|
3049
|
+
return void 0;
|
|
3050
|
+
}
|
|
3051
|
+
try {
|
|
3052
|
+
return JSON.parse(json);
|
|
3053
|
+
} catch {
|
|
3054
|
+
return void 0;
|
|
3055
|
+
}
|
|
3056
|
+
}
|
|
3057
|
+
|
|
2829
3058
|
// src/commands/deploy.ts
|
|
2830
|
-
import { Glob } from "glob";
|
|
2831
3059
|
var DeployCommandOptions = CommonCommandOptions.extend({
|
|
2832
3060
|
skipTypecheck: z4.boolean().default(false),
|
|
2833
3061
|
skipDeploy: z4.boolean().default(false),
|
|
@@ -3001,26 +3229,38 @@ async function _deployCommand(dir, options) {
|
|
|
3001
3229
|
"Failed to initialize deployment. The deployment does not have any external build data. To deploy this project, you must use the --self-hosted flag to build and push the image yourself."
|
|
3002
3230
|
);
|
|
3003
3231
|
}
|
|
3004
|
-
return buildAndPushImage(
|
|
3005
|
-
|
|
3006
|
-
|
|
3007
|
-
|
|
3008
|
-
|
|
3009
|
-
|
|
3010
|
-
|
|
3011
|
-
|
|
3012
|
-
|
|
3013
|
-
|
|
3014
|
-
|
|
3015
|
-
|
|
3016
|
-
|
|
3017
|
-
|
|
3018
|
-
|
|
3019
|
-
|
|
3232
|
+
return buildAndPushImage(
|
|
3233
|
+
{
|
|
3234
|
+
registryHost,
|
|
3235
|
+
auth: authorization.auth.accessToken,
|
|
3236
|
+
imageTag: deploymentResponse.data.imageTag,
|
|
3237
|
+
buildId: deploymentResponse.data.externalBuildData.buildId,
|
|
3238
|
+
buildToken: deploymentResponse.data.externalBuildData.buildToken,
|
|
3239
|
+
buildProjectId: deploymentResponse.data.externalBuildData.projectId,
|
|
3240
|
+
cwd: compilation.path,
|
|
3241
|
+
projectId: resolvedConfig.config.project,
|
|
3242
|
+
deploymentId: deploymentResponse.data.id,
|
|
3243
|
+
deploymentVersion: deploymentResponse.data.version,
|
|
3244
|
+
contentHash: deploymentResponse.data.contentHash,
|
|
3245
|
+
projectRef: resolvedConfig.config.project,
|
|
3246
|
+
loadImage: options.loadImage,
|
|
3247
|
+
buildPlatform: options.buildPlatform
|
|
3248
|
+
},
|
|
3249
|
+
deploymentSpinner
|
|
3250
|
+
);
|
|
3020
3251
|
};
|
|
3021
3252
|
const image = await buildImage();
|
|
3022
3253
|
if (!image.ok) {
|
|
3023
|
-
deploymentSpinner.stop(`Failed to build project
|
|
3254
|
+
deploymentSpinner.stop(`Failed to build project.`);
|
|
3255
|
+
if (image.logs.trim() !== "") {
|
|
3256
|
+
const logPath = join4(await createTempDir(), `build-${deploymentResponse.data.shortCode}.log`);
|
|
3257
|
+
await writeFile2(logPath, image.logs);
|
|
3258
|
+
logger.log(
|
|
3259
|
+
`${chalkError("X Error:")} ${image.error}. Full build logs have been saved to ${logPath})`
|
|
3260
|
+
);
|
|
3261
|
+
} else {
|
|
3262
|
+
logger.log(`${chalkError("X Error:")} ${image.error}.`);
|
|
3263
|
+
}
|
|
3024
3264
|
throw new SkipLoggingError(`Failed to build project image: ${image.error}`);
|
|
3025
3265
|
}
|
|
3026
3266
|
const imageReference = options.selfHosted ? `${selfHostedRegistryHost ? `${selfHostedRegistryHost}/` : ""}${image.image}${image.digest ? `@${image.digest}` : ""}` : `${registryHost}/${image.image}${image.digest ? `@${image.digest}` : ""}`;
|
|
@@ -3080,10 +3320,27 @@ async function _deployCommand(dir, options) {
|
|
|
3080
3320
|
}
|
|
3081
3321
|
case "FAILED": {
|
|
3082
3322
|
if (finishedDeployment.errorData) {
|
|
3083
|
-
|
|
3084
|
-
|
|
3085
|
-
|
|
3086
|
-
|
|
3323
|
+
if (finishedDeployment.errorData.name === "TaskMetadataParseError") {
|
|
3324
|
+
const errorJson = safeJsonParse(finishedDeployment.errorData.stack);
|
|
3325
|
+
if (errorJson) {
|
|
3326
|
+
const parsedError2 = TaskMetadataFailedToParseData.safeParse(errorJson);
|
|
3327
|
+
if (parsedError2.success) {
|
|
3328
|
+
deploymentSpinner.stop(`Deployment encountered an error. ${deploymentLink}`);
|
|
3329
|
+
logTaskMetadataParseError(parsedError2.data.zodIssues, parsedError2.data.tasks);
|
|
3330
|
+
throw new SkipLoggingError(
|
|
3331
|
+
`Deployment encountered an error: ${finishedDeployment.errorData.name}`
|
|
3332
|
+
);
|
|
3333
|
+
}
|
|
3334
|
+
}
|
|
3335
|
+
}
|
|
3336
|
+
const parsedError = finishedDeployment.errorData.stack ? parseBuildErrorStack(finishedDeployment.errorData) : finishedDeployment.errorData.message;
|
|
3337
|
+
if (typeof parsedError === "string") {
|
|
3338
|
+
deploymentSpinner.stop(`Deployment encountered an error. ${deploymentLink}`);
|
|
3339
|
+
logger.log(`${chalkError("X Error:")} ${parsedError}`);
|
|
3340
|
+
} else {
|
|
3341
|
+
deploymentSpinner.stop(`Deployment encountered an error. ${deploymentLink}`);
|
|
3342
|
+
logESMRequireError(parsedError, resolvedConfig);
|
|
3343
|
+
}
|
|
3087
3344
|
throw new SkipLoggingError(
|
|
3088
3345
|
`Deployment encountered an error: ${finishedDeployment.errorData.name}`
|
|
3089
3346
|
);
|
|
@@ -3121,7 +3378,7 @@ async function checkEnvVars(envVars, config, options, environmentClient, apiUrl)
|
|
|
3121
3378
|
environmentVariablesSpinner.stop(
|
|
3122
3379
|
`Found missing env vars in ${options.env}: ${arrayToSentence(
|
|
3123
3380
|
missingEnvironmentVariables
|
|
3124
|
-
)}. ${options.ignoreEnvVarCheck ? "Continuing deployment because of --ignore-env-var-check. " : "Aborting deployment. "}${
|
|
3381
|
+
)}. ${options.ignoreEnvVarCheck ? "Continuing deployment because of --ignore-env-var-check. " : "Aborting deployment. "}${chalk5.bgBlueBright(
|
|
3125
3382
|
terminalLink(
|
|
3126
3383
|
"Manage env vars",
|
|
3127
3384
|
`${apiUrl}/projects/v3/${config.project}/environment-variables`
|
|
@@ -3182,7 +3439,7 @@ async function waitForDeploymentToFinish(deploymentId, client, timeoutInSeconds
|
|
|
3182
3439
|
}
|
|
3183
3440
|
});
|
|
3184
3441
|
}
|
|
3185
|
-
async function buildAndPushImage(options) {
|
|
3442
|
+
async function buildAndPushImage(options, updater) {
|
|
3186
3443
|
return tracer.startActiveSpan("buildAndPushImage", async (span) => {
|
|
3187
3444
|
span.setAttributes({
|
|
3188
3445
|
"options.registryHost": options.registryHost,
|
|
@@ -3238,15 +3495,23 @@ async function buildAndPushImage(options) {
|
|
|
3238
3495
|
});
|
|
3239
3496
|
const errors = [];
|
|
3240
3497
|
try {
|
|
3241
|
-
await new Promise((res, rej) => {
|
|
3498
|
+
const processCode = await new Promise((res, rej) => {
|
|
3242
3499
|
childProcess2.stderr?.on("data", (data) => {
|
|
3243
|
-
const
|
|
3244
|
-
errors.push(
|
|
3245
|
-
logger.debug(
|
|
3500
|
+
const text3 = data.toString();
|
|
3501
|
+
errors.push(text3);
|
|
3502
|
+
logger.debug(text3);
|
|
3246
3503
|
});
|
|
3247
3504
|
childProcess2.on("error", (e) => rej(e));
|
|
3248
|
-
childProcess2.on("close", () => res());
|
|
3505
|
+
childProcess2.on("close", (code) => res(code));
|
|
3249
3506
|
});
|
|
3507
|
+
const logs = extractLogs(errors);
|
|
3508
|
+
if (processCode !== 0) {
|
|
3509
|
+
return {
|
|
3510
|
+
ok: false,
|
|
3511
|
+
error: `Error building image`,
|
|
3512
|
+
logs
|
|
3513
|
+
};
|
|
3514
|
+
}
|
|
3250
3515
|
const digest = extractImageDigest(errors);
|
|
3251
3516
|
span.setAttributes({
|
|
3252
3517
|
"image.digest": digest
|
|
@@ -3255,6 +3520,7 @@ async function buildAndPushImage(options) {
|
|
|
3255
3520
|
return {
|
|
3256
3521
|
ok: true,
|
|
3257
3522
|
image: options.imageTag,
|
|
3523
|
+
logs,
|
|
3258
3524
|
digest
|
|
3259
3525
|
};
|
|
3260
3526
|
} catch (e) {
|
|
@@ -3262,7 +3528,8 @@ async function buildAndPushImage(options) {
|
|
|
3262
3528
|
span.end();
|
|
3263
3529
|
return {
|
|
3264
3530
|
ok: false,
|
|
3265
|
-
error: e instanceof Error ? e.message : JSON.stringify(e)
|
|
3531
|
+
error: e instanceof Error ? e.message : JSON.stringify(e),
|
|
3532
|
+
logs: extractLogs(errors)
|
|
3266
3533
|
};
|
|
3267
3534
|
}
|
|
3268
3535
|
});
|
|
@@ -3310,9 +3577,9 @@ async function buildAndPushSelfHostedImage(options) {
|
|
|
3310
3577
|
try {
|
|
3311
3578
|
await new Promise((res, rej) => {
|
|
3312
3579
|
buildProcess.stderr?.on("data", (data) => {
|
|
3313
|
-
const
|
|
3314
|
-
errors.push(
|
|
3315
|
-
logger.debug(
|
|
3580
|
+
const text3 = data.toString();
|
|
3581
|
+
errors.push(text3);
|
|
3582
|
+
logger.debug(text3);
|
|
3316
3583
|
});
|
|
3317
3584
|
buildProcess.on("error", (e) => rej(e));
|
|
3318
3585
|
buildProcess.on("close", () => res());
|
|
@@ -3326,7 +3593,8 @@ async function buildAndPushSelfHostedImage(options) {
|
|
|
3326
3593
|
span.end();
|
|
3327
3594
|
return {
|
|
3328
3595
|
ok: false,
|
|
3329
|
-
error: e instanceof Error ? e.message : JSON.stringify(e)
|
|
3596
|
+
error: e instanceof Error ? e.message : JSON.stringify(e),
|
|
3597
|
+
logs: extractLogs(errors)
|
|
3330
3598
|
};
|
|
3331
3599
|
}
|
|
3332
3600
|
const pushArgs = ["push", imageRef].filter(Boolean);
|
|
@@ -3339,12 +3607,12 @@ async function buildAndPushSelfHostedImage(options) {
|
|
|
3339
3607
|
try {
|
|
3340
3608
|
await new Promise((res, rej) => {
|
|
3341
3609
|
pushProcess.stdout?.on("data", (data) => {
|
|
3342
|
-
const
|
|
3343
|
-
logger.debug(
|
|
3610
|
+
const text3 = data.toString();
|
|
3611
|
+
logger.debug(text3);
|
|
3344
3612
|
});
|
|
3345
3613
|
pushProcess.stderr?.on("data", (data) => {
|
|
3346
|
-
const
|
|
3347
|
-
logger.debug(
|
|
3614
|
+
const text3 = data.toString();
|
|
3615
|
+
logger.debug(text3);
|
|
3348
3616
|
});
|
|
3349
3617
|
pushProcess.on("error", (e) => rej(e));
|
|
3350
3618
|
pushProcess.on("close", () => res());
|
|
@@ -3355,7 +3623,8 @@ async function buildAndPushSelfHostedImage(options) {
|
|
|
3355
3623
|
span.end();
|
|
3356
3624
|
return {
|
|
3357
3625
|
ok: false,
|
|
3358
|
-
error: e instanceof Error ? e.message : JSON.stringify(e)
|
|
3626
|
+
error: e instanceof Error ? e.message : JSON.stringify(e),
|
|
3627
|
+
logs: extractLogs(errors)
|
|
3359
3628
|
};
|
|
3360
3629
|
}
|
|
3361
3630
|
}
|
|
@@ -3363,7 +3632,8 @@ async function buildAndPushSelfHostedImage(options) {
|
|
|
3363
3632
|
return {
|
|
3364
3633
|
ok: true,
|
|
3365
3634
|
image: options.imageTag,
|
|
3366
|
-
digest
|
|
3635
|
+
digest,
|
|
3636
|
+
logs: extractLogs(errors)
|
|
3367
3637
|
};
|
|
3368
3638
|
});
|
|
3369
3639
|
}
|
|
@@ -3378,6 +3648,10 @@ function extractImageDigest(outputs) {
|
|
|
3378
3648
|
}
|
|
3379
3649
|
}
|
|
3380
3650
|
}
|
|
3651
|
+
function extractLogs(outputs) {
|
|
3652
|
+
const cleanedOutputs = outputs.map((line) => line.trim()).filter((line) => line !== "");
|
|
3653
|
+
return cleanedOutputs.map((line) => line.trim()).join("\n");
|
|
3654
|
+
}
|
|
3381
3655
|
async function compileProject(config, options, configPath) {
|
|
3382
3656
|
return await tracer.startActiveSpan("compileProject", async (span) => {
|
|
3383
3657
|
try {
|
|
@@ -3435,7 +3709,14 @@ async function compileProject(config, options, configPath) {
|
|
|
3435
3709
|
TRIGGER_API_URL: `"${config.triggerUrl}"`,
|
|
3436
3710
|
__PROJECT_CONFIG__: JSON.stringify(config)
|
|
3437
3711
|
},
|
|
3438
|
-
plugins: [
|
|
3712
|
+
plugins: [
|
|
3713
|
+
bundleDependenciesPlugin(
|
|
3714
|
+
"workerFacade",
|
|
3715
|
+
config.dependenciesToBundle,
|
|
3716
|
+
config.tsconfigPath
|
|
3717
|
+
),
|
|
3718
|
+
workerSetupImportConfigPlugin(configPath)
|
|
3719
|
+
]
|
|
3439
3720
|
});
|
|
3440
3721
|
if (result.errors.length > 0) {
|
|
3441
3722
|
compileSpinner.stop("Build failed, aborting deployment");
|
|
@@ -3467,17 +3748,23 @@ async function compileProject(config, options, configPath) {
|
|
|
3467
3748
|
write: false,
|
|
3468
3749
|
minify: false,
|
|
3469
3750
|
sourcemap: false,
|
|
3470
|
-
packages: "external",
|
|
3471
|
-
// https://esbuild.github.io/api/#packages
|
|
3472
3751
|
logLevel: "error",
|
|
3473
3752
|
platform: "node",
|
|
3753
|
+
packages: "external",
|
|
3474
3754
|
format: "cjs",
|
|
3475
3755
|
// This is needed to support opentelemetry instrumentation that uses module patching
|
|
3476
3756
|
target: ["node18", "es2020"],
|
|
3477
3757
|
outdir: "out",
|
|
3478
3758
|
define: {
|
|
3479
3759
|
__PROJECT_CONFIG__: JSON.stringify(config)
|
|
3480
|
-
}
|
|
3760
|
+
},
|
|
3761
|
+
plugins: [
|
|
3762
|
+
bundleDependenciesPlugin(
|
|
3763
|
+
"entryPoint.ts",
|
|
3764
|
+
config.dependenciesToBundle,
|
|
3765
|
+
config.tsconfigPath
|
|
3766
|
+
)
|
|
3767
|
+
]
|
|
3481
3768
|
});
|
|
3482
3769
|
if (entryPointResult.errors.length > 0) {
|
|
3483
3770
|
compileSpinner.stop("Build failed, aborting deployment");
|
|
@@ -3519,6 +3806,10 @@ async function compileProject(config, options, configPath) {
|
|
|
3519
3806
|
);
|
|
3520
3807
|
await writeFile2(join4(tempDir, "worker.js.map"), workerSourcemapFile.text);
|
|
3521
3808
|
await writeFile2(join4(tempDir, "index.js"), entryPointOutputFile.text);
|
|
3809
|
+
logger.debug("Getting the imports for the worker and entryPoint builds", {
|
|
3810
|
+
workerImports: metaOutput.imports,
|
|
3811
|
+
entryPointImports: entryPointMetaOutput.imports
|
|
3812
|
+
});
|
|
3522
3813
|
const allImports = [...metaOutput.imports, ...entryPointMetaOutput.imports];
|
|
3523
3814
|
const externalPackageJson = await readJSONFile(join4(config.projectDir, "package.json"));
|
|
3524
3815
|
const dependencies2 = await gatherRequiredDependencies(
|
|
@@ -3545,7 +3836,7 @@ async function compileProject(config, options, configPath) {
|
|
|
3545
3836
|
options
|
|
3546
3837
|
);
|
|
3547
3838
|
if (!resolvingDependenciesResult) {
|
|
3548
|
-
throw new
|
|
3839
|
+
throw new SkipLoggingError("Failed to resolve dependencies");
|
|
3549
3840
|
}
|
|
3550
3841
|
const containerFilePath = new URL(
|
|
3551
3842
|
importResolve("./Containerfile.prod", import.meta.url)
|
|
@@ -3624,12 +3915,35 @@ async function resolveDependencies(projectDir, packageJsonContents, config, opti
|
|
|
3624
3915
|
resolvingDepsSpinner.stop("Dependencies resolved");
|
|
3625
3916
|
return true;
|
|
3626
3917
|
} catch (installError) {
|
|
3627
|
-
logger.debug(`Failed to resolve dependencies: ${JSON.stringify(installError)}`);
|
|
3628
3918
|
recordSpanException4(span, installError);
|
|
3629
3919
|
span.end();
|
|
3630
|
-
|
|
3631
|
-
|
|
3632
|
-
|
|
3920
|
+
const parsedError = parseNpmInstallError(installError);
|
|
3921
|
+
if (typeof parsedError === "string") {
|
|
3922
|
+
resolvingDepsSpinner.stop(`Failed to resolve dependencies: ${parsedError}`);
|
|
3923
|
+
} else {
|
|
3924
|
+
switch (parsedError.type) {
|
|
3925
|
+
case "package-not-found-error": {
|
|
3926
|
+
resolvingDepsSpinner.stop(`Failed to resolve dependencies`);
|
|
3927
|
+
logger.log(
|
|
3928
|
+
`
|
|
3929
|
+
${chalkError("X Error:")} The package ${chalkPurple(
|
|
3930
|
+
parsedError.packageName
|
|
3931
|
+
)} could not be found in the npm registry.`
|
|
3932
|
+
);
|
|
3933
|
+
break;
|
|
3934
|
+
}
|
|
3935
|
+
case "no-matching-version-error": {
|
|
3936
|
+
resolvingDepsSpinner.stop(`Failed to resolve dependencies`);
|
|
3937
|
+
logger.log(
|
|
3938
|
+
`
|
|
3939
|
+
${chalkError("X Error:")} The package ${chalkPurple(
|
|
3940
|
+
parsedError.packageName
|
|
3941
|
+
)} could not resolve because the version doesn't exist`
|
|
3942
|
+
);
|
|
3943
|
+
break;
|
|
3944
|
+
}
|
|
3945
|
+
}
|
|
3946
|
+
}
|
|
3633
3947
|
return false;
|
|
3634
3948
|
}
|
|
3635
3949
|
}
|
|
@@ -3676,7 +3990,7 @@ async function typecheckProject(config, options) {
|
|
|
3676
3990
|
async function gatherRequiredDependencies(imports, config, projectPackageJson) {
|
|
3677
3991
|
const dependencies2 = {};
|
|
3678
3992
|
for (const file of imports) {
|
|
3679
|
-
if (file.kind !== "require-call" || !file.external) {
|
|
3993
|
+
if (file.kind !== "require-call" && file.kind !== "dynamic-import" || !file.external) {
|
|
3680
3994
|
continue;
|
|
3681
3995
|
}
|
|
3682
3996
|
const packageName = detectPackageNameFromImportPath(file.path);
|
|
@@ -3711,8 +4025,10 @@ async function gatherRequiredDependencies(imports, config, projectPackageJson) {
|
|
|
3711
4025
|
dependencies2[packageParts.name] = externalDependencyVersion;
|
|
3712
4026
|
continue;
|
|
3713
4027
|
} else {
|
|
3714
|
-
logger.
|
|
3715
|
-
|
|
4028
|
+
logger.log(
|
|
4029
|
+
`${chalkWarning("X Warning:")} Could not find version for package ${chalkPurple(
|
|
4030
|
+
packageName
|
|
4031
|
+
)}, add a version specifier to the package name (e.g. ${packageParts.name}@latest) or add it to your project's package.json`
|
|
3716
4032
|
);
|
|
3717
4033
|
}
|
|
3718
4034
|
}
|
|
@@ -3746,7 +4062,7 @@ async function copyAdditionalFiles(config, tempDir) {
|
|
|
3746
4062
|
for await (const file of glob) {
|
|
3747
4063
|
const relativeDestinationPath = join4(
|
|
3748
4064
|
tempDir,
|
|
3749
|
-
|
|
4065
|
+
relative3(config.projectDir, file.fullpath())
|
|
3750
4066
|
);
|
|
3751
4067
|
logger.debug(`Copying file ${file.fullpath()} to ${relativeDestinationPath}`);
|
|
3752
4068
|
await mkdir(dirname(relativeDestinationPath), { recursive: true });
|
|
@@ -3778,7 +4094,7 @@ async function findAllEnvironmentVariableReferencesInFile(filePath) {
|
|
|
3778
4094
|
const fileContents = await readFile2(filePath, "utf-8");
|
|
3779
4095
|
return findAllEnvironmentVariableReferences(fileContents);
|
|
3780
4096
|
}
|
|
3781
|
-
var IGNORED_ENV_VARS = ["NODE_ENV", "SHELL", "HOME", "PWD", "LOGNAME", "USER", "PATH"];
|
|
4097
|
+
var IGNORED_ENV_VARS = ["NODE_ENV", "SHELL", "HOME", "PWD", "LOGNAME", "USER", "PATH", "DEBUG"];
|
|
3782
4098
|
function findAllEnvironmentVariableReferences(code) {
|
|
3783
4099
|
const regex = /\bprocess\.env\.([a-zA-Z_][a-zA-Z0-9_]*)\b/g;
|
|
3784
4100
|
const matches = code.matchAll(regex);
|
|
@@ -3804,7 +4120,6 @@ import {
|
|
|
3804
4120
|
detectDependencyVersion as detectDependencyVersion2,
|
|
3805
4121
|
serverWebsocketMessages
|
|
3806
4122
|
} from "@trigger.dev/core/v3";
|
|
3807
|
-
import chalk6 from "chalk";
|
|
3808
4123
|
import { watch } from "chokidar";
|
|
3809
4124
|
import { context as context2 } from "esbuild";
|
|
3810
4125
|
import { resolve as importResolve2 } from "import-meta-resolve";
|
|
@@ -3812,7 +4127,7 @@ import { render, useInput } from "ink";
|
|
|
3812
4127
|
import { createHash as createHash2 } from "node:crypto";
|
|
3813
4128
|
import fs7, { readFileSync as readFileSync3 } from "node:fs";
|
|
3814
4129
|
import { basename, dirname as dirname3, join as join5 } from "node:path";
|
|
3815
|
-
import
|
|
4130
|
+
import pDebounce from "p-debounce";
|
|
3816
4131
|
import { WebSocket } from "partysocket";
|
|
3817
4132
|
import React, { Suspense, useEffect } from "react";
|
|
3818
4133
|
import { WebSocket as wsWebSocket } from "ws";
|
|
@@ -3827,6 +4142,14 @@ var UncaughtExceptionError = class extends Error {
|
|
|
3827
4142
|
this.name = "UncaughtExceptionError";
|
|
3828
4143
|
}
|
|
3829
4144
|
};
|
|
4145
|
+
var TaskMetadataParseError = class extends Error {
|
|
4146
|
+
constructor(zodIssues, tasks) {
|
|
4147
|
+
super(`Failed to parse task metadata`);
|
|
4148
|
+
this.zodIssues = zodIssues;
|
|
4149
|
+
this.tasks = tasks;
|
|
4150
|
+
this.name = "TaskMetadataParseError";
|
|
4151
|
+
}
|
|
4152
|
+
};
|
|
3830
4153
|
|
|
3831
4154
|
// src/workers/dev/backgroundWorker.ts
|
|
3832
4155
|
import {
|
|
@@ -3836,9 +4159,9 @@ import {
|
|
|
3836
4159
|
ZodMessageSender,
|
|
3837
4160
|
childToWorkerMessages,
|
|
3838
4161
|
correctErrorStackTrace,
|
|
4162
|
+
formatDurationMilliseconds,
|
|
3839
4163
|
workerToChildMessages
|
|
3840
4164
|
} from "@trigger.dev/core/v3";
|
|
3841
|
-
import chalk5 from "chalk";
|
|
3842
4165
|
import dotenv from "dotenv";
|
|
3843
4166
|
import { Evt } from "evt";
|
|
3844
4167
|
import { fork } from "node:child_process";
|
|
@@ -3897,7 +4220,7 @@ var BackgroundWorkerCoordinator = class {
|
|
|
3897
4220
|
this._records.clear();
|
|
3898
4221
|
}
|
|
3899
4222
|
async handleMessage(id, message) {
|
|
3900
|
-
logger.debug(`Received message from worker ${id}`, { workerMessage: message });
|
|
4223
|
+
logger.debug(`Received message from worker ${id}`, JSON.stringify({ workerMessage: message }));
|
|
3901
4224
|
switch (message.type) {
|
|
3902
4225
|
case "EXECUTE_RUNS": {
|
|
3903
4226
|
await Promise.all(message.payloads.map((payload) => this.#executeTaskRun(id, payload)));
|
|
@@ -3926,23 +4249,32 @@ var BackgroundWorkerCoordinator = class {
|
|
|
3926
4249
|
}
|
|
3927
4250
|
const { execution } = payload;
|
|
3928
4251
|
const logsUrl = `${this.baseURL}/runs/${execution.run.id}`;
|
|
3929
|
-
const
|
|
3930
|
-
|
|
3931
|
-
const
|
|
3932
|
-
|
|
3933
|
-
const
|
|
3934
|
-
const
|
|
3935
|
-
|
|
4252
|
+
const pipe = chalkGrey("|");
|
|
4253
|
+
const bullet = chalkGrey("\u25CB");
|
|
4254
|
+
const link = chalkLink(terminalLink2("View logs", logsUrl));
|
|
4255
|
+
let timestampPrefix = chalkGrey(prettyPrintDate(payload.execution.attempt.startedAt));
|
|
4256
|
+
const workerPrefix = chalkWorker(record.version);
|
|
4257
|
+
const taskPrefix = chalkTask(execution.task.id);
|
|
4258
|
+
const runId = chalkRun(`${execution.run.id}.${execution.attempt.number}`);
|
|
4259
|
+
logger.log(
|
|
4260
|
+
`${bullet} ${timestampPrefix} ${chalkGrey(
|
|
4261
|
+
"->"
|
|
4262
|
+
)} ${link} ${pipe} ${workerPrefix} ${pipe} ${taskPrefix} ${pipe} ${runId}`
|
|
4263
|
+
);
|
|
3936
4264
|
const now = performance.now();
|
|
3937
4265
|
const completion = await worker.executeTaskRun(payload);
|
|
3938
4266
|
const elapsed = performance.now() - now;
|
|
3939
|
-
const retryingText =
|
|
3940
|
-
|
|
4267
|
+
const retryingText = chalkGrey(
|
|
4268
|
+
!completion.ok && completion.skippedRetrying ? " (retrying skipped)" : !completion.ok && completion.retry !== void 0 ? ` (retrying in ${completion.retry.delay}ms)` : ""
|
|
4269
|
+
);
|
|
4270
|
+
const resultText = !completion.ok ? completion.error.type === "INTERNAL_ERROR" && (completion.error.code === TaskRunErrorCodes.TASK_EXECUTION_ABORTED || completion.error.code === TaskRunErrorCodes.TASK_RUN_CANCELLED) ? chalkWarning("Cancelled") : `${chalkError("Error")}${retryingText}` : chalkSuccess("Success");
|
|
3941
4271
|
const errorText = !completion.ok ? this.#formatErrorLog(completion.error) : "retry" in completion ? `retry in ${completion.retry}ms` : "";
|
|
3942
|
-
const elapsedText =
|
|
3943
|
-
timestampPrefix =
|
|
4272
|
+
const elapsedText = chalkGrey(`(${formatDurationMilliseconds(elapsed, { style: "short" })})`);
|
|
4273
|
+
timestampPrefix = chalkGrey(prettyPrintDate());
|
|
3944
4274
|
logger.log(
|
|
3945
|
-
`${
|
|
4275
|
+
`${bullet} ${timestampPrefix} ${chalkGrey(
|
|
4276
|
+
"->"
|
|
4277
|
+
)} ${link} ${pipe} ${workerPrefix} ${pipe} ${taskPrefix} ${pipe} ${runId} ${pipe} ${resultText} ${elapsedText}${errorText}`
|
|
3946
4278
|
);
|
|
3947
4279
|
this.onTaskCompleted.post({ completion, execution, worker, backgroundWorkerId: id });
|
|
3948
4280
|
}
|
|
@@ -3954,19 +4286,19 @@ var BackgroundWorkerCoordinator = class {
|
|
|
3954
4286
|
case "STRING_ERROR": {
|
|
3955
4287
|
return `
|
|
3956
4288
|
|
|
3957
|
-
${error.raw}
|
|
4289
|
+
${chalkError("X Error:")} ${error.raw}
|
|
3958
4290
|
`;
|
|
3959
4291
|
}
|
|
3960
4292
|
case "CUSTOM_ERROR": {
|
|
3961
4293
|
return `
|
|
3962
4294
|
|
|
3963
|
-
${error.raw}
|
|
4295
|
+
${chalkError("X Error:")} ${error.raw}
|
|
3964
4296
|
`;
|
|
3965
4297
|
}
|
|
3966
4298
|
case "BUILT_IN_ERROR": {
|
|
3967
4299
|
return `
|
|
3968
4300
|
|
|
3969
|
-
${error.stackTrace}
|
|
4301
|
+
${error.stackTrace.replace(/^Error: /, chalkError("X Error: "))}
|
|
3970
4302
|
`;
|
|
3971
4303
|
}
|
|
3972
4304
|
}
|
|
@@ -4063,6 +4395,11 @@ var BackgroundWorker = class {
|
|
|
4063
4395
|
resolved = true;
|
|
4064
4396
|
reject(new UncaughtExceptionError(message.payload.error, message.payload.origin));
|
|
4065
4397
|
child.kill();
|
|
4398
|
+
} else if (message.type === "TASKS_FAILED_TO_PARSE") {
|
|
4399
|
+
clearTimeout(timeout);
|
|
4400
|
+
resolved = true;
|
|
4401
|
+
reject(new TaskMetadataParseError(message.payload.zodIssues, message.payload.tasks));
|
|
4402
|
+
child.kill();
|
|
4066
4403
|
}
|
|
4067
4404
|
});
|
|
4068
4405
|
child.on("exit", (code) => {
|
|
@@ -4088,7 +4425,7 @@ var BackgroundWorker = class {
|
|
|
4088
4425
|
}
|
|
4089
4426
|
if (!this._taskRunProcesses.has(payload.execution.run.id)) {
|
|
4090
4427
|
const taskRunProcess = new TaskRunProcess(
|
|
4091
|
-
payload.execution
|
|
4428
|
+
payload.execution,
|
|
4092
4429
|
this.path,
|
|
4093
4430
|
{
|
|
4094
4431
|
...this.params.env,
|
|
@@ -4198,8 +4535,8 @@ var BackgroundWorker = class {
|
|
|
4198
4535
|
}
|
|
4199
4536
|
};
|
|
4200
4537
|
var TaskRunProcess = class {
|
|
4201
|
-
constructor(
|
|
4202
|
-
this.
|
|
4538
|
+
constructor(execution, path6, env, metadata, worker) {
|
|
4539
|
+
this.execution = execution;
|
|
4203
4540
|
this.path = path6;
|
|
4204
4541
|
this.env = env;
|
|
4205
4542
|
this.metadata = metadata;
|
|
@@ -4230,8 +4567,17 @@ var TaskRunProcess = class {
|
|
|
4230
4567
|
await this.cleanup(true);
|
|
4231
4568
|
}
|
|
4232
4569
|
async initialize() {
|
|
4233
|
-
|
|
4234
|
-
|
|
4570
|
+
const fullEnv = {
|
|
4571
|
+
...this.execution.run.isTest ? { TRIGGER_LOG_LEVEL: "debug" } : {},
|
|
4572
|
+
...this.env,
|
|
4573
|
+
OTEL_RESOURCE_ATTRIBUTES: JSON.stringify({
|
|
4574
|
+
[SemanticInternalAttributes.PROJECT_DIR]: this.worker.projectConfig.projectDir
|
|
4575
|
+
}),
|
|
4576
|
+
OTEL_EXPORTER_OTLP_COMPRESSION: "none",
|
|
4577
|
+
...this.worker.debugOtel ? { OTEL_LOG_LEVEL: "debug" } : {}
|
|
4578
|
+
};
|
|
4579
|
+
logger.debug(`[${this.execution.run.id}] initializing task run process`, {
|
|
4580
|
+
env: fullEnv,
|
|
4235
4581
|
path: this.path
|
|
4236
4582
|
});
|
|
4237
4583
|
this._child = fork(this.path, {
|
|
@@ -4245,14 +4591,7 @@ var TaskRunProcess = class {
|
|
|
4245
4591
|
"ipc"
|
|
4246
4592
|
],
|
|
4247
4593
|
cwd: dirname2(this.path),
|
|
4248
|
-
env:
|
|
4249
|
-
...this.env,
|
|
4250
|
-
OTEL_RESOURCE_ATTRIBUTES: JSON.stringify({
|
|
4251
|
-
[SemanticInternalAttributes.PROJECT_DIR]: this.worker.projectConfig.projectDir
|
|
4252
|
-
}),
|
|
4253
|
-
OTEL_EXPORTER_OTLP_COMPRESSION: "none",
|
|
4254
|
-
...this.worker.debugOtel ? { OTEL_LOG_LEVEL: "debug" } : {}
|
|
4255
|
-
},
|
|
4594
|
+
env: fullEnv,
|
|
4256
4595
|
execArgv: this.worker.debuggerOn ? ["--inspect-brk", "--trace-uncaught", "--no-warnings=ExperimentalWarning"] : ["--trace-uncaught", "--no-warnings=ExperimentalWarning"]
|
|
4257
4596
|
});
|
|
4258
4597
|
this._child.on("message", this.#handleMessage.bind(this));
|
|
@@ -4264,7 +4603,7 @@ var TaskRunProcess = class {
|
|
|
4264
4603
|
if (kill && this._isBeingKilled) {
|
|
4265
4604
|
return;
|
|
4266
4605
|
}
|
|
4267
|
-
logger.debug(`[${this.
|
|
4606
|
+
logger.debug(`[${this.execution.run.id}] cleaning up task run process`, { kill });
|
|
4268
4607
|
await this._sender.send("CLEANUP", {
|
|
4269
4608
|
flush: true,
|
|
4270
4609
|
kill
|
|
@@ -4295,10 +4634,13 @@ var TaskRunProcess = class {
|
|
|
4295
4634
|
if (!completion.ok && typeof completion.retry !== "undefined") {
|
|
4296
4635
|
return;
|
|
4297
4636
|
}
|
|
4298
|
-
if (execution.run.id === this.
|
|
4637
|
+
if (execution.run.id === this.execution.run.id) {
|
|
4299
4638
|
return;
|
|
4300
4639
|
}
|
|
4301
|
-
logger.debug(`[${this.
|
|
4640
|
+
logger.debug(`[${this.execution.run.id}] task run completed notification`, {
|
|
4641
|
+
completion,
|
|
4642
|
+
execution
|
|
4643
|
+
});
|
|
4302
4644
|
this._sender.send("TASK_RUN_COMPLETED_NOTIFICATION", {
|
|
4303
4645
|
completion,
|
|
4304
4646
|
execution
|
|
@@ -4336,7 +4678,7 @@ var TaskRunProcess = class {
|
|
|
4336
4678
|
}
|
|
4337
4679
|
}
|
|
4338
4680
|
async #handleExit(code) {
|
|
4339
|
-
logger.debug(`[${this.
|
|
4681
|
+
logger.debug(`[${this.execution.run.id}] task run process exiting`, { code });
|
|
4340
4682
|
for (const [id, status] of this._attemptStatuses.entries()) {
|
|
4341
4683
|
if (status === "PENDING") {
|
|
4342
4684
|
this._attemptStatuses.set(id, "REJECTED");
|
|
@@ -4383,6 +4725,25 @@ var TaskRunProcess = class {
|
|
|
4383
4725
|
}
|
|
4384
4726
|
};
|
|
4385
4727
|
|
|
4728
|
+
// src/utilities/runtimeCheck.ts
|
|
4729
|
+
function runtimeCheck(minimumMajor, minimumMinor) {
|
|
4730
|
+
if (typeof process === "undefined") {
|
|
4731
|
+
throw "The dev CLI can only be run in a Node.js compatible environment";
|
|
4732
|
+
}
|
|
4733
|
+
const [major = 0, minor = 0] = process.versions.node.split(".").map(Number);
|
|
4734
|
+
const isBun = typeof process.versions.bun === "string";
|
|
4735
|
+
if (major < minimumMajor || major === minimumMajor && minor < minimumMinor) {
|
|
4736
|
+
if (isBun) {
|
|
4737
|
+
throw `The dev CLI requires at least Node.js ${minimumMajor}.${minimumMinor}. You are running Bun ${process.versions.bun}, which is compatible with Node.js ${process.versions.node}`;
|
|
4738
|
+
} else {
|
|
4739
|
+
throw `The dev CLI requires at least Node.js ${minimumMajor}.${minimumMinor}. You are running Node.js ${process.versions.node}`;
|
|
4740
|
+
}
|
|
4741
|
+
}
|
|
4742
|
+
logger.debug(
|
|
4743
|
+
`Node.js version: ${process.versions.node}${isBun ? ` (Bun ${process.versions.bun})` : ""}`
|
|
4744
|
+
);
|
|
4745
|
+
}
|
|
4746
|
+
|
|
4386
4747
|
// src/commands/dev.tsx
|
|
4387
4748
|
var apiClient;
|
|
4388
4749
|
var DevCommandOptions = CommonCommandOptions.extend({
|
|
@@ -4393,7 +4754,7 @@ var DevCommandOptions = CommonCommandOptions.extend({
|
|
|
4393
4754
|
});
|
|
4394
4755
|
function configureDevCommand(program2) {
|
|
4395
4756
|
return commonOptions(
|
|
4396
|
-
program2.command("dev").description("Run your Trigger.dev tasks locally").argument("[path]", "The path to the project", ".").option("-c, --config <config file>", "The name of the config file, found at [path]").option(
|
|
4757
|
+
program2.command("dev").description("Run your Trigger.dev tasks locally").argument("[path]", "The path to the project", ".").option("-c, --config <config file>", "The name of the config file, found at [path].").option(
|
|
4397
4758
|
"-p, --project-ref <project ref>",
|
|
4398
4759
|
"The project ref. Required if there is no config file."
|
|
4399
4760
|
).option("--debugger", "Enable the debugger").option("--debug-otel", "Enable OpenTelemetry debugging")
|
|
@@ -4403,13 +4764,26 @@ function configureDevCommand(program2) {
|
|
|
4403
4764
|
});
|
|
4404
4765
|
});
|
|
4405
4766
|
}
|
|
4767
|
+
var MINIMUM_NODE_MAJOR = 18;
|
|
4768
|
+
var MINIMUM_NODE_MINOR = 16;
|
|
4406
4769
|
async function devCommand(dir, options) {
|
|
4770
|
+
try {
|
|
4771
|
+
runtimeCheck(MINIMUM_NODE_MAJOR, MINIMUM_NODE_MINOR);
|
|
4772
|
+
} catch (e) {
|
|
4773
|
+
logger.log(`${chalkError("X Error:")} ${e}`);
|
|
4774
|
+
process.exitCode = 1;
|
|
4775
|
+
return;
|
|
4776
|
+
}
|
|
4407
4777
|
const authorization = await isLoggedIn(options.profile);
|
|
4408
4778
|
if (!authorization.ok) {
|
|
4409
4779
|
if (authorization.error === "fetch failed") {
|
|
4410
|
-
logger.
|
|
4780
|
+
logger.log(
|
|
4781
|
+
`${chalkError(
|
|
4782
|
+
"X Error:"
|
|
4783
|
+
)} Connecting to the server failed. Please check your internet connection or contact eric@trigger.dev for help.`
|
|
4784
|
+
);
|
|
4411
4785
|
} else {
|
|
4412
|
-
logger.
|
|
4786
|
+
logger.log(`${chalkError("X Error:")} You must login first. Use the \`login\` CLI command.`);
|
|
4413
4787
|
}
|
|
4414
4788
|
process.exitCode = 1;
|
|
4415
4789
|
return;
|
|
@@ -4425,6 +4799,7 @@ async function startDev(dir, options, authorization) {
|
|
|
4425
4799
|
logger.loggerLevel = options.logLevel;
|
|
4426
4800
|
}
|
|
4427
4801
|
await printStandloneInitialBanner(true);
|
|
4802
|
+
printDevBanner();
|
|
4428
4803
|
logger.debug("Starting dev session", { dir, options, authorization });
|
|
4429
4804
|
let config = await readConfig(dir, {
|
|
4430
4805
|
projectRef: options.projectRef,
|
|
@@ -4611,7 +4986,7 @@ function useDev({
|
|
|
4611
4986
|
);
|
|
4612
4987
|
}
|
|
4613
4988
|
let firstBuild = true;
|
|
4614
|
-
logger.log(
|
|
4989
|
+
logger.log(chalkGrey("\u25CB Building background worker\u2026"));
|
|
4615
4990
|
ctx = await context2({
|
|
4616
4991
|
stdin: {
|
|
4617
4992
|
contents: entryPointContents,
|
|
@@ -4635,7 +5010,12 @@ function useDev({
|
|
|
4635
5010
|
__PROJECT_CONFIG__: JSON.stringify(config)
|
|
4636
5011
|
},
|
|
4637
5012
|
plugins: [
|
|
4638
|
-
|
|
5013
|
+
bundleTriggerDevCore("workerFacade", config.tsconfigPath),
|
|
5014
|
+
bundleDependenciesPlugin(
|
|
5015
|
+
"workerFacade",
|
|
5016
|
+
(config.dependenciesToBundle ?? []).concat([/^@trigger.dev/]),
|
|
5017
|
+
config.tsconfigPath
|
|
5018
|
+
),
|
|
4639
5019
|
workerSetupImportConfigPlugin(configPath),
|
|
4640
5020
|
{
|
|
4641
5021
|
name: "trigger.dev v3",
|
|
@@ -4648,7 +5028,7 @@ function useDev({
|
|
|
4648
5028
|
return;
|
|
4649
5029
|
}
|
|
4650
5030
|
if (!firstBuild) {
|
|
4651
|
-
logger.log(
|
|
5031
|
+
logger.log(chalkGrey("\u25CB Building background worker\u2026"));
|
|
4652
5032
|
}
|
|
4653
5033
|
const metaOutputKey = join5("out", `stdin.js`);
|
|
4654
5034
|
const metaOutput = result.metafile.outputs[metaOutputKey];
|
|
@@ -4670,8 +5050,7 @@ function useDev({
|
|
|
4670
5050
|
md5Hasher.update(Buffer.from(outputFile.contents.buffer));
|
|
4671
5051
|
const contentHash = md5Hasher.digest("hex");
|
|
4672
5052
|
if (latestWorkerContentHash === contentHash) {
|
|
4673
|
-
logger.log(
|
|
4674
|
-
logger.debug(`No changes detected, skipping build`);
|
|
5053
|
+
logger.log(chalkGrey("\u25CB No changes detected, skipping build\u2026"));
|
|
4675
5054
|
return;
|
|
4676
5055
|
}
|
|
4677
5056
|
const fullPath = join5(config.projectDir, ".trigger", `${contentHash}.js`);
|
|
@@ -4742,36 +5121,65 @@ function useDev({
|
|
|
4742
5121
|
throw new Error(backgroundWorkerRecord.error);
|
|
4743
5122
|
}
|
|
4744
5123
|
backgroundWorker.metadata = backgroundWorkerRecord.data;
|
|
4745
|
-
|
|
4746
|
-
|
|
4747
|
-
|
|
4748
|
-
|
|
4749
|
-
)
|
|
4750
|
-
)
|
|
4751
|
-
|
|
4752
|
-
logger.log(
|
|
4753
|
-
chalk6.dim(
|
|
4754
|
-
`Background worker rebuilt (${backgroundWorkerRecord.data.version})`
|
|
4755
|
-
)
|
|
4756
|
-
);
|
|
4757
|
-
}
|
|
5124
|
+
logger.log(
|
|
5125
|
+
`${chalkGrey(
|
|
5126
|
+
`\u25CB Background worker started -> ${chalkWorker(
|
|
5127
|
+
backgroundWorkerRecord.data.version
|
|
5128
|
+
)}`
|
|
5129
|
+
)}`
|
|
5130
|
+
);
|
|
4758
5131
|
firstBuild = false;
|
|
4759
5132
|
await backgroundWorkerCoordinator.registerWorker(
|
|
4760
5133
|
backgroundWorkerRecord.data,
|
|
4761
5134
|
backgroundWorker
|
|
4762
5135
|
);
|
|
4763
5136
|
} catch (e) {
|
|
4764
|
-
if (e instanceof
|
|
5137
|
+
if (e instanceof TaskMetadataParseError) {
|
|
5138
|
+
logTaskMetadataParseError(e.zodIssues, e.tasks);
|
|
5139
|
+
return;
|
|
5140
|
+
} else if (e instanceof UncaughtExceptionError) {
|
|
5141
|
+
const parsedBuildError = parseBuildErrorStack(e.originalError);
|
|
5142
|
+
if (typeof parsedBuildError !== "string") {
|
|
5143
|
+
logESMRequireError(
|
|
5144
|
+
parsedBuildError,
|
|
5145
|
+
configPath ? { status: "file", path: configPath, config } : { status: "in-memory", config }
|
|
5146
|
+
);
|
|
5147
|
+
return;
|
|
5148
|
+
} else {
|
|
5149
|
+
}
|
|
4765
5150
|
if (e.originalError.stack) {
|
|
4766
|
-
logger.
|
|
5151
|
+
logger.log(
|
|
5152
|
+
`${chalkError("X Error:")} Worker failed to start`,
|
|
5153
|
+
e.originalError.stack
|
|
5154
|
+
);
|
|
4767
5155
|
}
|
|
4768
5156
|
return;
|
|
4769
5157
|
}
|
|
4770
|
-
|
|
4771
|
-
|
|
4772
|
-
|
|
5158
|
+
const parsedError = parseNpmInstallError(e);
|
|
5159
|
+
if (typeof parsedError === "string") {
|
|
5160
|
+
logger.log(`${chalkError("X Error:")} ${parsedError}`);
|
|
5161
|
+
} else {
|
|
5162
|
+
switch (parsedError.type) {
|
|
5163
|
+
case "package-not-found-error": {
|
|
5164
|
+
logger.log(
|
|
5165
|
+
`
|
|
5166
|
+
${chalkError("X Error:")} The package ${chalkPurple(
|
|
5167
|
+
parsedError.packageName
|
|
5168
|
+
)} could not be found in the npm registry.`
|
|
5169
|
+
);
|
|
5170
|
+
break;
|
|
5171
|
+
}
|
|
5172
|
+
case "no-matching-version-error": {
|
|
5173
|
+
logger.log(
|
|
5174
|
+
`
|
|
5175
|
+
${chalkError("X Error:")} The package ${chalkPurple(
|
|
5176
|
+
parsedError.packageName
|
|
5177
|
+
)} could not resolve because the version doesn't exist`
|
|
5178
|
+
);
|
|
5179
|
+
break;
|
|
5180
|
+
}
|
|
5181
|
+
}
|
|
4773
5182
|
}
|
|
4774
|
-
logger.error(`Background worker failed to start: ${e}`);
|
|
4775
5183
|
}
|
|
4776
5184
|
});
|
|
4777
5185
|
}
|
|
@@ -4780,19 +5188,14 @@ function useDev({
|
|
|
4780
5188
|
});
|
|
4781
5189
|
await ctx.watch();
|
|
4782
5190
|
}
|
|
4783
|
-
const
|
|
4784
|
-
limit: 1,
|
|
4785
|
-
interval: 1e3,
|
|
4786
|
-
strict: true
|
|
4787
|
-
});
|
|
4788
|
-
const throttledRebuild = throttle(runBuild);
|
|
5191
|
+
const throttledRebuild = pDebounce(runBuild, 250, { before: true });
|
|
4789
5192
|
const taskFileWatcher = watch(
|
|
4790
5193
|
config.triggerDirectories.map((triggerDir) => `${triggerDir}/*.ts`),
|
|
4791
5194
|
{
|
|
4792
5195
|
ignoreInitial: true
|
|
4793
5196
|
}
|
|
4794
5197
|
);
|
|
4795
|
-
taskFileWatcher.on("
|
|
5198
|
+
taskFileWatcher.on("add", async (path6) => {
|
|
4796
5199
|
throttledRebuild().catch((error) => {
|
|
4797
5200
|
logger.error(error);
|
|
4798
5201
|
});
|
|
@@ -4840,8 +5243,11 @@ function WebsocketFactory(apiKey) {
|
|
|
4840
5243
|
}
|
|
4841
5244
|
async function gatherRequiredDependencies2(outputMeta, config) {
|
|
4842
5245
|
const dependencies2 = {};
|
|
5246
|
+
logger.debug("Gathering required dependencies from imports", {
|
|
5247
|
+
imports: outputMeta.imports
|
|
5248
|
+
});
|
|
4843
5249
|
for (const file of outputMeta.imports) {
|
|
4844
|
-
if (file.kind !== "require-call" || !file.external) {
|
|
5250
|
+
if (file.kind !== "require-call" && file.kind !== "dynamic-import" || !file.external) {
|
|
4845
5251
|
continue;
|
|
4846
5252
|
}
|
|
4847
5253
|
const packageName = detectPackageNameFromImportPath(file.path);
|
|
@@ -4884,14 +5290,12 @@ async function gatherRequiredDependencies2(outputMeta, config) {
|
|
|
4884
5290
|
function createDuplicateTaskIdOutputErrorMessage(duplicateTaskIds, taskResources) {
|
|
4885
5291
|
const duplicateTable = duplicateTaskIds.map((id) => {
|
|
4886
5292
|
const tasks = taskResources.filter((task) => task.id === id);
|
|
4887
|
-
return `
|
|
4888
|
-
${tasks.map((task) => `${task.filePath} -> ${task.exportName}`).join("\n")}`;
|
|
4889
|
-
}).join("\n\n");
|
|
4890
|
-
return `Duplicate task ids detected:
|
|
5293
|
+
return `
|
|
4891
5294
|
|
|
4892
|
-
${
|
|
4893
|
-
|
|
4894
|
-
|
|
5295
|
+
${chalkTask(id)} was found in:${tasks.map((task) => `
|
|
5296
|
+
${task.filePath} -> ${task.exportName}`).join("")}`;
|
|
5297
|
+
}).join("");
|
|
5298
|
+
return `Duplicate ${chalkTask("task id")} detected:${duplicateTable}`;
|
|
4895
5299
|
}
|
|
4896
5300
|
function gatherProcessEnv() {
|
|
4897
5301
|
const env = {
|
|
@@ -4918,11 +5322,11 @@ import {
|
|
|
4918
5322
|
flattenAttributes as flattenAttributes3,
|
|
4919
5323
|
recordSpanException as recordSpanException5
|
|
4920
5324
|
} from "@trigger.dev/core/v3";
|
|
4921
|
-
import
|
|
5325
|
+
import chalk6 from "chalk";
|
|
4922
5326
|
import { execa as execa3 } from "execa";
|
|
4923
5327
|
import { applyEdits, modify } from "jsonc-parser";
|
|
4924
5328
|
import { writeFile as writeFile3 } from "node:fs/promises";
|
|
4925
|
-
import { join as join6, relative as
|
|
5329
|
+
import { join as join6, relative as relative4, resolve as resolve3 } from "node:path";
|
|
4926
5330
|
import terminalLink3 from "terminal-link";
|
|
4927
5331
|
import { z as z6 } from "zod";
|
|
4928
5332
|
|
|
@@ -5016,7 +5420,7 @@ function resolveInternalFilePath(filePath) {
|
|
|
5016
5420
|
var InitCommandOptions = CommonCommandOptions.extend({
|
|
5017
5421
|
projectRef: z6.string().optional(),
|
|
5018
5422
|
overrideConfig: z6.boolean().default(false),
|
|
5019
|
-
tag: z6.string().default("
|
|
5423
|
+
tag: z6.string().default("beta"),
|
|
5020
5424
|
skipPackageInstall: z6.boolean().default(false)
|
|
5021
5425
|
});
|
|
5022
5426
|
function configureInitCommand(program2) {
|
|
@@ -5027,7 +5431,7 @@ function configureInitCommand(program2) {
|
|
|
5027
5431
|
).option(
|
|
5028
5432
|
"-t, --tag <package tag>",
|
|
5029
5433
|
"The version of the @trigger.dev/sdk package to install",
|
|
5030
|
-
"
|
|
5434
|
+
"beta"
|
|
5031
5435
|
).option("--skip-package-install", "Skip installing the @trigger.dev/sdk package").option("--override-config", "Override the existing config file if it exists")
|
|
5032
5436
|
).action(async (path6, options) => {
|
|
5033
5437
|
await handleTelemetry(async () => {
|
|
@@ -5101,7 +5505,7 @@ async function _initCommand(dir, options) {
|
|
|
5101
5505
|
log3.success("Successfully initialized project for Trigger.dev v3 \u{1FAE1}");
|
|
5102
5506
|
log3.info("Next steps:");
|
|
5103
5507
|
log3.info(
|
|
5104
|
-
` 1. To start developing, run ${
|
|
5508
|
+
` 1. To start developing, run ${chalk6.green(
|
|
5105
5509
|
`npx trigger.dev@${options.tag} dev`
|
|
5106
5510
|
)} in your project directory`
|
|
5107
5511
|
);
|
|
@@ -5116,7 +5520,7 @@ async function _initCommand(dir, options) {
|
|
|
5116
5520
|
` 4. Need help? Join our ${terminalLink3(
|
|
5117
5521
|
"Discord community",
|
|
5118
5522
|
"https://trigger.dev/discord"
|
|
5119
|
-
)} or email us at ${
|
|
5523
|
+
)} or email us at ${chalk6.cyan("help@trigger.dev")}`
|
|
5120
5524
|
);
|
|
5121
5525
|
outro4(`Project initialized successfully. Happy coding!`);
|
|
5122
5526
|
}
|
|
@@ -5170,7 +5574,7 @@ async function createTriggerDir(dir, options) {
|
|
|
5170
5574
|
outputPath,
|
|
5171
5575
|
replacements: {}
|
|
5172
5576
|
});
|
|
5173
|
-
const relativeOutputPath =
|
|
5577
|
+
const relativeOutputPath = relative4(process.cwd(), outputPath);
|
|
5174
5578
|
log3.step(`Created example file at ${relativeOutputPath}`);
|
|
5175
5579
|
span.end();
|
|
5176
5580
|
return { location, isCustomValue: location !== defaultValue };
|
|
@@ -5324,7 +5728,7 @@ async function writeConfigFile(dir, project, options, triggerDir) {
|
|
|
5324
5728
|
outputPath,
|
|
5325
5729
|
override: options.overrideConfig
|
|
5326
5730
|
});
|
|
5327
|
-
const relativePathToOutput =
|
|
5731
|
+
const relativePathToOutput = relative4(process.cwd(), outputPath);
|
|
5328
5732
|
spnnr.stop(
|
|
5329
5733
|
result.success ? `Config file created at ${relativePathToOutput}` : `Failed to create config file: ${result.error}`
|
|
5330
5734
|
);
|
|
@@ -5406,12 +5810,14 @@ async function selectProject(apiClient2, dashboardUrl, projectRef) {
|
|
|
5406
5810
|
// src/commands/logout.ts
|
|
5407
5811
|
var LogoutCommandOptions = CommonCommandOptions;
|
|
5408
5812
|
function configureLogoutCommand(program2) {
|
|
5409
|
-
return commonOptions(program2.command("logout").description("Logout of Trigger.dev")).action(
|
|
5410
|
-
|
|
5411
|
-
await
|
|
5412
|
-
|
|
5413
|
-
|
|
5414
|
-
|
|
5813
|
+
return commonOptions(program2.command("logout").description("Logout of Trigger.dev")).action(
|
|
5814
|
+
async (options) => {
|
|
5815
|
+
await handleTelemetry(async () => {
|
|
5816
|
+
await printInitialBanner(false);
|
|
5817
|
+
await logoutCommand(options);
|
|
5818
|
+
});
|
|
5819
|
+
}
|
|
5820
|
+
);
|
|
5415
5821
|
}
|
|
5416
5822
|
async function logoutCommand(options) {
|
|
5417
5823
|
return await wrapCommandAction("logoutCommand", LogoutCommandOptions, options, async (opts) => {
|
|
@@ -5421,11 +5827,46 @@ async function logoutCommand(options) {
|
|
|
5421
5827
|
async function logout(options) {
|
|
5422
5828
|
const config = readAuthConfigProfile(options.profile);
|
|
5423
5829
|
if (!config?.accessToken) {
|
|
5424
|
-
logger.info(`You are already logged out [${options.profile
|
|
5830
|
+
logger.info(`You are already logged out [${options.profile}]`);
|
|
5831
|
+
return;
|
|
5832
|
+
}
|
|
5833
|
+
deleteAuthConfigProfile(options.profile);
|
|
5834
|
+
logger.info(`Logged out of Trigger.dev [${options.profile}]`);
|
|
5835
|
+
}
|
|
5836
|
+
|
|
5837
|
+
// src/commands/list-profiles.ts
|
|
5838
|
+
import { log as log4, outro as outro5 } from "@clack/prompts";
|
|
5839
|
+
var ListProfilesOptions = CommonCommandOptions;
|
|
5840
|
+
function configureListProfilesCommand(program2) {
|
|
5841
|
+
return program2.command("list-profiles").description("List all of your CLI profiles").option(
|
|
5842
|
+
"-l, --log-level <level>",
|
|
5843
|
+
"The CLI log level to use (debug, info, log, warn, error, none). This does not effect the log level of your trigger.dev tasks.",
|
|
5844
|
+
"log"
|
|
5845
|
+
).option("--skip-telemetry", "Opt-out of sending telemetry").action(async (options) => {
|
|
5846
|
+
await handleTelemetry(async () => {
|
|
5847
|
+
await printInitialBanner(true);
|
|
5848
|
+
await listProfilesCommand(options);
|
|
5849
|
+
});
|
|
5850
|
+
});
|
|
5851
|
+
}
|
|
5852
|
+
async function listProfilesCommand(options) {
|
|
5853
|
+
return await wrapCommandAction("listProfiles", ListProfilesOptions, options, async (opts) => {
|
|
5854
|
+
return await listProfiles(opts);
|
|
5855
|
+
});
|
|
5856
|
+
}
|
|
5857
|
+
async function listProfiles(options) {
|
|
5858
|
+
const authConfig = readAuthConfigFile();
|
|
5859
|
+
if (!authConfig) {
|
|
5860
|
+
logger.info("No profiles found");
|
|
5425
5861
|
return;
|
|
5426
5862
|
}
|
|
5427
|
-
|
|
5428
|
-
|
|
5863
|
+
const profiles = Object.keys(authConfig);
|
|
5864
|
+
log4.message("Profiles:");
|
|
5865
|
+
for (const profile of profiles) {
|
|
5866
|
+
const profileConfig = authConfig[profile];
|
|
5867
|
+
log4.info(`${profile}${profileConfig?.apiUrl ? ` - ${chalkGrey(profileConfig.apiUrl)}` : ""}`);
|
|
5868
|
+
}
|
|
5869
|
+
outro5("Retrieve account info by running whoami --profile <profile>");
|
|
5429
5870
|
}
|
|
5430
5871
|
|
|
5431
5872
|
// src/cli/index.ts
|
|
@@ -5437,6 +5878,7 @@ configureDevCommand(program);
|
|
|
5437
5878
|
configureDeployCommand(program);
|
|
5438
5879
|
configureWhoamiCommand(program);
|
|
5439
5880
|
configureLogoutCommand(program);
|
|
5881
|
+
configureListProfilesCommand(program);
|
|
5440
5882
|
|
|
5441
5883
|
// src/index.ts
|
|
5442
5884
|
var main = async () => {
|