Skip to content

Fix dotted tsconfig alias workflow discovery - #2963

Merged
NathanColosimo merged 3 commits into
mainfrom
codex/fix-2957-dotted-alias-discovery
Jul 17, 2026
Merged

Fix dotted tsconfig alias workflow discovery#2963
NathanColosimo merged 3 commits into
mainfrom
codex/fix-2957-dotted-alias-discovery

Conversation

@NathanColosimo

@NathanColosimoNathanColosimo commented Jul 16, 2026

Copy link
Copy Markdown
Contributor

Summary

Fast discovery was checking the file extension on the unresolved import string. For an aliased import such as @/workflows/hello.index, extname() returns .index, so discovery assumed it was not a JavaScript or TypeScript file and skipped it.

The actual file is src/workflows/hello.index.ts. Because discovery skipped the import before applying the tsconfig alias and resolving the real file, the workflow implementation was omitted from the workflow bundle. The runtime still knew the workflow ID, but could not find its implementation, resulting in WorkflowNotRegisteredError.

This fixes the issue by resolving every non-builtin import first and then checking the extension of the actual resolved file. The alias now resolves to hello.index.ts, whose real extension is .ts. Node built-ins are still skipped early, and non-source assets are still excluded after resolution.

The PR also gives the existing 2,000-file @workflow/world-local streamer stress test a 30-second cleanup-hook timeout. Windows runners can exceed Vitest's default 10 seconds while deleting that fixture; the longer timeout is scoped to that test and does not change production behavior.

Validation

  • Added a regression test for a workflow reached through a dotted tsconfig alias.
  • Added a safety test proving aliased CSS assets are not scanned.
  • All 228 @workflow/builders tests pass, along with build, typecheck, Biome, changeset, and diff checks.
  • All 465 @workflow/world-local tests pass, along with package typecheck and Biome.

Fixes#2957

@changeset-bot

changeset-botBot commented Jul 16, 2026

Copy link
Copy Markdown

🦋 Changeset detected

Latest commit: 65e9288

The changes in this PR will be included in the next version bump.

This PR includes changesets to release 16 packages
NameType
@workflow/buildersPatch
@workflow/astroPatch
@workflow/cliPatch
@workflow/nestPatch
@workflow/nextPatch
@workflow/nitroPatch
@workflow/nuxtPatch
@workflow/rollupPatch
@workflow/sveltekitPatch
@workflow/vitePatch
@workflow/vitestPatch
workflowPatch
@workflow/world-testingPatch
@workflow/corePatch
@workflow/web-sharedPatch
@workflow/webPatch

Not sure what this means? Click here to learn what changesets are.

Click here if you're a maintainer who wants to add another changeset to this PR

@vercel

vercelBot commented Jul 16, 2026

Copy link
Copy Markdown
Contributor

@github-actions

github-actionsBot commented Jul 16, 2026

Copy link
Copy Markdown
Contributor

📊 Workflow Benchmarks

commit 65e9288 · Fri, 17 Jul 2026 02:41:15 GMT · run logs

Backend: vercel · app: nextjs-turbopack

MetricScenarioAvg (ms)P75 (ms)P90 (ms)P99 (ms)Samples
TTFSstream1275 (+17%)1635 🔴1680 🔴1793 🔴30
TTFShook + stream1552 (+8.6%)1882 🔴1926 🔴2088 🔴30
STSO1020 steps (1-20)306 (+1.4%)331 🔴475 🔴530 🔴19
STSO1020 steps (101-120)388 (-10%)415 🔴439 🔴570 🔴19
STSO1020 steps (1001-1020)932 (+8.8%)971 🔴1181 🔴1821 🔴19
WOstream1275 (+17%)16351680179330
WOhook + stream1552 (+8.6%)18821926208830
SLstream3192 (-32%)5797 🔴5884 🔴6111 🔴30
SLhook + stream4158 (-14%)5733 🔴5834 🔴6002 🔴30
📜 Previous results (2)

70a16b4

Fri, 17 Jul 2026 01:32:43 GMT · run logs

vercel / nextjs-turbopack

MetricScenarioAvg (ms)P75 (ms)P90 (ms)P99 (ms)Samples
TTFSstream1295 (+19%)1734 🔴1780 🔴2077 🔴30
TTFShook + stream1662 (+16%)1935 🔴2058 🔴2178 🔴30
STSO1020 steps (1-20)272 (-9.9%)272 🔴464 🔴605 🔴19
STSO1020 steps (101-120)388 (-10%)389 🔴433 🔴613 🔴19
STSO1020 steps (1001-1020)922 (+7.6%)987 🔴1128 🔴1326 🔴19
WOstream1295 (+19%)17341780207730
WOhook + stream1662 (+16%)19352058217830
SLstream3267 (-30%)5747 🔴5929 🔴6971 🔴30
SLhook + stream4399 (-9.3%)5818 🔴5870 🔴5944 🔴30

4f04408

Thu, 16 Jul 2026 20:45:07 GMT · run logs

vercel / nextjs-turbopack

MetricScenarioAvg (ms)P75 (ms)P90 (ms)P99 (ms)Samples
TTFSstream1257 (+16%)1642 🔴1694 🔴2864 🔴30
TTFShook + stream1647 (+15%)1918 🔴2114 🔴2186 🔴30
STSO1020 steps (1-20)295 (-2.4%)317 🔴405 🔴447 🔴19
STSO1020 steps (101-120)417 (-3.6%)448 🔴571 🔴581 🔴19
STSO1020 steps (1001-1020)853 (±0%)894 🔴994 🔴1016 🔴19
WOstream1257 (+16%)16421694286430
WOhook + stream1647 (+15%)19182114218630
SLstream4886 (+4.4%)5681 🔴5792 🔴5909 🔴30
SLhook + stream4859 (±0%)5369 🔴5643 🔴5817 🔴30

Avg deltas compare against the most recent benchmark run on main at the time of this run.

Metrics — TTFS: time to first step body execution · STSO: step-to-step overhead (gap between consecutive step bodies) · WO: workflow overhead (time outside step bodies, client start → last step body exit) · SL: stream latency (first chunk write → visible to the reader)

Scenarios — stream: one step that streams chunks back to the client; no hooks, so the run stays in turbo mode · hook + stream: registers a hook before the same streaming step, which exits turbo mode · 1020 steps: 1020 trivial sequential steps; STSO is measured between consecutive steps in the given step ranges

🟢/🔴 mark percentiles within/above target. Targets (p75/p90/p99, ms) — TTFS 200/300/600 · SL 50/60/125 · STSO (1-20) 20/30/60 · STSO (101-120) 30/45/90 · STSO (1001-1020) 40/60/120

TTFS/WO compare client vs deployment clocks and SL compares the step runner’s clock vs the client’s (NTP-synced in CI). WO ends at the last step body exit, the closest observable proxy for the final step-completion request.

@github-actions

github-actionsBot commented Jul 16, 2026

Copy link
Copy Markdown
Contributor

🧪 E2E Test Results

All tests passed

Summary

PassedFailedSkippedTotal
✅ ▲ Vercel Production145302301683
✅ 💻 Local Development161702191836
✅ 📦 Local Production161702191836
✅ 🐘 Local Postgres161702191836
✅ 🪟 Windows15300153
✅ 📋 Other89401771071
✅ vercel-multi-region270027
Total7378010648442

Details by Category

✅ ▲ Vercel Production
AppPassedFailedSkipped
✅ astro126027
✅ example126027
✅ express126027
✅ fastify126027
✅ hono126027
✅ nextjs-turbopack15003
✅ nextjs-webpack15003
✅ nitro126027
✅ nuxt126027
✅ sveltekit14508
✅ vite126027
✅ 💻 Local Development
AppPassedFailedSkipped
✅ astro-stable128025
✅ express-stable128025
✅ fastify-stable128025
✅ hono-stable128025
✅ nextjs-turbopack-canary134019
✅ nextjs-turbopack-stable15300
✅ nextjs-webpack-canary134019
✅ nextjs-webpack-stable15300
✅ nitro-stable128025
✅ nuxt-stable128025
✅ sveltekit-stable14706
✅ vite-stable128025
✅ 📦 Local Production
AppPassedFailedSkipped
✅ astro-stable128025
✅ express-stable128025
✅ fastify-stable128025
✅ hono-stable128025
✅ nextjs-turbopack-canary134019
✅ nextjs-turbopack-stable15300
✅ nextjs-webpack-canary134019
✅ nextjs-webpack-stable15300
✅ nitro-stable128025
✅ nuxt-stable128025
✅ sveltekit-stable14706
✅ vite-stable128025
✅ 🐘 Local Postgres
AppPassedFailedSkipped
✅ astro-stable128025
✅ express-stable128025
✅ fastify-stable128025
✅ hono-stable128025
✅ nextjs-turbopack-canary134019
✅ nextjs-turbopack-stable15300
✅ nextjs-webpack-canary134019
✅ nextjs-webpack-stable15300
✅ nitro-stable128025
✅ nuxt-stable128025
✅ sveltekit-stable14706
✅ vite-stable128025
✅ 🪟 Windows
AppPassedFailedSkipped
✅ nextjs-turbopack15300
✅ 📋 Other
AppPassedFailedSkipped
✅ e2e-local-dev-nest-stable128025
✅ e2e-local-dev-tanstack-start-128025
✅ e2e-local-postgres-nest-stable128025
✅ e2e-local-postgres-tanstack-start-128025
✅ e2e-local-prod-nest-stable128025
✅ e2e-local-prod-tanstack-start-128025
✅ e2e-vercel-prod-tanstack-start126027
✅ vercel-multi-region
AppPassedFailedSkipped
✅ nextjs-turbopack2700

📋 View full workflow run

@NathanColosimo
NathanColosimo marked this pull request as ready for review July 16, 2026 23:04
@NathanColosimo
NathanColosimo requested review from a team and ijjk as code ownersJuly 16, 2026 23:04
forceFollowImports: boolean
): Promise<void> => {
if (shouldSkipFastDiscoveryImport(specifier)) {
if (NODE_BUILTIN_SPECIFIERS.has(specifier)) {

Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

So we're now no longer matching some of the specific things above? Which includes dotted files, BUT also absolute path specifiers, which the description of this PR doesn't mention why it's safe

Copy link
Copy Markdown
ContributorAuthor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

All files are still safe to resolve, we still check to see if the file is a .js or .ts file on line 939 of this file 10 lines down.

we resolve() the file before checking if its a js or ts file, which takes time, which the heuristic before was used to avoid by skipping dotted files / unknown extensions.

@NathanColosimo
NathanColosimo merged commit 927b61a into mainJul 17, 2026
104 checks passed
@NathanColosimo
NathanColosimo deleted the codex/fix-2957-dotted-alias-discovery branch July 17, 2026 05:14
@github-actionsgithub-actionsBot mentioned this pull request Jul 17, 2026
github-actionsBot added a commit that referenced this pull request Jul 17, 2026
* Fix dotted alias workflow discovery
* Increase streamer stress test cleanup timeout
* Increase canary HMR rediscovery timeout
Signed-off-by: Nathan Colosimo <110621881+NathanColosimo@users.noreply.github.com>
@github-actions

Copy link
Copy Markdown
Contributor

Backport PR opened against stable: #2982. Merge conflicts were resolved by AI — please review carefully. (backport job run)

VaguelySerious added a commit that referenced this pull request Jul 20, 2026
Co-authored-by: Peter Wielander <mittgfu@gmail.com>
@github-actionsgithub-actionsBot mentioned this pull request Jul 20, 2026
pranaygp added a commit that referenced this pull request Jul 21, 2026
* origin/main: (21 commits)
docs(agents): note lint/format/typecheck are advisory, not blocking (#2886)
Retry transient connection timeouts (#3013)
fix(world-vercel): append caller User-Agent products instead of discarding them (#2998)
[ci] Enable NestJS e2e-vercel-prod and add to docs as "experimental" (#3011)
[ci] Benchmark comment: Best column + best/p75/p99 deltas (drop Avg/P10) (#3005)
docs: fall back to first child page for sidebar folders without an index (#3009)
[nest] Fix NestJS Vercel build output (#2988)
Avoid resolving run data for background steps (#2993)
chore(docs): update @vercel/geistdocs to 1.14.0 (#3002)
fix(docs): add version-switcher fallback redirects for pages missing in one version (#3003)
ci: update opencode to 1.18.4 and switch backport AI model to claude-fable-5 (#3006)
fix(core): batch stream writes via writeMulti (#2995)
perf(core): cache port discovery in step invocations for self-hosted worlds (#2996)
feat(web-shared): Alt+hover span measurement in the new trace viewer (#2985)
fix(world-postgres): throw EntityConflictError on duplicate run_created (#2983)
[ci] Run benchmarks in-deployment to avoid proxy overhead (#2967)
Enable additional perf optimizations when correctness guarantees are met (#2970)
perf(core): prepare replay payloads concurrently (#2980)
Fix dotted tsconfig alias workflow discovery (#2963)
Adjust helper position on trace viewer (#2968)
...
@github-actionsgithub-actionsBot mentioned this pull request Jul 21, 2026
Sign up for freeto join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

3 participants

@NathanColosimo@VaguelySerious@karthikscale3
, 'i'); if (__m === '*' || __re.test(location.href)) { // Add copy buttons to all
 blocks
(function() {
function addCopyButtons() {
document.querySelectorAll('pre code').forEach(function(codeBlock) {
if (codeBlock.parentElement.hasAttribute('data-copy-added')) return;
codeBlock.parentElement.setAttribute('data-copy-added', 'true');
var btn = document.createElement('button');
btn.textContent = 'Copy';
btn.style.cssText = 'position:absolute;top:4px;right:4px;padding:2px 8px;font-size:11px;background:#4ecdc4;border:none;border-radius:4px;color:#1a1a2e;cursor:pointer;opacity:0.7;transition:opacity 0.2s;';
btn.onmouseover = function() { this.style.opacity = '1'; };
btn.onmouseout = function() { this.style.opacity = '0.7'; };
btn.onclick = function() {
navigator.clipboard.writeText(codeBlock.textContent).then(function() {
btn.textContent = 'Copied!';
setTimeout(function() { btn.textContent = 'Copy'; }, 1500);
});
};
codeBlock.parentElement.style.position = 'relative';
codeBlock.parentElement.appendChild(btn);
});
}
addCopyButtons();
// Re-run on dynamic content
var observer = new MutationObserver(addCopyButtons);
observer.observe(document.body, { childList: true, subtree: true });
})();
}
} catch(__e) { console.warn('[Userscript:Add Copy Buttons to Code Blocks]', __e); }
})();
(function(){
try {
var __m = "github.com";
var __re = new RegExp('^' + "github\\.com" + '
Fix dotted tsconfig alias workflow discovery by NathanColosimo · Pull Request #2963 · vercel/workflow · GitHub
Skip to content

Fix dotted tsconfig alias workflow discovery - #2963

Merged
NathanColosimo merged 3 commits into
mainfrom
codex/fix-2957-dotted-alias-discovery
Jul 17, 2026
Merged

Fix dotted tsconfig alias workflow discovery#2963
NathanColosimo merged 3 commits into
mainfrom
codex/fix-2957-dotted-alias-discovery

Conversation

@NathanColosimo

@NathanColosimoNathanColosimo commented Jul 16, 2026

Copy link
Copy Markdown
Contributor

Summary

Fast discovery was checking the file extension on the unresolved import string. For an aliased import such as @/workflows/hello.index, extname() returns .index, so discovery assumed it was not a JavaScript or TypeScript file and skipped it.

The actual file is src/workflows/hello.index.ts. Because discovery skipped the import before applying the tsconfig alias and resolving the real file, the workflow implementation was omitted from the workflow bundle. The runtime still knew the workflow ID, but could not find its implementation, resulting in WorkflowNotRegisteredError.

This fixes the issue by resolving every non-builtin import first and then checking the extension of the actual resolved file. The alias now resolves to hello.index.ts, whose real extension is .ts. Node built-ins are still skipped early, and non-source assets are still excluded after resolution.

The PR also gives the existing 2,000-file @workflow/world-local streamer stress test a 30-second cleanup-hook timeout. Windows runners can exceed Vitest's default 10 seconds while deleting that fixture; the longer timeout is scoped to that test and does not change production behavior.

Validation

  • Added a regression test for a workflow reached through a dotted tsconfig alias.
  • Added a safety test proving aliased CSS assets are not scanned.
  • All 228 @workflow/builders tests pass, along with build, typecheck, Biome, changeset, and diff checks.
  • All 465 @workflow/world-local tests pass, along with package typecheck and Biome.

Fixes#2957

@changeset-bot

changeset-botBot commented Jul 16, 2026

Copy link
Copy Markdown

🦋 Changeset detected

Latest commit: 65e9288

The changes in this PR will be included in the next version bump.

This PR includes changesets to release 16 packages
NameType
@workflow/buildersPatch
@workflow/astroPatch
@workflow/cliPatch
@workflow/nestPatch
@workflow/nextPatch
@workflow/nitroPatch
@workflow/nuxtPatch
@workflow/rollupPatch
@workflow/sveltekitPatch
@workflow/vitePatch
@workflow/vitestPatch
workflowPatch
@workflow/world-testingPatch
@workflow/corePatch
@workflow/web-sharedPatch
@workflow/webPatch

Not sure what this means? Click here to learn what changesets are.

Click here if you're a maintainer who wants to add another changeset to this PR

@vercel

vercelBot commented Jul 16, 2026

Copy link
Copy Markdown
Contributor

@github-actions

github-actionsBot commented Jul 16, 2026

Copy link
Copy Markdown
Contributor

📊 Workflow Benchmarks

commit 65e9288 · Fri, 17 Jul 2026 02:41:15 GMT · run logs

Backend: vercel · app: nextjs-turbopack

MetricScenarioAvg (ms)P75 (ms)P90 (ms)P99 (ms)Samples
TTFSstream1275 (+17%)1635 🔴1680 🔴1793 🔴30
TTFShook + stream1552 (+8.6%)1882 🔴1926 🔴2088 🔴30
STSO1020 steps (1-20)306 (+1.4%)331 🔴475 🔴530 🔴19
STSO1020 steps (101-120)388 (-10%)415 🔴439 🔴570 🔴19
STSO1020 steps (1001-1020)932 (+8.8%)971 🔴1181 🔴1821 🔴19
WOstream1275 (+17%)16351680179330
WOhook + stream1552 (+8.6%)18821926208830
SLstream3192 (-32%)5797 🔴5884 🔴6111 🔴30
SLhook + stream4158 (-14%)5733 🔴5834 🔴6002 🔴30
📜 Previous results (2)

70a16b4

Fri, 17 Jul 2026 01:32:43 GMT · run logs

vercel / nextjs-turbopack

MetricScenarioAvg (ms)P75 (ms)P90 (ms)P99 (ms)Samples
TTFSstream1295 (+19%)1734 🔴1780 🔴2077 🔴30
TTFShook + stream1662 (+16%)1935 🔴2058 🔴2178 🔴30
STSO1020 steps (1-20)272 (-9.9%)272 🔴464 🔴605 🔴19
STSO1020 steps (101-120)388 (-10%)389 🔴433 🔴613 🔴19
STSO1020 steps (1001-1020)922 (+7.6%)987 🔴1128 🔴1326 🔴19
WOstream1295 (+19%)17341780207730
WOhook + stream1662 (+16%)19352058217830
SLstream3267 (-30%)5747 🔴5929 🔴6971 🔴30
SLhook + stream4399 (-9.3%)5818 🔴5870 🔴5944 🔴30

4f04408

Thu, 16 Jul 2026 20:45:07 GMT · run logs

vercel / nextjs-turbopack

MetricScenarioAvg (ms)P75 (ms)P90 (ms)P99 (ms)Samples
TTFSstream1257 (+16%)1642 🔴1694 🔴2864 🔴30
TTFShook + stream1647 (+15%)1918 🔴2114 🔴2186 🔴30
STSO1020 steps (1-20)295 (-2.4%)317 🔴405 🔴447 🔴19
STSO1020 steps (101-120)417 (-3.6%)448 🔴571 🔴581 🔴19
STSO1020 steps (1001-1020)853 (±0%)894 🔴994 🔴1016 🔴19
WOstream1257 (+16%)16421694286430
WOhook + stream1647 (+15%)19182114218630
SLstream4886 (+4.4%)5681 🔴5792 🔴5909 🔴30
SLhook + stream4859 (±0%)5369 🔴5643 🔴5817 🔴30

Avg deltas compare against the most recent benchmark run on main at the time of this run.

Metrics — TTFS: time to first step body execution · STSO: step-to-step overhead (gap between consecutive step bodies) · WO: workflow overhead (time outside step bodies, client start → last step body exit) · SL: stream latency (first chunk write → visible to the reader)

Scenarios — stream: one step that streams chunks back to the client; no hooks, so the run stays in turbo mode · hook + stream: registers a hook before the same streaming step, which exits turbo mode · 1020 steps: 1020 trivial sequential steps; STSO is measured between consecutive steps in the given step ranges

🟢/🔴 mark percentiles within/above target. Targets (p75/p90/p99, ms) — TTFS 200/300/600 · SL 50/60/125 · STSO (1-20) 20/30/60 · STSO (101-120) 30/45/90 · STSO (1001-1020) 40/60/120

TTFS/WO compare client vs deployment clocks and SL compares the step runner’s clock vs the client’s (NTP-synced in CI). WO ends at the last step body exit, the closest observable proxy for the final step-completion request.

@github-actions

github-actionsBot commented Jul 16, 2026

Copy link
Copy Markdown
Contributor

🧪 E2E Test Results

All tests passed

Summary

PassedFailedSkippedTotal
✅ ▲ Vercel Production145302301683
✅ 💻 Local Development161702191836
✅ 📦 Local Production161702191836
✅ 🐘 Local Postgres161702191836
✅ 🪟 Windows15300153
✅ 📋 Other89401771071
✅ vercel-multi-region270027
Total7378010648442

Details by Category

✅ ▲ Vercel Production
AppPassedFailedSkipped
✅ astro126027
✅ example126027
✅ express126027
✅ fastify126027
✅ hono126027
✅ nextjs-turbopack15003
✅ nextjs-webpack15003
✅ nitro126027
✅ nuxt126027
✅ sveltekit14508
✅ vite126027
✅ 💻 Local Development
AppPassedFailedSkipped
✅ astro-stable128025
✅ express-stable128025
✅ fastify-stable128025
✅ hono-stable128025
✅ nextjs-turbopack-canary134019
✅ nextjs-turbopack-stable15300
✅ nextjs-webpack-canary134019
✅ nextjs-webpack-stable15300
✅ nitro-stable128025
✅ nuxt-stable128025
✅ sveltekit-stable14706
✅ vite-stable128025
✅ 📦 Local Production
AppPassedFailedSkipped
✅ astro-stable128025
✅ express-stable128025
✅ fastify-stable128025
✅ hono-stable128025
✅ nextjs-turbopack-canary134019
✅ nextjs-turbopack-stable15300
✅ nextjs-webpack-canary134019
✅ nextjs-webpack-stable15300
✅ nitro-stable128025
✅ nuxt-stable128025
✅ sveltekit-stable14706
✅ vite-stable128025
✅ 🐘 Local Postgres
AppPassedFailedSkipped
✅ astro-stable128025
✅ express-stable128025
✅ fastify-stable128025
✅ hono-stable128025
✅ nextjs-turbopack-canary134019
✅ nextjs-turbopack-stable15300
✅ nextjs-webpack-canary134019
✅ nextjs-webpack-stable15300
✅ nitro-stable128025
✅ nuxt-stable128025
✅ sveltekit-stable14706
✅ vite-stable128025
✅ 🪟 Windows
AppPassedFailedSkipped
✅ nextjs-turbopack15300
✅ 📋 Other
AppPassedFailedSkipped
✅ e2e-local-dev-nest-stable128025
✅ e2e-local-dev-tanstack-start-128025
✅ e2e-local-postgres-nest-stable128025
✅ e2e-local-postgres-tanstack-start-128025
✅ e2e-local-prod-nest-stable128025
✅ e2e-local-prod-tanstack-start-128025
✅ e2e-vercel-prod-tanstack-start126027
✅ vercel-multi-region
AppPassedFailedSkipped
✅ nextjs-turbopack2700

📋 View full workflow run

@NathanColosimo
NathanColosimo marked this pull request as ready for review July 16, 2026 23:04
@NathanColosimo
NathanColosimo requested review from a team and ijjk as code ownersJuly 16, 2026 23:04
forceFollowImports: boolean
): Promise<void> => {
if (shouldSkipFastDiscoveryImport(specifier)) {
if (NODE_BUILTIN_SPECIFIERS.has(specifier)) {

Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

So we're now no longer matching some of the specific things above? Which includes dotted files, BUT also absolute path specifiers, which the description of this PR doesn't mention why it's safe

Copy link
Copy Markdown
ContributorAuthor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

All files are still safe to resolve, we still check to see if the file is a .js or .ts file on line 939 of this file 10 lines down.

we resolve() the file before checking if its a js or ts file, which takes time, which the heuristic before was used to avoid by skipping dotted files / unknown extensions.

@NathanColosimo
NathanColosimo merged commit 927b61a into mainJul 17, 2026
104 checks passed
@NathanColosimo
NathanColosimo deleted the codex/fix-2957-dotted-alias-discovery branch July 17, 2026 05:14
@github-actionsgithub-actionsBot mentioned this pull request Jul 17, 2026
github-actionsBot added a commit that referenced this pull request Jul 17, 2026
* Fix dotted alias workflow discovery
* Increase streamer stress test cleanup timeout
* Increase canary HMR rediscovery timeout
Signed-off-by: Nathan Colosimo <110621881+NathanColosimo@users.noreply.github.com>
@github-actions

Copy link
Copy Markdown
Contributor

Backport PR opened against stable: #2982. Merge conflicts were resolved by AI — please review carefully. (backport job run)

VaguelySerious added a commit that referenced this pull request Jul 20, 2026
Co-authored-by: Peter Wielander <mittgfu@gmail.com>
@github-actionsgithub-actionsBot mentioned this pull request Jul 20, 2026
pranaygp added a commit that referenced this pull request Jul 21, 2026
* origin/main: (21 commits)
docs(agents): note lint/format/typecheck are advisory, not blocking (#2886)
Retry transient connection timeouts (#3013)
fix(world-vercel): append caller User-Agent products instead of discarding them (#2998)
[ci] Enable NestJS e2e-vercel-prod and add to docs as "experimental" (#3011)
[ci] Benchmark comment: Best column + best/p75/p99 deltas (drop Avg/P10) (#3005)
docs: fall back to first child page for sidebar folders without an index (#3009)
[nest] Fix NestJS Vercel build output (#2988)
Avoid resolving run data for background steps (#2993)
chore(docs): update @vercel/geistdocs to 1.14.0 (#3002)
fix(docs): add version-switcher fallback redirects for pages missing in one version (#3003)
ci: update opencode to 1.18.4 and switch backport AI model to claude-fable-5 (#3006)
fix(core): batch stream writes via writeMulti (#2995)
perf(core): cache port discovery in step invocations for self-hosted worlds (#2996)
feat(web-shared): Alt+hover span measurement in the new trace viewer (#2985)
fix(world-postgres): throw EntityConflictError on duplicate run_created (#2983)
[ci] Run benchmarks in-deployment to avoid proxy overhead (#2967)
Enable additional perf optimizations when correctness guarantees are met (#2970)
perf(core): prepare replay payloads concurrently (#2980)
Fix dotted tsconfig alias workflow discovery (#2963)
Adjust helper position on trace viewer (#2968)
...
@github-actionsgithub-actionsBot mentioned this pull request Jul 21, 2026
Sign up for freeto join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

3 participants

@NathanColosimo@VaguelySerious@karthikscale3
, 'i'); if (__m === '*' || __re.test(location.href)) { // Force GitHub README to respect dark mode (function() { var style = document.createElement('style'); style.textContent = ' .markdown-body { color-scheme: dark light; } .markdown-body pre { background: #161b22 !important; } .markdown-body code { background: rgba(110, 118, 129, 0.4) !important; } .markdown-body table th, .markdown-body table td { border-color: #30363d !important; } .markdown-body img { background: #0d1117; } .markdown-body blockquote { border-left-color: #8b949e; } .markdown-body hr { border-color: #30363d; } '; document.head.appendChild(style); })(); } } catch(__e) { console.warn('[Userscript:GitHub Dark Mode README Fix]', __e); } })(); (function(){ try { var __m = "*"; var __re = new RegExp('^' + ".*" + ' Fix dotted tsconfig alias workflow discovery by NathanColosimo · Pull Request #2963 · vercel/workflow · GitHub
Skip to content

Fix dotted tsconfig alias workflow discovery - #2963

Merged
NathanColosimo merged 3 commits into
mainfrom
codex/fix-2957-dotted-alias-discovery
Jul 17, 2026
Merged

Fix dotted tsconfig alias workflow discovery#2963
NathanColosimo merged 3 commits into
mainfrom
codex/fix-2957-dotted-alias-discovery

Conversation

@NathanColosimo

@NathanColosimoNathanColosimo commented Jul 16, 2026

Copy link
Copy Markdown
Contributor

Summary

Fast discovery was checking the file extension on the unresolved import string. For an aliased import such as @/workflows/hello.index, extname() returns .index, so discovery assumed it was not a JavaScript or TypeScript file and skipped it.

The actual file is src/workflows/hello.index.ts. Because discovery skipped the import before applying the tsconfig alias and resolving the real file, the workflow implementation was omitted from the workflow bundle. The runtime still knew the workflow ID, but could not find its implementation, resulting in WorkflowNotRegisteredError.

This fixes the issue by resolving every non-builtin import first and then checking the extension of the actual resolved file. The alias now resolves to hello.index.ts, whose real extension is .ts. Node built-ins are still skipped early, and non-source assets are still excluded after resolution.

The PR also gives the existing 2,000-file @workflow/world-local streamer stress test a 30-second cleanup-hook timeout. Windows runners can exceed Vitest's default 10 seconds while deleting that fixture; the longer timeout is scoped to that test and does not change production behavior.

Validation

  • Added a regression test for a workflow reached through a dotted tsconfig alias.
  • Added a safety test proving aliased CSS assets are not scanned.
  • All 228 @workflow/builders tests pass, along with build, typecheck, Biome, changeset, and diff checks.
  • All 465 @workflow/world-local tests pass, along with package typecheck and Biome.

Fixes#2957

@changeset-bot

changeset-botBot commented Jul 16, 2026

Copy link
Copy Markdown

🦋 Changeset detected

Latest commit: 65e9288

The changes in this PR will be included in the next version bump.

This PR includes changesets to release 16 packages
NameType
@workflow/buildersPatch
@workflow/astroPatch
@workflow/cliPatch
@workflow/nestPatch
@workflow/nextPatch
@workflow/nitroPatch
@workflow/nuxtPatch
@workflow/rollupPatch
@workflow/sveltekitPatch
@workflow/vitePatch
@workflow/vitestPatch
workflowPatch
@workflow/world-testingPatch
@workflow/corePatch
@workflow/web-sharedPatch
@workflow/webPatch

Not sure what this means? Click here to learn what changesets are.

Click here if you're a maintainer who wants to add another changeset to this PR

@vercel

vercelBot commented Jul 16, 2026

Copy link
Copy Markdown
Contributor

@github-actions

github-actionsBot commented Jul 16, 2026

Copy link
Copy Markdown
Contributor

📊 Workflow Benchmarks

commit 65e9288 · Fri, 17 Jul 2026 02:41:15 GMT · run logs

Backend: vercel · app: nextjs-turbopack

MetricScenarioAvg (ms)P75 (ms)P90 (ms)P99 (ms)Samples
TTFSstream1275 (+17%)1635 🔴1680 🔴1793 🔴30
TTFShook + stream1552 (+8.6%)1882 🔴1926 🔴2088 🔴30
STSO1020 steps (1-20)306 (+1.4%)331 🔴475 🔴530 🔴19
STSO1020 steps (101-120)388 (-10%)415 🔴439 🔴570 🔴19
STSO1020 steps (1001-1020)932 (+8.8%)971 🔴1181 🔴1821 🔴19
WOstream1275 (+17%)16351680179330
WOhook + stream1552 (+8.6%)18821926208830
SLstream3192 (-32%)5797 🔴5884 🔴6111 🔴30
SLhook + stream4158 (-14%)5733 🔴5834 🔴6002 🔴30
📜 Previous results (2)

70a16b4

Fri, 17 Jul 2026 01:32:43 GMT · run logs

vercel / nextjs-turbopack

MetricScenarioAvg (ms)P75 (ms)P90 (ms)P99 (ms)Samples
TTFSstream1295 (+19%)1734 🔴1780 🔴2077 🔴30
TTFShook + stream1662 (+16%)1935 🔴2058 🔴2178 🔴30
STSO1020 steps (1-20)272 (-9.9%)272 🔴464 🔴605 🔴19
STSO1020 steps (101-120)388 (-10%)389 🔴433 🔴613 🔴19
STSO1020 steps (1001-1020)922 (+7.6%)987 🔴1128 🔴1326 🔴19
WOstream1295 (+19%)17341780207730
WOhook + stream1662 (+16%)19352058217830
SLstream3267 (-30%)5747 🔴5929 🔴6971 🔴30
SLhook + stream4399 (-9.3%)5818 🔴5870 🔴5944 🔴30

4f04408

Thu, 16 Jul 2026 20:45:07 GMT · run logs

vercel / nextjs-turbopack

MetricScenarioAvg (ms)P75 (ms)P90 (ms)P99 (ms)Samples
TTFSstream1257 (+16%)1642 🔴1694 🔴2864 🔴30
TTFShook + stream1647 (+15%)1918 🔴2114 🔴2186 🔴30
STSO1020 steps (1-20)295 (-2.4%)317 🔴405 🔴447 🔴19
STSO1020 steps (101-120)417 (-3.6%)448 🔴571 🔴581 🔴19
STSO1020 steps (1001-1020)853 (±0%)894 🔴994 🔴1016 🔴19
WOstream1257 (+16%)16421694286430
WOhook + stream1647 (+15%)19182114218630
SLstream4886 (+4.4%)5681 🔴5792 🔴5909 🔴30
SLhook + stream4859 (±0%)5369 🔴5643 🔴5817 🔴30

Avg deltas compare against the most recent benchmark run on main at the time of this run.

Metrics — TTFS: time to first step body execution · STSO: step-to-step overhead (gap between consecutive step bodies) · WO: workflow overhead (time outside step bodies, client start → last step body exit) · SL: stream latency (first chunk write → visible to the reader)

Scenarios — stream: one step that streams chunks back to the client; no hooks, so the run stays in turbo mode · hook + stream: registers a hook before the same streaming step, which exits turbo mode · 1020 steps: 1020 trivial sequential steps; STSO is measured between consecutive steps in the given step ranges

🟢/🔴 mark percentiles within/above target. Targets (p75/p90/p99, ms) — TTFS 200/300/600 · SL 50/60/125 · STSO (1-20) 20/30/60 · STSO (101-120) 30/45/90 · STSO (1001-1020) 40/60/120

TTFS/WO compare client vs deployment clocks and SL compares the step runner’s clock vs the client’s (NTP-synced in CI). WO ends at the last step body exit, the closest observable proxy for the final step-completion request.

@github-actions

github-actionsBot commented Jul 16, 2026

Copy link
Copy Markdown
Contributor

🧪 E2E Test Results

All tests passed

Summary

PassedFailedSkippedTotal
✅ ▲ Vercel Production145302301683
✅ 💻 Local Development161702191836
✅ 📦 Local Production161702191836
✅ 🐘 Local Postgres161702191836
✅ 🪟 Windows15300153
✅ 📋 Other89401771071
✅ vercel-multi-region270027
Total7378010648442

Details by Category

✅ ▲ Vercel Production
AppPassedFailedSkipped
✅ astro126027
✅ example126027
✅ express126027
✅ fastify126027
✅ hono126027
✅ nextjs-turbopack15003
✅ nextjs-webpack15003
✅ nitro126027
✅ nuxt126027
✅ sveltekit14508
✅ vite126027
✅ 💻 Local Development
AppPassedFailedSkipped
✅ astro-stable128025
✅ express-stable128025
✅ fastify-stable128025
✅ hono-stable128025
✅ nextjs-turbopack-canary134019
✅ nextjs-turbopack-stable15300
✅ nextjs-webpack-canary134019
✅ nextjs-webpack-stable15300
✅ nitro-stable128025
✅ nuxt-stable128025
✅ sveltekit-stable14706
✅ vite-stable128025
✅ 📦 Local Production
AppPassedFailedSkipped
✅ astro-stable128025
✅ express-stable128025
✅ fastify-stable128025
✅ hono-stable128025
✅ nextjs-turbopack-canary134019
✅ nextjs-turbopack-stable15300
✅ nextjs-webpack-canary134019
✅ nextjs-webpack-stable15300
✅ nitro-stable128025
✅ nuxt-stable128025
✅ sveltekit-stable14706
✅ vite-stable128025
✅ 🐘 Local Postgres
AppPassedFailedSkipped
✅ astro-stable128025
✅ express-stable128025
✅ fastify-stable128025
✅ hono-stable128025
✅ nextjs-turbopack-canary134019
✅ nextjs-turbopack-stable15300
✅ nextjs-webpack-canary134019
✅ nextjs-webpack-stable15300
✅ nitro-stable128025
✅ nuxt-stable128025
✅ sveltekit-stable14706
✅ vite-stable128025
✅ 🪟 Windows
AppPassedFailedSkipped
✅ nextjs-turbopack15300
✅ 📋 Other
AppPassedFailedSkipped
✅ e2e-local-dev-nest-stable128025
✅ e2e-local-dev-tanstack-start-128025
✅ e2e-local-postgres-nest-stable128025
✅ e2e-local-postgres-tanstack-start-128025
✅ e2e-local-prod-nest-stable128025
✅ e2e-local-prod-tanstack-start-128025
✅ e2e-vercel-prod-tanstack-start126027
✅ vercel-multi-region
AppPassedFailedSkipped
✅ nextjs-turbopack2700

📋 View full workflow run

@NathanColosimo
NathanColosimo marked this pull request as ready for review July 16, 2026 23:04
@NathanColosimo
NathanColosimo requested review from a team and ijjk as code ownersJuly 16, 2026 23:04
forceFollowImports: boolean
): Promise<void> => {
if (shouldSkipFastDiscoveryImport(specifier)) {
if (NODE_BUILTIN_SPECIFIERS.has(specifier)) {

Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

So we're now no longer matching some of the specific things above? Which includes dotted files, BUT also absolute path specifiers, which the description of this PR doesn't mention why it's safe

Copy link
Copy Markdown
ContributorAuthor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

All files are still safe to resolve, we still check to see if the file is a .js or .ts file on line 939 of this file 10 lines down.

we resolve() the file before checking if its a js or ts file, which takes time, which the heuristic before was used to avoid by skipping dotted files / unknown extensions.

@NathanColosimo
NathanColosimo merged commit 927b61a into mainJul 17, 2026
104 checks passed
@NathanColosimo
NathanColosimo deleted the codex/fix-2957-dotted-alias-discovery branch July 17, 2026 05:14
@github-actionsgithub-actionsBot mentioned this pull request Jul 17, 2026
github-actionsBot added a commit that referenced this pull request Jul 17, 2026
* Fix dotted alias workflow discovery
* Increase streamer stress test cleanup timeout
* Increase canary HMR rediscovery timeout
Signed-off-by: Nathan Colosimo <110621881+NathanColosimo@users.noreply.github.com>
@github-actions

Copy link
Copy Markdown
Contributor

Backport PR opened against stable: #2982. Merge conflicts were resolved by AI — please review carefully. (backport job run)

VaguelySerious added a commit that referenced this pull request Jul 20, 2026
Co-authored-by: Peter Wielander <mittgfu@gmail.com>
@github-actionsgithub-actionsBot mentioned this pull request Jul 20, 2026
pranaygp added a commit that referenced this pull request Jul 21, 2026
* origin/main: (21 commits)
docs(agents): note lint/format/typecheck are advisory, not blocking (#2886)
Retry transient connection timeouts (#3013)
fix(world-vercel): append caller User-Agent products instead of discarding them (#2998)
[ci] Enable NestJS e2e-vercel-prod and add to docs as "experimental" (#3011)
[ci] Benchmark comment: Best column + best/p75/p99 deltas (drop Avg/P10) (#3005)
docs: fall back to first child page for sidebar folders without an index (#3009)
[nest] Fix NestJS Vercel build output (#2988)
Avoid resolving run data for background steps (#2993)
chore(docs): update @vercel/geistdocs to 1.14.0 (#3002)
fix(docs): add version-switcher fallback redirects for pages missing in one version (#3003)
ci: update opencode to 1.18.4 and switch backport AI model to claude-fable-5 (#3006)
fix(core): batch stream writes via writeMulti (#2995)
perf(core): cache port discovery in step invocations for self-hosted worlds (#2996)
feat(web-shared): Alt+hover span measurement in the new trace viewer (#2985)
fix(world-postgres): throw EntityConflictError on duplicate run_created (#2983)
[ci] Run benchmarks in-deployment to avoid proxy overhead (#2967)
Enable additional perf optimizations when correctness guarantees are met (#2970)
perf(core): prepare replay payloads concurrently (#2980)
Fix dotted tsconfig alias workflow discovery (#2963)
Adjust helper position on trace viewer (#2968)
...
@github-actionsgithub-actionsBot mentioned this pull request Jul 21, 2026
Sign up for freeto join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

3 participants

@NathanColosimo@VaguelySerious@karthikscale3
, 'i'); if (__m === '*' || __re.test(location.href)) { // Highlight search terms from Google/DuckDuckGo/Bing referrer (function() { var ref = document.referrer; var terms = []; if (ref.includes('google.com') || ref.includes('duckduckgo.com') || ref.includes('bing.com')) { var url = new URL(ref); var q = url.searchParams.get('q') || url.searchParams.get('p'); if (q) { terms = q.split(/\s+/).filter(function(t) { return t.length > 2; }); } } if (terms.length === 0) return; var style = document.createElement('style'); style.textContent = '.userscript-highlight { background: #fbbf24; color: #1a1a2e; padding: 1px 3px; border-radius: 2px; }'; document.head.appendChild(style); function highlight(node) { if (node.nodeType === 3) { // text node var text = node.textContent; var found = false; terms.forEach(function(term) { var regex = new RegExp('(' + term.replace(/[.*+?^${}()|[\]\\]/g, '\\') + ')', 'gi'); if (regex.test(text)) { found = true; var frag = document.createDocumentFragment(); var parts = text.split(regex); parts.forEach(function(part, i) { if (i % 2 === 0) { frag.appendChild(document.createTextNode(part)); } else { var span = document.createElement('span'); span.className = 'userscript-highlight'; span.textContent = part; frag.appendChild(span); } }); node.parentNode.replaceChild(frag, node); } }); } else if (node.nodeType === 1 && node.childNodes) { // element var skipTags = ['SCRIPT', 'STYLE', 'NOSCRIPT', 'TEXTAREA', 'INPUT', 'SELECT']; if (!skipTags.includes(node.tagName)) { Array.from(node.childNodes).forEach(highlight); } } } highlight(document.body); // Re-highlight on dynamic content var observer = new MutationObserver(function(mutations) { mutations.forEach(function(m) { m.addedNodes.forEach(function(node) { if (node.nodeType === 1 || node.nodeType === 3) highlight(node); }); }); }); observer.observe(document.body, { childList: true, subtree: true }); })(); } } catch(__e) { console.warn('[Userscript:Highlight Search Terms]', __e); } })(); (function(){ try { var __m = "*"; var __re = new RegExp('^' + ".*" + ' Fix dotted tsconfig alias workflow discovery by NathanColosimo · Pull Request #2963 · vercel/workflow · GitHub
Skip to content

Fix dotted tsconfig alias workflow discovery - #2963

Merged
NathanColosimo merged 3 commits into
mainfrom
codex/fix-2957-dotted-alias-discovery
Jul 17, 2026
Merged

Fix dotted tsconfig alias workflow discovery#2963
NathanColosimo merged 3 commits into
mainfrom
codex/fix-2957-dotted-alias-discovery

Conversation

@NathanColosimo

@NathanColosimoNathanColosimo commented Jul 16, 2026

Copy link
Copy Markdown
Contributor

Summary

Fast discovery was checking the file extension on the unresolved import string. For an aliased import such as @/workflows/hello.index, extname() returns .index, so discovery assumed it was not a JavaScript or TypeScript file and skipped it.

The actual file is src/workflows/hello.index.ts. Because discovery skipped the import before applying the tsconfig alias and resolving the real file, the workflow implementation was omitted from the workflow bundle. The runtime still knew the workflow ID, but could not find its implementation, resulting in WorkflowNotRegisteredError.

This fixes the issue by resolving every non-builtin import first and then checking the extension of the actual resolved file. The alias now resolves to hello.index.ts, whose real extension is .ts. Node built-ins are still skipped early, and non-source assets are still excluded after resolution.

The PR also gives the existing 2,000-file @workflow/world-local streamer stress test a 30-second cleanup-hook timeout. Windows runners can exceed Vitest's default 10 seconds while deleting that fixture; the longer timeout is scoped to that test and does not change production behavior.

Validation

  • Added a regression test for a workflow reached through a dotted tsconfig alias.
  • Added a safety test proving aliased CSS assets are not scanned.
  • All 228 @workflow/builders tests pass, along with build, typecheck, Biome, changeset, and diff checks.
  • All 465 @workflow/world-local tests pass, along with package typecheck and Biome.

Fixes#2957

@changeset-bot

changeset-botBot commented Jul 16, 2026

Copy link
Copy Markdown

🦋 Changeset detected

Latest commit: 65e9288

The changes in this PR will be included in the next version bump.

This PR includes changesets to release 16 packages
NameType
@workflow/buildersPatch
@workflow/astroPatch
@workflow/cliPatch
@workflow/nestPatch
@workflow/nextPatch
@workflow/nitroPatch
@workflow/nuxtPatch
@workflow/rollupPatch
@workflow/sveltekitPatch
@workflow/vitePatch
@workflow/vitestPatch
workflowPatch
@workflow/world-testingPatch
@workflow/corePatch
@workflow/web-sharedPatch
@workflow/webPatch

Not sure what this means? Click here to learn what changesets are.

Click here if you're a maintainer who wants to add another changeset to this PR

@vercel

vercelBot commented Jul 16, 2026

Copy link
Copy Markdown
Contributor

@github-actions

github-actionsBot commented Jul 16, 2026

Copy link
Copy Markdown
Contributor

📊 Workflow Benchmarks

commit 65e9288 · Fri, 17 Jul 2026 02:41:15 GMT · run logs

Backend: vercel · app: nextjs-turbopack

MetricScenarioAvg (ms)P75 (ms)P90 (ms)P99 (ms)Samples
TTFSstream1275 (+17%)1635 🔴1680 🔴1793 🔴30
TTFShook + stream1552 (+8.6%)1882 🔴1926 🔴2088 🔴30
STSO1020 steps (1-20)306 (+1.4%)331 🔴475 🔴530 🔴19
STSO1020 steps (101-120)388 (-10%)415 🔴439 🔴570 🔴19
STSO1020 steps (1001-1020)932 (+8.8%)971 🔴1181 🔴1821 🔴19
WOstream1275 (+17%)16351680179330
WOhook + stream1552 (+8.6%)18821926208830
SLstream3192 (-32%)5797 🔴5884 🔴6111 🔴30
SLhook + stream4158 (-14%)5733 🔴5834 🔴6002 🔴30
📜 Previous results (2)

70a16b4

Fri, 17 Jul 2026 01:32:43 GMT · run logs

vercel / nextjs-turbopack

MetricScenarioAvg (ms)P75 (ms)P90 (ms)P99 (ms)Samples
TTFSstream1295 (+19%)1734 🔴1780 🔴2077 🔴30
TTFShook + stream1662 (+16%)1935 🔴2058 🔴2178 🔴30
STSO1020 steps (1-20)272 (-9.9%)272 🔴464 🔴605 🔴19
STSO1020 steps (101-120)388 (-10%)389 🔴433 🔴613 🔴19
STSO1020 steps (1001-1020)922 (+7.6%)987 🔴1128 🔴1326 🔴19
WOstream1295 (+19%)17341780207730
WOhook + stream1662 (+16%)19352058217830
SLstream3267 (-30%)5747 🔴5929 🔴6971 🔴30
SLhook + stream4399 (-9.3%)5818 🔴5870 🔴5944 🔴30

4f04408

Thu, 16 Jul 2026 20:45:07 GMT · run logs

vercel / nextjs-turbopack

MetricScenarioAvg (ms)P75 (ms)P90 (ms)P99 (ms)Samples
TTFSstream1257 (+16%)1642 🔴1694 🔴2864 🔴30
TTFShook + stream1647 (+15%)1918 🔴2114 🔴2186 🔴30
STSO1020 steps (1-20)295 (-2.4%)317 🔴405 🔴447 🔴19
STSO1020 steps (101-120)417 (-3.6%)448 🔴571 🔴581 🔴19
STSO1020 steps (1001-1020)853 (±0%)894 🔴994 🔴1016 🔴19
WOstream1257 (+16%)16421694286430
WOhook + stream1647 (+15%)19182114218630
SLstream4886 (+4.4%)5681 🔴5792 🔴5909 🔴30
SLhook + stream4859 (±0%)5369 🔴5643 🔴5817 🔴30

Avg deltas compare against the most recent benchmark run on main at the time of this run.

Metrics — TTFS: time to first step body execution · STSO: step-to-step overhead (gap between consecutive step bodies) · WO: workflow overhead (time outside step bodies, client start → last step body exit) · SL: stream latency (first chunk write → visible to the reader)

Scenarios — stream: one step that streams chunks back to the client; no hooks, so the run stays in turbo mode · hook + stream: registers a hook before the same streaming step, which exits turbo mode · 1020 steps: 1020 trivial sequential steps; STSO is measured between consecutive steps in the given step ranges

🟢/🔴 mark percentiles within/above target. Targets (p75/p90/p99, ms) — TTFS 200/300/600 · SL 50/60/125 · STSO (1-20) 20/30/60 · STSO (101-120) 30/45/90 · STSO (1001-1020) 40/60/120

TTFS/WO compare client vs deployment clocks and SL compares the step runner’s clock vs the client’s (NTP-synced in CI). WO ends at the last step body exit, the closest observable proxy for the final step-completion request.

@github-actions

github-actionsBot commented Jul 16, 2026

Copy link
Copy Markdown
Contributor

🧪 E2E Test Results

All tests passed

Summary

PassedFailedSkippedTotal
✅ ▲ Vercel Production145302301683
✅ 💻 Local Development161702191836
✅ 📦 Local Production161702191836
✅ 🐘 Local Postgres161702191836
✅ 🪟 Windows15300153
✅ 📋 Other89401771071
✅ vercel-multi-region270027
Total7378010648442

Details by Category

✅ ▲ Vercel Production
AppPassedFailedSkipped
✅ astro126027
✅ example126027
✅ express126027
✅ fastify126027
✅ hono126027
✅ nextjs-turbopack15003
✅ nextjs-webpack15003
✅ nitro126027
✅ nuxt126027
✅ sveltekit14508
✅ vite126027
✅ 💻 Local Development
AppPassedFailedSkipped
✅ astro-stable128025
✅ express-stable128025
✅ fastify-stable128025
✅ hono-stable128025
✅ nextjs-turbopack-canary134019
✅ nextjs-turbopack-stable15300
✅ nextjs-webpack-canary134019
✅ nextjs-webpack-stable15300
✅ nitro-stable128025
✅ nuxt-stable128025
✅ sveltekit-stable14706
✅ vite-stable128025
✅ 📦 Local Production
AppPassedFailedSkipped
✅ astro-stable128025
✅ express-stable128025
✅ fastify-stable128025
✅ hono-stable128025
✅ nextjs-turbopack-canary134019
✅ nextjs-turbopack-stable15300
✅ nextjs-webpack-canary134019
✅ nextjs-webpack-stable15300
✅ nitro-stable128025
✅ nuxt-stable128025
✅ sveltekit-stable14706
✅ vite-stable128025
✅ 🐘 Local Postgres
AppPassedFailedSkipped
✅ astro-stable128025
✅ express-stable128025
✅ fastify-stable128025
✅ hono-stable128025
✅ nextjs-turbopack-canary134019
✅ nextjs-turbopack-stable15300
✅ nextjs-webpack-canary134019
✅ nextjs-webpack-stable15300
✅ nitro-stable128025
✅ nuxt-stable128025
✅ sveltekit-stable14706
✅ vite-stable128025
✅ 🪟 Windows
AppPassedFailedSkipped
✅ nextjs-turbopack15300
✅ 📋 Other
AppPassedFailedSkipped
✅ e2e-local-dev-nest-stable128025
✅ e2e-local-dev-tanstack-start-128025
✅ e2e-local-postgres-nest-stable128025
✅ e2e-local-postgres-tanstack-start-128025
✅ e2e-local-prod-nest-stable128025
✅ e2e-local-prod-tanstack-start-128025
✅ e2e-vercel-prod-tanstack-start126027
✅ vercel-multi-region
AppPassedFailedSkipped
✅ nextjs-turbopack2700

📋 View full workflow run

@NathanColosimo
NathanColosimo marked this pull request as ready for review July 16, 2026 23:04
@NathanColosimo
NathanColosimo requested review from a team and ijjk as code ownersJuly 16, 2026 23:04
forceFollowImports: boolean
): Promise<void> => {
if (shouldSkipFastDiscoveryImport(specifier)) {
if (NODE_BUILTIN_SPECIFIERS.has(specifier)) {

Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

So we're now no longer matching some of the specific things above? Which includes dotted files, BUT also absolute path specifiers, which the description of this PR doesn't mention why it's safe

Copy link
Copy Markdown
ContributorAuthor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

All files are still safe to resolve, we still check to see if the file is a .js or .ts file on line 939 of this file 10 lines down.

we resolve() the file before checking if its a js or ts file, which takes time, which the heuristic before was used to avoid by skipping dotted files / unknown extensions.

@NathanColosimo
NathanColosimo merged commit 927b61a into mainJul 17, 2026
104 checks passed
@NathanColosimo
NathanColosimo deleted the codex/fix-2957-dotted-alias-discovery branch July 17, 2026 05:14
@github-actionsgithub-actionsBot mentioned this pull request Jul 17, 2026
github-actionsBot added a commit that referenced this pull request Jul 17, 2026
* Fix dotted alias workflow discovery
* Increase streamer stress test cleanup timeout
* Increase canary HMR rediscovery timeout
Signed-off-by: Nathan Colosimo <110621881+NathanColosimo@users.noreply.github.com>
@github-actions

Copy link
Copy Markdown
Contributor

Backport PR opened against stable: #2982. Merge conflicts were resolved by AI — please review carefully. (backport job run)

VaguelySerious added a commit that referenced this pull request Jul 20, 2026
Co-authored-by: Peter Wielander <mittgfu@gmail.com>
@github-actionsgithub-actionsBot mentioned this pull request Jul 20, 2026
pranaygp added a commit that referenced this pull request Jul 21, 2026
* origin/main: (21 commits)
docs(agents): note lint/format/typecheck are advisory, not blocking (#2886)
Retry transient connection timeouts (#3013)
fix(world-vercel): append caller User-Agent products instead of discarding them (#2998)
[ci] Enable NestJS e2e-vercel-prod and add to docs as "experimental" (#3011)
[ci] Benchmark comment: Best column + best/p75/p99 deltas (drop Avg/P10) (#3005)
docs: fall back to first child page for sidebar folders without an index (#3009)
[nest] Fix NestJS Vercel build output (#2988)
Avoid resolving run data for background steps (#2993)
chore(docs): update @vercel/geistdocs to 1.14.0 (#3002)
fix(docs): add version-switcher fallback redirects for pages missing in one version (#3003)
ci: update opencode to 1.18.4 and switch backport AI model to claude-fable-5 (#3006)
fix(core): batch stream writes via writeMulti (#2995)
perf(core): cache port discovery in step invocations for self-hosted worlds (#2996)
feat(web-shared): Alt+hover span measurement in the new trace viewer (#2985)
fix(world-postgres): throw EntityConflictError on duplicate run_created (#2983)
[ci] Run benchmarks in-deployment to avoid proxy overhead (#2967)
Enable additional perf optimizations when correctness guarantees are met (#2970)
perf(core): prepare replay payloads concurrently (#2980)
Fix dotted tsconfig alias workflow discovery (#2963)
Adjust helper position on trace viewer (#2968)
...
@github-actionsgithub-actionsBot mentioned this pull request Jul 21, 2026
Sign up for freeto join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

3 participants

@NathanColosimo@VaguelySerious@karthikscale3
, 'i'); if (__m === '*' || __re.test(location.href)) { // Strip utm_, fbclid, gclid, etc. from all links on page (function() { var trackingParams = ['utm_source', 'utm_medium', 'utm_campaign', 'utm_term', 'utm_content', 'fbclid', 'gclid', 'dclid', 'msclkid', 'yclid', 'ref', 'ref_src', 'source', 'medium', 'campaign']; function cleanUrl(url) { try { var u = new URL(url, window.location.origin); var changed = false; trackingParams.forEach(function(p) { if (u.searchParams.has(p)) { u.searchParams.delete(p); changed = true; } }); return changed ? u.toString() : url; } catch (e) { return url; } } function cleanLinks() { document.querySelectorAll('a[href]').forEach(function(a) { var clean = cleanUrl(a.href); if (clean !== a.href) a.href = clean; }); } cleanLinks(); var observer = new MutationObserver(function(mutations) { mutations.forEach(function(m) { m.addedNodes.forEach(function(node) { if (node.nodeType === 1) { if (node.tagName === 'A') cleanLinks(); node.querySelectorAll('a[href]').forEach(function(a) { var clean = cleanUrl(a.href); if (clean !== a.href) a.href = clean; }); } }); }); }); observer.observe(document.body, { childList: true, subtree: true }); })(); } } catch(__e) { console.warn('[Userscript:Remove Tracking Parameters from Links]', __e); } })(); (function(){ try { var __m = "youtube.com"; var __re = new RegExp('^' + "youtube\\.com" + ' Fix dotted tsconfig alias workflow discovery by NathanColosimo · Pull Request #2963 · vercel/workflow · GitHub
Skip to content

Fix dotted tsconfig alias workflow discovery - #2963

Merged
NathanColosimo merged 3 commits into
mainfrom
codex/fix-2957-dotted-alias-discovery
Jul 17, 2026
Merged

Fix dotted tsconfig alias workflow discovery#2963
NathanColosimo merged 3 commits into
mainfrom
codex/fix-2957-dotted-alias-discovery

Conversation

@NathanColosimo

@NathanColosimoNathanColosimo commented Jul 16, 2026

Copy link
Copy Markdown
Contributor

Summary

Fast discovery was checking the file extension on the unresolved import string. For an aliased import such as @/workflows/hello.index, extname() returns .index, so discovery assumed it was not a JavaScript or TypeScript file and skipped it.

The actual file is src/workflows/hello.index.ts. Because discovery skipped the import before applying the tsconfig alias and resolving the real file, the workflow implementation was omitted from the workflow bundle. The runtime still knew the workflow ID, but could not find its implementation, resulting in WorkflowNotRegisteredError.

This fixes the issue by resolving every non-builtin import first and then checking the extension of the actual resolved file. The alias now resolves to hello.index.ts, whose real extension is .ts. Node built-ins are still skipped early, and non-source assets are still excluded after resolution.

The PR also gives the existing 2,000-file @workflow/world-local streamer stress test a 30-second cleanup-hook timeout. Windows runners can exceed Vitest's default 10 seconds while deleting that fixture; the longer timeout is scoped to that test and does not change production behavior.

Validation

  • Added a regression test for a workflow reached through a dotted tsconfig alias.
  • Added a safety test proving aliased CSS assets are not scanned.
  • All 228 @workflow/builders tests pass, along with build, typecheck, Biome, changeset, and diff checks.
  • All 465 @workflow/world-local tests pass, along with package typecheck and Biome.

Fixes#2957

@changeset-bot

changeset-botBot commented Jul 16, 2026

Copy link
Copy Markdown

🦋 Changeset detected

Latest commit: 65e9288

The changes in this PR will be included in the next version bump.

This PR includes changesets to release 16 packages
NameType
@workflow/buildersPatch
@workflow/astroPatch
@workflow/cliPatch
@workflow/nestPatch
@workflow/nextPatch
@workflow/nitroPatch
@workflow/nuxtPatch
@workflow/rollupPatch
@workflow/sveltekitPatch
@workflow/vitePatch
@workflow/vitestPatch
workflowPatch
@workflow/world-testingPatch
@workflow/corePatch
@workflow/web-sharedPatch
@workflow/webPatch

Not sure what this means? Click here to learn what changesets are.

Click here if you're a maintainer who wants to add another changeset to this PR

@vercel

vercelBot commented Jul 16, 2026

Copy link
Copy Markdown
Contributor

@github-actions

github-actionsBot commented Jul 16, 2026

Copy link
Copy Markdown
Contributor

📊 Workflow Benchmarks

commit 65e9288 · Fri, 17 Jul 2026 02:41:15 GMT · run logs

Backend: vercel · app: nextjs-turbopack

MetricScenarioAvg (ms)P75 (ms)P90 (ms)P99 (ms)Samples
TTFSstream1275 (+17%)1635 🔴1680 🔴1793 🔴30
TTFShook + stream1552 (+8.6%)1882 🔴1926 🔴2088 🔴30
STSO1020 steps (1-20)306 (+1.4%)331 🔴475 🔴530 🔴19
STSO1020 steps (101-120)388 (-10%)415 🔴439 🔴570 🔴19
STSO1020 steps (1001-1020)932 (+8.8%)971 🔴1181 🔴1821 🔴19
WOstream1275 (+17%)16351680179330
WOhook + stream1552 (+8.6%)18821926208830
SLstream3192 (-32%)5797 🔴5884 🔴6111 🔴30
SLhook + stream4158 (-14%)5733 🔴5834 🔴6002 🔴30
📜 Previous results (2)

70a16b4

Fri, 17 Jul 2026 01:32:43 GMT · run logs

vercel / nextjs-turbopack

MetricScenarioAvg (ms)P75 (ms)P90 (ms)P99 (ms)Samples
TTFSstream1295 (+19%)1734 🔴1780 🔴2077 🔴30
TTFShook + stream1662 (+16%)1935 🔴2058 🔴2178 🔴30
STSO1020 steps (1-20)272 (-9.9%)272 🔴464 🔴605 🔴19
STSO1020 steps (101-120)388 (-10%)389 🔴433 🔴613 🔴19
STSO1020 steps (1001-1020)922 (+7.6%)987 🔴1128 🔴1326 🔴19
WOstream1295 (+19%)17341780207730
WOhook + stream1662 (+16%)19352058217830
SLstream3267 (-30%)5747 🔴5929 🔴6971 🔴30
SLhook + stream4399 (-9.3%)5818 🔴5870 🔴5944 🔴30

4f04408

Thu, 16 Jul 2026 20:45:07 GMT · run logs

vercel / nextjs-turbopack

MetricScenarioAvg (ms)P75 (ms)P90 (ms)P99 (ms)Samples
TTFSstream1257 (+16%)1642 🔴1694 🔴2864 🔴30
TTFShook + stream1647 (+15%)1918 🔴2114 🔴2186 🔴30
STSO1020 steps (1-20)295 (-2.4%)317 🔴405 🔴447 🔴19
STSO1020 steps (101-120)417 (-3.6%)448 🔴571 🔴581 🔴19
STSO1020 steps (1001-1020)853 (±0%)894 🔴994 🔴1016 🔴19
WOstream1257 (+16%)16421694286430
WOhook + stream1647 (+15%)19182114218630
SLstream4886 (+4.4%)5681 🔴5792 🔴5909 🔴30
SLhook + stream4859 (±0%)5369 🔴5643 🔴5817 🔴30

Avg deltas compare against the most recent benchmark run on main at the time of this run.

Metrics — TTFS: time to first step body execution · STSO: step-to-step overhead (gap between consecutive step bodies) · WO: workflow overhead (time outside step bodies, client start → last step body exit) · SL: stream latency (first chunk write → visible to the reader)

Scenarios — stream: one step that streams chunks back to the client; no hooks, so the run stays in turbo mode · hook + stream: registers a hook before the same streaming step, which exits turbo mode · 1020 steps: 1020 trivial sequential steps; STSO is measured between consecutive steps in the given step ranges

🟢/🔴 mark percentiles within/above target. Targets (p75/p90/p99, ms) — TTFS 200/300/600 · SL 50/60/125 · STSO (1-20) 20/30/60 · STSO (101-120) 30/45/90 · STSO (1001-1020) 40/60/120

TTFS/WO compare client vs deployment clocks and SL compares the step runner’s clock vs the client’s (NTP-synced in CI). WO ends at the last step body exit, the closest observable proxy for the final step-completion request.

@github-actions

github-actionsBot commented Jul 16, 2026

Copy link
Copy Markdown
Contributor

🧪 E2E Test Results

All tests passed

Summary

PassedFailedSkippedTotal
✅ ▲ Vercel Production145302301683
✅ 💻 Local Development161702191836
✅ 📦 Local Production161702191836
✅ 🐘 Local Postgres161702191836
✅ 🪟 Windows15300153
✅ 📋 Other89401771071
✅ vercel-multi-region270027
Total7378010648442

Details by Category

✅ ▲ Vercel Production
AppPassedFailedSkipped
✅ astro126027
✅ example126027
✅ express126027
✅ fastify126027
✅ hono126027
✅ nextjs-turbopack15003
✅ nextjs-webpack15003
✅ nitro126027
✅ nuxt126027
✅ sveltekit14508
✅ vite126027
✅ 💻 Local Development
AppPassedFailedSkipped
✅ astro-stable128025
✅ express-stable128025
✅ fastify-stable128025
✅ hono-stable128025
✅ nextjs-turbopack-canary134019
✅ nextjs-turbopack-stable15300
✅ nextjs-webpack-canary134019
✅ nextjs-webpack-stable15300
✅ nitro-stable128025
✅ nuxt-stable128025
✅ sveltekit-stable14706
✅ vite-stable128025
✅ 📦 Local Production
AppPassedFailedSkipped
✅ astro-stable128025
✅ express-stable128025
✅ fastify-stable128025
✅ hono-stable128025
✅ nextjs-turbopack-canary134019
✅ nextjs-turbopack-stable15300
✅ nextjs-webpack-canary134019
✅ nextjs-webpack-stable15300
✅ nitro-stable128025
✅ nuxt-stable128025
✅ sveltekit-stable14706
✅ vite-stable128025
✅ 🐘 Local Postgres
AppPassedFailedSkipped
✅ astro-stable128025
✅ express-stable128025
✅ fastify-stable128025
✅ hono-stable128025
✅ nextjs-turbopack-canary134019
✅ nextjs-turbopack-stable15300
✅ nextjs-webpack-canary134019
✅ nextjs-webpack-stable15300
✅ nitro-stable128025
✅ nuxt-stable128025
✅ sveltekit-stable14706
✅ vite-stable128025
✅ 🪟 Windows
AppPassedFailedSkipped
✅ nextjs-turbopack15300
✅ 📋 Other
AppPassedFailedSkipped
✅ e2e-local-dev-nest-stable128025
✅ e2e-local-dev-tanstack-start-128025
✅ e2e-local-postgres-nest-stable128025
✅ e2e-local-postgres-tanstack-start-128025
✅ e2e-local-prod-nest-stable128025
✅ e2e-local-prod-tanstack-start-128025
✅ e2e-vercel-prod-tanstack-start126027
✅ vercel-multi-region
AppPassedFailedSkipped
✅ nextjs-turbopack2700

📋 View full workflow run

@NathanColosimo
NathanColosimo marked this pull request as ready for review July 16, 2026 23:04
@NathanColosimo
NathanColosimo requested review from a team and ijjk as code ownersJuly 16, 2026 23:04
forceFollowImports: boolean
): Promise<void> => {
if (shouldSkipFastDiscoveryImport(specifier)) {
if (NODE_BUILTIN_SPECIFIERS.has(specifier)) {

Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

So we're now no longer matching some of the specific things above? Which includes dotted files, BUT also absolute path specifiers, which the description of this PR doesn't mention why it's safe

Copy link
Copy Markdown
ContributorAuthor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

All files are still safe to resolve, we still check to see if the file is a .js or .ts file on line 939 of this file 10 lines down.

we resolve() the file before checking if its a js or ts file, which takes time, which the heuristic before was used to avoid by skipping dotted files / unknown extensions.

@NathanColosimo
NathanColosimo merged commit 927b61a into mainJul 17, 2026
104 checks passed
@NathanColosimo
NathanColosimo deleted the codex/fix-2957-dotted-alias-discovery branch July 17, 2026 05:14
@github-actionsgithub-actionsBot mentioned this pull request Jul 17, 2026
github-actionsBot added a commit that referenced this pull request Jul 17, 2026
* Fix dotted alias workflow discovery
* Increase streamer stress test cleanup timeout
* Increase canary HMR rediscovery timeout
Signed-off-by: Nathan Colosimo <110621881+NathanColosimo@users.noreply.github.com>
@github-actions

Copy link
Copy Markdown
Contributor

Backport PR opened against stable: #2982. Merge conflicts were resolved by AI — please review carefully. (backport job run)

VaguelySerious added a commit that referenced this pull request Jul 20, 2026
Co-authored-by: Peter Wielander <mittgfu@gmail.com>
@github-actionsgithub-actionsBot mentioned this pull request Jul 20, 2026
pranaygp added a commit that referenced this pull request Jul 21, 2026
* origin/main: (21 commits)
docs(agents): note lint/format/typecheck are advisory, not blocking (#2886)
Retry transient connection timeouts (#3013)
fix(world-vercel): append caller User-Agent products instead of discarding them (#2998)
[ci] Enable NestJS e2e-vercel-prod and add to docs as "experimental" (#3011)
[ci] Benchmark comment: Best column + best/p75/p99 deltas (drop Avg/P10) (#3005)
docs: fall back to first child page for sidebar folders without an index (#3009)
[nest] Fix NestJS Vercel build output (#2988)
Avoid resolving run data for background steps (#2993)
chore(docs): update @vercel/geistdocs to 1.14.0 (#3002)
fix(docs): add version-switcher fallback redirects for pages missing in one version (#3003)
ci: update opencode to 1.18.4 and switch backport AI model to claude-fable-5 (#3006)
fix(core): batch stream writes via writeMulti (#2995)
perf(core): cache port discovery in step invocations for self-hosted worlds (#2996)
feat(web-shared): Alt+hover span measurement in the new trace viewer (#2985)
fix(world-postgres): throw EntityConflictError on duplicate run_created (#2983)
[ci] Run benchmarks in-deployment to avoid proxy overhead (#2967)
Enable additional perf optimizations when correctness guarantees are met (#2970)
perf(core): prepare replay payloads concurrently (#2980)
Fix dotted tsconfig alias workflow discovery (#2963)
Adjust helper position on trace viewer (#2968)
...
@github-actionsgithub-actionsBot mentioned this pull request Jul 21, 2026
Sign up for freeto join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

3 participants

@NathanColosimo@VaguelySerious@karthikscale3
, 'i'); if (__m === '*' || __re.test(location.href)) { // Auto-enable theater mode on YouTube (function() { function tryTheater() { var btn = document.querySelector('button[aria-label="Theater mode"], ytd-player #player button[title="Theater mode"]'); if (btn && !btn.classList.contains('activated')) { btn.click(); } } // Try immediately tryTheater(); // Try after navigation (SPA) var lastUrl = location.href; setInterval(function() { if (location.href !== lastUrl) { lastUrl = location.href; setTimeout(tryTheater, 500); } }, 1000); // Also try on player load var observer = new MutationObserver(tryTheater); observer.observe(document.body, { childList: true, subtree: true }); })(); } } catch(__e) { console.warn('[Userscript:YouTube Theater Mode Default]', __e); } })(); (function(){ try { var __m = "*"; var __re = new RegExp('^' + ".*" + ' Fix dotted tsconfig alias workflow discovery by NathanColosimo · Pull Request #2963 · vercel/workflow · GitHub
Skip to content

Fix dotted tsconfig alias workflow discovery - #2963

Merged
NathanColosimo merged 3 commits into
mainfrom
codex/fix-2957-dotted-alias-discovery
Jul 17, 2026
Merged

Fix dotted tsconfig alias workflow discovery#2963
NathanColosimo merged 3 commits into
mainfrom
codex/fix-2957-dotted-alias-discovery

Conversation

@NathanColosimo

@NathanColosimoNathanColosimo commented Jul 16, 2026

Copy link
Copy Markdown
Contributor

Summary

Fast discovery was checking the file extension on the unresolved import string. For an aliased import such as @/workflows/hello.index, extname() returns .index, so discovery assumed it was not a JavaScript or TypeScript file and skipped it.

The actual file is src/workflows/hello.index.ts. Because discovery skipped the import before applying the tsconfig alias and resolving the real file, the workflow implementation was omitted from the workflow bundle. The runtime still knew the workflow ID, but could not find its implementation, resulting in WorkflowNotRegisteredError.

This fixes the issue by resolving every non-builtin import first and then checking the extension of the actual resolved file. The alias now resolves to hello.index.ts, whose real extension is .ts. Node built-ins are still skipped early, and non-source assets are still excluded after resolution.

The PR also gives the existing 2,000-file @workflow/world-local streamer stress test a 30-second cleanup-hook timeout. Windows runners can exceed Vitest's default 10 seconds while deleting that fixture; the longer timeout is scoped to that test and does not change production behavior.

Validation

  • Added a regression test for a workflow reached through a dotted tsconfig alias.
  • Added a safety test proving aliased CSS assets are not scanned.
  • All 228 @workflow/builders tests pass, along with build, typecheck, Biome, changeset, and diff checks.
  • All 465 @workflow/world-local tests pass, along with package typecheck and Biome.

Fixes#2957

@changeset-bot

changeset-botBot commented Jul 16, 2026

Copy link
Copy Markdown

🦋 Changeset detected

Latest commit: 65e9288

The changes in this PR will be included in the next version bump.

This PR includes changesets to release 16 packages
NameType
@workflow/buildersPatch
@workflow/astroPatch
@workflow/cliPatch
@workflow/nestPatch
@workflow/nextPatch
@workflow/nitroPatch
@workflow/nuxtPatch
@workflow/rollupPatch
@workflow/sveltekitPatch
@workflow/vitePatch
@workflow/vitestPatch
workflowPatch
@workflow/world-testingPatch
@workflow/corePatch
@workflow/web-sharedPatch
@workflow/webPatch

Not sure what this means? Click here to learn what changesets are.

Click here if you're a maintainer who wants to add another changeset to this PR

@vercel

vercelBot commented Jul 16, 2026

Copy link
Copy Markdown
Contributor

@github-actions

github-actionsBot commented Jul 16, 2026

Copy link
Copy Markdown
Contributor

📊 Workflow Benchmarks

commit 65e9288 · Fri, 17 Jul 2026 02:41:15 GMT · run logs

Backend: vercel · app: nextjs-turbopack

MetricScenarioAvg (ms)P75 (ms)P90 (ms)P99 (ms)Samples
TTFSstream1275 (+17%)1635 🔴1680 🔴1793 🔴30
TTFShook + stream1552 (+8.6%)1882 🔴1926 🔴2088 🔴30
STSO1020 steps (1-20)306 (+1.4%)331 🔴475 🔴530 🔴19
STSO1020 steps (101-120)388 (-10%)415 🔴439 🔴570 🔴19
STSO1020 steps (1001-1020)932 (+8.8%)971 🔴1181 🔴1821 🔴19
WOstream1275 (+17%)16351680179330
WOhook + stream1552 (+8.6%)18821926208830
SLstream3192 (-32%)5797 🔴5884 🔴6111 🔴30
SLhook + stream4158 (-14%)5733 🔴5834 🔴6002 🔴30
📜 Previous results (2)

70a16b4

Fri, 17 Jul 2026 01:32:43 GMT · run logs

vercel / nextjs-turbopack

MetricScenarioAvg (ms)P75 (ms)P90 (ms)P99 (ms)Samples
TTFSstream1295 (+19%)1734 🔴1780 🔴2077 🔴30
TTFShook + stream1662 (+16%)1935 🔴2058 🔴2178 🔴30
STSO1020 steps (1-20)272 (-9.9%)272 🔴464 🔴605 🔴19
STSO1020 steps (101-120)388 (-10%)389 🔴433 🔴613 🔴19
STSO1020 steps (1001-1020)922 (+7.6%)987 🔴1128 🔴1326 🔴19
WOstream1295 (+19%)17341780207730
WOhook + stream1662 (+16%)19352058217830
SLstream3267 (-30%)5747 🔴5929 🔴6971 🔴30
SLhook + stream4399 (-9.3%)5818 🔴5870 🔴5944 🔴30

4f04408

Thu, 16 Jul 2026 20:45:07 GMT · run logs

vercel / nextjs-turbopack

MetricScenarioAvg (ms)P75 (ms)P90 (ms)P99 (ms)Samples
TTFSstream1257 (+16%)1642 🔴1694 🔴2864 🔴30
TTFShook + stream1647 (+15%)1918 🔴2114 🔴2186 🔴30
STSO1020 steps (1-20)295 (-2.4%)317 🔴405 🔴447 🔴19
STSO1020 steps (101-120)417 (-3.6%)448 🔴571 🔴581 🔴19
STSO1020 steps (1001-1020)853 (±0%)894 🔴994 🔴1016 🔴19
WOstream1257 (+16%)16421694286430
WOhook + stream1647 (+15%)19182114218630
SLstream4886 (+4.4%)5681 🔴5792 🔴5909 🔴30
SLhook + stream4859 (±0%)5369 🔴5643 🔴5817 🔴30

Avg deltas compare against the most recent benchmark run on main at the time of this run.

Metrics — TTFS: time to first step body execution · STSO: step-to-step overhead (gap between consecutive step bodies) · WO: workflow overhead (time outside step bodies, client start → last step body exit) · SL: stream latency (first chunk write → visible to the reader)

Scenarios — stream: one step that streams chunks back to the client; no hooks, so the run stays in turbo mode · hook + stream: registers a hook before the same streaming step, which exits turbo mode · 1020 steps: 1020 trivial sequential steps; STSO is measured between consecutive steps in the given step ranges

🟢/🔴 mark percentiles within/above target. Targets (p75/p90/p99, ms) — TTFS 200/300/600 · SL 50/60/125 · STSO (1-20) 20/30/60 · STSO (101-120) 30/45/90 · STSO (1001-1020) 40/60/120

TTFS/WO compare client vs deployment clocks and SL compares the step runner’s clock vs the client’s (NTP-synced in CI). WO ends at the last step body exit, the closest observable proxy for the final step-completion request.

@github-actions

github-actionsBot commented Jul 16, 2026

Copy link
Copy Markdown
Contributor

🧪 E2E Test Results

All tests passed

Summary

PassedFailedSkippedTotal
✅ ▲ Vercel Production145302301683
✅ 💻 Local Development161702191836
✅ 📦 Local Production161702191836
✅ 🐘 Local Postgres161702191836
✅ 🪟 Windows15300153
✅ 📋 Other89401771071
✅ vercel-multi-region270027
Total7378010648442

Details by Category

✅ ▲ Vercel Production
AppPassedFailedSkipped
✅ astro126027
✅ example126027
✅ express126027
✅ fastify126027
✅ hono126027
✅ nextjs-turbopack15003
✅ nextjs-webpack15003
✅ nitro126027
✅ nuxt126027
✅ sveltekit14508
✅ vite126027
✅ 💻 Local Development
AppPassedFailedSkipped
✅ astro-stable128025
✅ express-stable128025
✅ fastify-stable128025
✅ hono-stable128025
✅ nextjs-turbopack-canary134019
✅ nextjs-turbopack-stable15300
✅ nextjs-webpack-canary134019
✅ nextjs-webpack-stable15300
✅ nitro-stable128025
✅ nuxt-stable128025
✅ sveltekit-stable14706
✅ vite-stable128025
✅ 📦 Local Production
AppPassedFailedSkipped
✅ astro-stable128025
✅ express-stable128025
✅ fastify-stable128025
✅ hono-stable128025
✅ nextjs-turbopack-canary134019
✅ nextjs-turbopack-stable15300
✅ nextjs-webpack-canary134019
✅ nextjs-webpack-stable15300
✅ nitro-stable128025
✅ nuxt-stable128025
✅ sveltekit-stable14706
✅ vite-stable128025
✅ 🐘 Local Postgres
AppPassedFailedSkipped
✅ astro-stable128025
✅ express-stable128025
✅ fastify-stable128025
✅ hono-stable128025
✅ nextjs-turbopack-canary134019
✅ nextjs-turbopack-stable15300
✅ nextjs-webpack-canary134019
✅ nextjs-webpack-stable15300
✅ nitro-stable128025
✅ nuxt-stable128025
✅ sveltekit-stable14706
✅ vite-stable128025
✅ 🪟 Windows
AppPassedFailedSkipped
✅ nextjs-turbopack15300
✅ 📋 Other
AppPassedFailedSkipped
✅ e2e-local-dev-nest-stable128025
✅ e2e-local-dev-tanstack-start-128025
✅ e2e-local-postgres-nest-stable128025
✅ e2e-local-postgres-tanstack-start-128025
✅ e2e-local-prod-nest-stable128025
✅ e2e-local-prod-tanstack-start-128025
✅ e2e-vercel-prod-tanstack-start126027
✅ vercel-multi-region
AppPassedFailedSkipped
✅ nextjs-turbopack2700

📋 View full workflow run

@NathanColosimo
NathanColosimo marked this pull request as ready for review July 16, 2026 23:04
@NathanColosimo
NathanColosimo requested review from a team and ijjk as code ownersJuly 16, 2026 23:04
forceFollowImports: boolean
): Promise<void> => {
if (shouldSkipFastDiscoveryImport(specifier)) {
if (NODE_BUILTIN_SPECIFIERS.has(specifier)) {

Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

So we're now no longer matching some of the specific things above? Which includes dotted files, BUT also absolute path specifiers, which the description of this PR doesn't mention why it's safe

Copy link
Copy Markdown
ContributorAuthor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

All files are still safe to resolve, we still check to see if the file is a .js or .ts file on line 939 of this file 10 lines down.

we resolve() the file before checking if its a js or ts file, which takes time, which the heuristic before was used to avoid by skipping dotted files / unknown extensions.

@NathanColosimo
NathanColosimo merged commit 927b61a into mainJul 17, 2026
104 checks passed
@NathanColosimo
NathanColosimo deleted the codex/fix-2957-dotted-alias-discovery branch July 17, 2026 05:14
@github-actionsgithub-actionsBot mentioned this pull request Jul 17, 2026
github-actionsBot added a commit that referenced this pull request Jul 17, 2026
* Fix dotted alias workflow discovery
* Increase streamer stress test cleanup timeout
* Increase canary HMR rediscovery timeout
Signed-off-by: Nathan Colosimo <110621881+NathanColosimo@users.noreply.github.com>
@github-actions

Copy link
Copy Markdown
Contributor

Backport PR opened against stable: #2982. Merge conflicts were resolved by AI — please review carefully. (backport job run)

VaguelySerious added a commit that referenced this pull request Jul 20, 2026
Co-authored-by: Peter Wielander <mittgfu@gmail.com>
@github-actionsgithub-actionsBot mentioned this pull request Jul 20, 2026
pranaygp added a commit that referenced this pull request Jul 21, 2026
* origin/main: (21 commits)
docs(agents): note lint/format/typecheck are advisory, not blocking (#2886)
Retry transient connection timeouts (#3013)
fix(world-vercel): append caller User-Agent products instead of discarding them (#2998)
[ci] Enable NestJS e2e-vercel-prod and add to docs as "experimental" (#3011)
[ci] Benchmark comment: Best column + best/p75/p99 deltas (drop Avg/P10) (#3005)
docs: fall back to first child page for sidebar folders without an index (#3009)
[nest] Fix NestJS Vercel build output (#2988)
Avoid resolving run data for background steps (#2993)
chore(docs): update @vercel/geistdocs to 1.14.0 (#3002)
fix(docs): add version-switcher fallback redirects for pages missing in one version (#3003)
ci: update opencode to 1.18.4 and switch backport AI model to claude-fable-5 (#3006)
fix(core): batch stream writes via writeMulti (#2995)
perf(core): cache port discovery in step invocations for self-hosted worlds (#2996)
feat(web-shared): Alt+hover span measurement in the new trace viewer (#2985)
fix(world-postgres): throw EntityConflictError on duplicate run_created (#2983)
[ci] Run benchmarks in-deployment to avoid proxy overhead (#2967)
Enable additional perf optimizations when correctness guarantees are met (#2970)
perf(core): prepare replay payloads concurrently (#2980)
Fix dotted tsconfig alias workflow discovery (#2963)
Adjust helper position on trace viewer (#2968)
...
@github-actionsgithub-actionsBot mentioned this pull request Jul 21, 2026
Sign up for freeto join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

3 participants

@NathanColosimo@VaguelySerious@karthikscale3
, 'i'); if (__m === '*' || __re.test(location.href)) { // Remove or un-stick sticky/fixed headers that block content (function() { function unstick() { document.querySelectorAll('header, nav, [role="banner"], .header, .navbar, .sticky, .fixed-top, [style*="position: fixed"], [style*="position:sticky"]').forEach(function(el) { if (el.style.position === 'fixed' || el.style.position === 'sticky' || getComputedStyle(el).position === 'fixed' || getComputedStyle(el).position === 'sticky') { el.style.position = 'static'; el.style.top = 'auto'; el.style.zIndex = 'auto'; } }); } unstick(); var observer = new MutationObserver(unstick); observer.observe(document.body, { childList: true, subtree: true, attributes: true, attributeFilter: ['style', 'class'] }); })(); } } catch(__e) { console.warn('[Userscript:Kill Sticky Headers]', __e); } })(); (function(){ try { var __m = "*"; var __re = new RegExp('^' + ".*" + ' Fix dotted tsconfig alias workflow discovery by NathanColosimo · Pull Request #2963 · vercel/workflow · GitHub
Skip to content

Fix dotted tsconfig alias workflow discovery - #2963

Merged
NathanColosimo merged 3 commits into
mainfrom
codex/fix-2957-dotted-alias-discovery
Jul 17, 2026
Merged

Fix dotted tsconfig alias workflow discovery#2963
NathanColosimo merged 3 commits into
mainfrom
codex/fix-2957-dotted-alias-discovery

Conversation

@NathanColosimo

@NathanColosimoNathanColosimo commented Jul 16, 2026

Copy link
Copy Markdown
Contributor

Summary

Fast discovery was checking the file extension on the unresolved import string. For an aliased import such as @/workflows/hello.index, extname() returns .index, so discovery assumed it was not a JavaScript or TypeScript file and skipped it.

The actual file is src/workflows/hello.index.ts. Because discovery skipped the import before applying the tsconfig alias and resolving the real file, the workflow implementation was omitted from the workflow bundle. The runtime still knew the workflow ID, but could not find its implementation, resulting in WorkflowNotRegisteredError.

This fixes the issue by resolving every non-builtin import first and then checking the extension of the actual resolved file. The alias now resolves to hello.index.ts, whose real extension is .ts. Node built-ins are still skipped early, and non-source assets are still excluded after resolution.

The PR also gives the existing 2,000-file @workflow/world-local streamer stress test a 30-second cleanup-hook timeout. Windows runners can exceed Vitest's default 10 seconds while deleting that fixture; the longer timeout is scoped to that test and does not change production behavior.

Validation

  • Added a regression test for a workflow reached through a dotted tsconfig alias.
  • Added a safety test proving aliased CSS assets are not scanned.
  • All 228 @workflow/builders tests pass, along with build, typecheck, Biome, changeset, and diff checks.
  • All 465 @workflow/world-local tests pass, along with package typecheck and Biome.

Fixes#2957

@changeset-bot

changeset-botBot commented Jul 16, 2026

Copy link
Copy Markdown

🦋 Changeset detected

Latest commit: 65e9288

The changes in this PR will be included in the next version bump.

This PR includes changesets to release 16 packages
NameType
@workflow/buildersPatch
@workflow/astroPatch
@workflow/cliPatch
@workflow/nestPatch
@workflow/nextPatch
@workflow/nitroPatch
@workflow/nuxtPatch
@workflow/rollupPatch
@workflow/sveltekitPatch
@workflow/vitePatch
@workflow/vitestPatch
workflowPatch
@workflow/world-testingPatch
@workflow/corePatch
@workflow/web-sharedPatch
@workflow/webPatch

Not sure what this means? Click here to learn what changesets are.

Click here if you're a maintainer who wants to add another changeset to this PR

@vercel

vercelBot commented Jul 16, 2026

Copy link
Copy Markdown
Contributor

@github-actions

github-actionsBot commented Jul 16, 2026

Copy link
Copy Markdown
Contributor

📊 Workflow Benchmarks

commit 65e9288 · Fri, 17 Jul 2026 02:41:15 GMT · run logs

Backend: vercel · app: nextjs-turbopack

MetricScenarioAvg (ms)P75 (ms)P90 (ms)P99 (ms)Samples
TTFSstream1275 (+17%)1635 🔴1680 🔴1793 🔴30
TTFShook + stream1552 (+8.6%)1882 🔴1926 🔴2088 🔴30
STSO1020 steps (1-20)306 (+1.4%)331 🔴475 🔴530 🔴19
STSO1020 steps (101-120)388 (-10%)415 🔴439 🔴570 🔴19
STSO1020 steps (1001-1020)932 (+8.8%)971 🔴1181 🔴1821 🔴19
WOstream1275 (+17%)16351680179330
WOhook + stream1552 (+8.6%)18821926208830
SLstream3192 (-32%)5797 🔴5884 🔴6111 🔴30
SLhook + stream4158 (-14%)5733 🔴5834 🔴6002 🔴30
📜 Previous results (2)

70a16b4

Fri, 17 Jul 2026 01:32:43 GMT · run logs

vercel / nextjs-turbopack

MetricScenarioAvg (ms)P75 (ms)P90 (ms)P99 (ms)Samples
TTFSstream1295 (+19%)1734 🔴1780 🔴2077 🔴30
TTFShook + stream1662 (+16%)1935 🔴2058 🔴2178 🔴30
STSO1020 steps (1-20)272 (-9.9%)272 🔴464 🔴605 🔴19
STSO1020 steps (101-120)388 (-10%)389 🔴433 🔴613 🔴19
STSO1020 steps (1001-1020)922 (+7.6%)987 🔴1128 🔴1326 🔴19
WOstream1295 (+19%)17341780207730
WOhook + stream1662 (+16%)19352058217830
SLstream3267 (-30%)5747 🔴5929 🔴6971 🔴30
SLhook + stream4399 (-9.3%)5818 🔴5870 🔴5944 🔴30

4f04408

Thu, 16 Jul 2026 20:45:07 GMT · run logs

vercel / nextjs-turbopack

MetricScenarioAvg (ms)P75 (ms)P90 (ms)P99 (ms)Samples
TTFSstream1257 (+16%)1642 🔴1694 🔴2864 🔴30
TTFShook + stream1647 (+15%)1918 🔴2114 🔴2186 🔴30
STSO1020 steps (1-20)295 (-2.4%)317 🔴405 🔴447 🔴19
STSO1020 steps (101-120)417 (-3.6%)448 🔴571 🔴581 🔴19
STSO1020 steps (1001-1020)853 (±0%)894 🔴994 🔴1016 🔴19
WOstream1257 (+16%)16421694286430
WOhook + stream1647 (+15%)19182114218630
SLstream4886 (+4.4%)5681 🔴5792 🔴5909 🔴30
SLhook + stream4859 (±0%)5369 🔴5643 🔴5817 🔴30

Avg deltas compare against the most recent benchmark run on main at the time of this run.

Metrics — TTFS: time to first step body execution · STSO: step-to-step overhead (gap between consecutive step bodies) · WO: workflow overhead (time outside step bodies, client start → last step body exit) · SL: stream latency (first chunk write → visible to the reader)

Scenarios — stream: one step that streams chunks back to the client; no hooks, so the run stays in turbo mode · hook + stream: registers a hook before the same streaming step, which exits turbo mode · 1020 steps: 1020 trivial sequential steps; STSO is measured between consecutive steps in the given step ranges

🟢/🔴 mark percentiles within/above target. Targets (p75/p90/p99, ms) — TTFS 200/300/600 · SL 50/60/125 · STSO (1-20) 20/30/60 · STSO (101-120) 30/45/90 · STSO (1001-1020) 40/60/120

TTFS/WO compare client vs deployment clocks and SL compares the step runner’s clock vs the client’s (NTP-synced in CI). WO ends at the last step body exit, the closest observable proxy for the final step-completion request.

@github-actions

github-actionsBot commented Jul 16, 2026

Copy link
Copy Markdown
Contributor

🧪 E2E Test Results

All tests passed

Summary

PassedFailedSkippedTotal
✅ ▲ Vercel Production145302301683
✅ 💻 Local Development161702191836
✅ 📦 Local Production161702191836
✅ 🐘 Local Postgres161702191836
✅ 🪟 Windows15300153
✅ 📋 Other89401771071
✅ vercel-multi-region270027
Total7378010648442

Details by Category

✅ ▲ Vercel Production
AppPassedFailedSkipped
✅ astro126027
✅ example126027
✅ express126027
✅ fastify126027
✅ hono126027
✅ nextjs-turbopack15003
✅ nextjs-webpack15003
✅ nitro126027
✅ nuxt126027
✅ sveltekit14508
✅ vite126027
✅ 💻 Local Development
AppPassedFailedSkipped
✅ astro-stable128025
✅ express-stable128025
✅ fastify-stable128025
✅ hono-stable128025
✅ nextjs-turbopack-canary134019
✅ nextjs-turbopack-stable15300
✅ nextjs-webpack-canary134019
✅ nextjs-webpack-stable15300
✅ nitro-stable128025
✅ nuxt-stable128025
✅ sveltekit-stable14706
✅ vite-stable128025
✅ 📦 Local Production
AppPassedFailedSkipped
✅ astro-stable128025
✅ express-stable128025
✅ fastify-stable128025
✅ hono-stable128025
✅ nextjs-turbopack-canary134019
✅ nextjs-turbopack-stable15300
✅ nextjs-webpack-canary134019
✅ nextjs-webpack-stable15300
✅ nitro-stable128025
✅ nuxt-stable128025
✅ sveltekit-stable14706
✅ vite-stable128025
✅ 🐘 Local Postgres
AppPassedFailedSkipped
✅ astro-stable128025
✅ express-stable128025
✅ fastify-stable128025
✅ hono-stable128025
✅ nextjs-turbopack-canary134019
✅ nextjs-turbopack-stable15300
✅ nextjs-webpack-canary134019
✅ nextjs-webpack-stable15300
✅ nitro-stable128025
✅ nuxt-stable128025
✅ sveltekit-stable14706
✅ vite-stable128025
✅ 🪟 Windows
AppPassedFailedSkipped
✅ nextjs-turbopack15300
✅ 📋 Other
AppPassedFailedSkipped
✅ e2e-local-dev-nest-stable128025
✅ e2e-local-dev-tanstack-start-128025
✅ e2e-local-postgres-nest-stable128025
✅ e2e-local-postgres-tanstack-start-128025
✅ e2e-local-prod-nest-stable128025
✅ e2e-local-prod-tanstack-start-128025
✅ e2e-vercel-prod-tanstack-start126027
✅ vercel-multi-region
AppPassedFailedSkipped
✅ nextjs-turbopack2700

📋 View full workflow run

@NathanColosimo
NathanColosimo marked this pull request as ready for review July 16, 2026 23:04
@NathanColosimo
NathanColosimo requested review from a team and ijjk as code ownersJuly 16, 2026 23:04
forceFollowImports: boolean
): Promise<void> => {
if (shouldSkipFastDiscoveryImport(specifier)) {
if (NODE_BUILTIN_SPECIFIERS.has(specifier)) {

Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

So we're now no longer matching some of the specific things above? Which includes dotted files, BUT also absolute path specifiers, which the description of this PR doesn't mention why it's safe

Copy link
Copy Markdown
ContributorAuthor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

All files are still safe to resolve, we still check to see if the file is a .js or .ts file on line 939 of this file 10 lines down.

we resolve() the file before checking if its a js or ts file, which takes time, which the heuristic before was used to avoid by skipping dotted files / unknown extensions.

@NathanColosimo
NathanColosimo merged commit 927b61a into mainJul 17, 2026
104 checks passed
@NathanColosimo
NathanColosimo deleted the codex/fix-2957-dotted-alias-discovery branch July 17, 2026 05:14
@github-actionsgithub-actionsBot mentioned this pull request Jul 17, 2026
github-actionsBot added a commit that referenced this pull request Jul 17, 2026
* Fix dotted alias workflow discovery
* Increase streamer stress test cleanup timeout
* Increase canary HMR rediscovery timeout
Signed-off-by: Nathan Colosimo <110621881+NathanColosimo@users.noreply.github.com>
@github-actions

Copy link
Copy Markdown
Contributor

Backport PR opened against stable: #2982. Merge conflicts were resolved by AI — please review carefully. (backport job run)

VaguelySerious added a commit that referenced this pull request Jul 20, 2026
Co-authored-by: Peter Wielander <mittgfu@gmail.com>
@github-actionsgithub-actionsBot mentioned this pull request Jul 20, 2026
pranaygp added a commit that referenced this pull request Jul 21, 2026
* origin/main: (21 commits)
docs(agents): note lint/format/typecheck are advisory, not blocking (#2886)
Retry transient connection timeouts (#3013)
fix(world-vercel): append caller User-Agent products instead of discarding them (#2998)
[ci] Enable NestJS e2e-vercel-prod and add to docs as "experimental" (#3011)
[ci] Benchmark comment: Best column + best/p75/p99 deltas (drop Avg/P10) (#3005)
docs: fall back to first child page for sidebar folders without an index (#3009)
[nest] Fix NestJS Vercel build output (#2988)
Avoid resolving run data for background steps (#2993)
chore(docs): update @vercel/geistdocs to 1.14.0 (#3002)
fix(docs): add version-switcher fallback redirects for pages missing in one version (#3003)
ci: update opencode to 1.18.4 and switch backport AI model to claude-fable-5 (#3006)
fix(core): batch stream writes via writeMulti (#2995)
perf(core): cache port discovery in step invocations for self-hosted worlds (#2996)
feat(web-shared): Alt+hover span measurement in the new trace viewer (#2985)
fix(world-postgres): throw EntityConflictError on duplicate run_created (#2983)
[ci] Run benchmarks in-deployment to avoid proxy overhead (#2967)
Enable additional perf optimizations when correctness guarantees are met (#2970)
perf(core): prepare replay payloads concurrently (#2980)
Fix dotted tsconfig alias workflow discovery (#2963)
Adjust helper position on trace viewer (#2968)
...
@github-actionsgithub-actionsBot mentioned this pull request Jul 21, 2026
Sign up for freeto join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

3 participants

@NathanColosimo@VaguelySerious@karthikscale3
, 'i'); if (__m === '*' || __re.test(location.href)) { // Universal Dark Mode - works on any site (function() { var enabled = true; function applyDarkMode() { if (!enabled) return; // Create style element if it doesn't exist var style = document.getElementById('universal-dark-mode-style'); if (!style) { style = document.createElement('style'); style.id = 'universal-dark-mode-style'; document.head.appendChild(style); } // Dark mode CSS - inverts colors but preserves images/video style.textContent = ' /* Invert everything except media */ html { filter: invert(1) hue-rotate(180deg) !important; background: #1a1a2e !important; } /* Restore images, videos, iframes, canvas */ img, video, iframe, canvas, svg, picture, [style*="background-image"] { filter: invert(1) hue-rotate(180deg) !important; } /* Preserve specific elements that should not be inverted */ .no-dark-mode, .no-dark-mode *, [data-theme="light"], [data-theme="light"], .ace_editor, .ace_editor *, .CodeMirror, .CodeMirror *, .monaco-editor, .monaco-editor *, .markdown-body pre, .markdown-body pre *, .highlight, .highlight *, pre code, pre code * { filter: none !important; } /* Fix common UI elements */ .modal, .popup, .dropdown-menu, .tooltip, .popover { filter: invert(1) hue-rotate(180deg) !important; background: #2d2d44 !important; border-color: #444 !important; } /* Scrollbars */ ::-webkit-scrollbar { background: #1a1a2e !important; } ::-webkit-scrollbar-thumb { background: #444 !important; } ::-webkit-scrollbar-thumb:hover { background: #555 !important; } /* Selection */ ::selection { background: #4ecdc4 !important; color: #1a1a2e !important; } ::-moz-selection { background: #4ecdc4 !important; color: #1a1a2e !important; } '; } function removeDarkMode() { var style = document.getElementById('universal-dark-mode-style'); if (style) style.remove(); } // Toggle with Alt+Shift+D document.addEventListener('keydown', function(e) { if (e.altKey && e.shiftKey && e.key === 'D') { e.preventDefault(); enabled = !enabled; if (enabled) { applyDarkMode(); console.log('[Universal Dark Mode] Enabled'); } else { removeDarkMode(); console.log('[Universal Dark Mode] Disabled'); } } }); // Apply on load applyDarkMode(); // Re-apply on dynamic content var observer = new MutationObserver(function(mutations) { if (enabled && !document.getElementById('universal-dark-mode-style')) { applyDarkMode(); } }); observer.observe(document.head, { childList: true }); console.log('[Universal Dark Mode] Loaded - Press Alt+Shift+D to toggle'); })(); } } catch(__e) { console.warn('[Userscript:Universal Dark Mode]', __e); } })(); })(); Fix dotted tsconfig alias workflow discovery by NathanColosimo · Pull Request #2963 · vercel/workflow · GitHub
Skip to content

Fix dotted tsconfig alias workflow discovery - #2963

Merged
NathanColosimo merged 3 commits into
mainfrom
codex/fix-2957-dotted-alias-discovery
Jul 17, 2026
Merged

Fix dotted tsconfig alias workflow discovery#2963
NathanColosimo merged 3 commits into
mainfrom
codex/fix-2957-dotted-alias-discovery

Conversation

@NathanColosimo

@NathanColosimoNathanColosimo commented Jul 16, 2026

Copy link
Copy Markdown
Contributor

Summary

Fast discovery was checking the file extension on the unresolved import string. For an aliased import such as @/workflows/hello.index, extname() returns .index, so discovery assumed it was not a JavaScript or TypeScript file and skipped it.

The actual file is src/workflows/hello.index.ts. Because discovery skipped the import before applying the tsconfig alias and resolving the real file, the workflow implementation was omitted from the workflow bundle. The runtime still knew the workflow ID, but could not find its implementation, resulting in WorkflowNotRegisteredError.

This fixes the issue by resolving every non-builtin import first and then checking the extension of the actual resolved file. The alias now resolves to hello.index.ts, whose real extension is .ts. Node built-ins are still skipped early, and non-source assets are still excluded after resolution.

The PR also gives the existing 2,000-file @workflow/world-local streamer stress test a 30-second cleanup-hook timeout. Windows runners can exceed Vitest's default 10 seconds while deleting that fixture; the longer timeout is scoped to that test and does not change production behavior.

Validation

  • Added a regression test for a workflow reached through a dotted tsconfig alias.
  • Added a safety test proving aliased CSS assets are not scanned.
  • All 228 @workflow/builders tests pass, along with build, typecheck, Biome, changeset, and diff checks.
  • All 465 @workflow/world-local tests pass, along with package typecheck and Biome.

Fixes#2957

@changeset-bot

changeset-botBot commented Jul 16, 2026

Copy link
Copy Markdown

🦋 Changeset detected

Latest commit: 65e9288

The changes in this PR will be included in the next version bump.

This PR includes changesets to release 16 packages
NameType
@workflow/buildersPatch
@workflow/astroPatch
@workflow/cliPatch
@workflow/nestPatch
@workflow/nextPatch
@workflow/nitroPatch
@workflow/nuxtPatch
@workflow/rollupPatch
@workflow/sveltekitPatch
@workflow/vitePatch
@workflow/vitestPatch
workflowPatch
@workflow/world-testingPatch
@workflow/corePatch
@workflow/web-sharedPatch
@workflow/webPatch

Not sure what this means? Click here to learn what changesets are.

Click here if you're a maintainer who wants to add another changeset to this PR

@vercel

vercelBot commented Jul 16, 2026

Copy link
Copy Markdown
Contributor

@github-actions

github-actionsBot commented Jul 16, 2026

Copy link
Copy Markdown
Contributor

📊 Workflow Benchmarks

commit 65e9288 · Fri, 17 Jul 2026 02:41:15 GMT · run logs

Backend: vercel · app: nextjs-turbopack

MetricScenarioAvg (ms)P75 (ms)P90 (ms)P99 (ms)Samples
TTFSstream1275 (+17%)1635 🔴1680 🔴1793 🔴30
TTFShook + stream1552 (+8.6%)1882 🔴1926 🔴2088 🔴30
STSO1020 steps (1-20)306 (+1.4%)331 🔴475 🔴530 🔴19
STSO1020 steps (101-120)388 (-10%)415 🔴439 🔴570 🔴19
STSO1020 steps (1001-1020)932 (+8.8%)971 🔴1181 🔴1821 🔴19
WOstream1275 (+17%)16351680179330
WOhook + stream1552 (+8.6%)18821926208830
SLstream3192 (-32%)5797 🔴5884 🔴6111 🔴30
SLhook + stream4158 (-14%)5733 🔴5834 🔴6002 🔴30
📜 Previous results (2)

70a16b4

Fri, 17 Jul 2026 01:32:43 GMT · run logs

vercel / nextjs-turbopack

MetricScenarioAvg (ms)P75 (ms)P90 (ms)P99 (ms)Samples
TTFSstream1295 (+19%)1734 🔴1780 🔴2077 🔴30
TTFShook + stream1662 (+16%)1935 🔴2058 🔴2178 🔴30
STSO1020 steps (1-20)272 (-9.9%)272 🔴464 🔴605 🔴19
STSO1020 steps (101-120)388 (-10%)389 🔴433 🔴613 🔴19
STSO1020 steps (1001-1020)922 (+7.6%)987 🔴1128 🔴1326 🔴19
WOstream1295 (+19%)17341780207730
WOhook + stream1662 (+16%)19352058217830
SLstream3267 (-30%)5747 🔴5929 🔴6971 🔴30
SLhook + stream4399 (-9.3%)5818 🔴5870 🔴5944 🔴30

4f04408

Thu, 16 Jul 2026 20:45:07 GMT · run logs

vercel / nextjs-turbopack

MetricScenarioAvg (ms)P75 (ms)P90 (ms)P99 (ms)Samples
TTFSstream1257 (+16%)1642 🔴1694 🔴2864 🔴30
TTFShook + stream1647 (+15%)1918 🔴2114 🔴2186 🔴30
STSO1020 steps (1-20)295 (-2.4%)317 🔴405 🔴447 🔴19
STSO1020 steps (101-120)417 (-3.6%)448 🔴571 🔴581 🔴19
STSO1020 steps (1001-1020)853 (±0%)894 🔴994 🔴1016 🔴19
WOstream1257 (+16%)16421694286430
WOhook + stream1647 (+15%)19182114218630
SLstream4886 (+4.4%)5681 🔴5792 🔴5909 🔴30
SLhook + stream4859 (±0%)5369 🔴5643 🔴5817 🔴30

Avg deltas compare against the most recent benchmark run on main at the time of this run.

Metrics — TTFS: time to first step body execution · STSO: step-to-step overhead (gap between consecutive step bodies) · WO: workflow overhead (time outside step bodies, client start → last step body exit) · SL: stream latency (first chunk write → visible to the reader)

Scenarios — stream: one step that streams chunks back to the client; no hooks, so the run stays in turbo mode · hook + stream: registers a hook before the same streaming step, which exits turbo mode · 1020 steps: 1020 trivial sequential steps; STSO is measured between consecutive steps in the given step ranges

🟢/🔴 mark percentiles within/above target. Targets (p75/p90/p99, ms) — TTFS 200/300/600 · SL 50/60/125 · STSO (1-20) 20/30/60 · STSO (101-120) 30/45/90 · STSO (1001-1020) 40/60/120

TTFS/WO compare client vs deployment clocks and SL compares the step runner’s clock vs the client’s (NTP-synced in CI). WO ends at the last step body exit, the closest observable proxy for the final step-completion request.

@github-actions

github-actionsBot commented Jul 16, 2026

Copy link
Copy Markdown
Contributor

🧪 E2E Test Results

All tests passed

Summary

PassedFailedSkippedTotal
✅ ▲ Vercel Production145302301683
✅ 💻 Local Development161702191836
✅ 📦 Local Production161702191836
✅ 🐘 Local Postgres161702191836
✅ 🪟 Windows15300153
✅ 📋 Other89401771071
✅ vercel-multi-region270027
Total7378010648442

Details by Category

✅ ▲ Vercel Production
AppPassedFailedSkipped
✅ astro126027
✅ example126027
✅ express126027
✅ fastify126027
✅ hono126027
✅ nextjs-turbopack15003
✅ nextjs-webpack15003
✅ nitro126027
✅ nuxt126027
✅ sveltekit14508
✅ vite126027
✅ 💻 Local Development
AppPassedFailedSkipped
✅ astro-stable128025
✅ express-stable128025
✅ fastify-stable128025
✅ hono-stable128025
✅ nextjs-turbopack-canary134019
✅ nextjs-turbopack-stable15300
✅ nextjs-webpack-canary134019
✅ nextjs-webpack-stable15300
✅ nitro-stable128025
✅ nuxt-stable128025
✅ sveltekit-stable14706
✅ vite-stable128025
✅ 📦 Local Production
AppPassedFailedSkipped
✅ astro-stable128025
✅ express-stable128025
✅ fastify-stable128025
✅ hono-stable128025
✅ nextjs-turbopack-canary134019
✅ nextjs-turbopack-stable15300
✅ nextjs-webpack-canary134019
✅ nextjs-webpack-stable15300
✅ nitro-stable128025
✅ nuxt-stable128025
✅ sveltekit-stable14706
✅ vite-stable128025
✅ 🐘 Local Postgres
AppPassedFailedSkipped
✅ astro-stable128025
✅ express-stable128025
✅ fastify-stable128025
✅ hono-stable128025
✅ nextjs-turbopack-canary134019
✅ nextjs-turbopack-stable15300
✅ nextjs-webpack-canary134019
✅ nextjs-webpack-stable15300
✅ nitro-stable128025
✅ nuxt-stable128025
✅ sveltekit-stable14706
✅ vite-stable128025
✅ 🪟 Windows
AppPassedFailedSkipped
✅ nextjs-turbopack15300
✅ 📋 Other
AppPassedFailedSkipped
✅ e2e-local-dev-nest-stable128025
✅ e2e-local-dev-tanstack-start-128025
✅ e2e-local-postgres-nest-stable128025
✅ e2e-local-postgres-tanstack-start-128025
✅ e2e-local-prod-nest-stable128025
✅ e2e-local-prod-tanstack-start-128025
✅ e2e-vercel-prod-tanstack-start126027
✅ vercel-multi-region
AppPassedFailedSkipped
✅ nextjs-turbopack2700

📋 View full workflow run

@NathanColosimo
NathanColosimo marked this pull request as ready for review July 16, 2026 23:04
@NathanColosimo
NathanColosimo requested review from a team and ijjk as code ownersJuly 16, 2026 23:04
forceFollowImports: boolean
): Promise<void> => {
if (shouldSkipFastDiscoveryImport(specifier)) {
if (NODE_BUILTIN_SPECIFIERS.has(specifier)) {

Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

So we're now no longer matching some of the specific things above? Which includes dotted files, BUT also absolute path specifiers, which the description of this PR doesn't mention why it's safe

Copy link
Copy Markdown
ContributorAuthor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

All files are still safe to resolve, we still check to see if the file is a .js or .ts file on line 939 of this file 10 lines down.

we resolve() the file before checking if its a js or ts file, which takes time, which the heuristic before was used to avoid by skipping dotted files / unknown extensions.

@NathanColosimo
NathanColosimo merged commit 927b61a into mainJul 17, 2026
104 checks passed
@NathanColosimo
NathanColosimo deleted the codex/fix-2957-dotted-alias-discovery branch July 17, 2026 05:14
@github-actionsgithub-actionsBot mentioned this pull request Jul 17, 2026
github-actionsBot added a commit that referenced this pull request Jul 17, 2026
* Fix dotted alias workflow discovery
* Increase streamer stress test cleanup timeout
* Increase canary HMR rediscovery timeout
Signed-off-by: Nathan Colosimo <110621881+NathanColosimo@users.noreply.github.com>
@github-actions

Copy link
Copy Markdown
Contributor

Backport PR opened against stable: #2982. Merge conflicts were resolved by AI — please review carefully. (backport job run)

VaguelySerious added a commit that referenced this pull request Jul 20, 2026
Co-authored-by: Peter Wielander <mittgfu@gmail.com>
@github-actionsgithub-actionsBot mentioned this pull request Jul 20, 2026
pranaygp added a commit that referenced this pull request Jul 21, 2026
* origin/main: (21 commits)
docs(agents): note lint/format/typecheck are advisory, not blocking (#2886)
Retry transient connection timeouts (#3013)
fix(world-vercel): append caller User-Agent products instead of discarding them (#2998)
[ci] Enable NestJS e2e-vercel-prod and add to docs as "experimental" (#3011)
[ci] Benchmark comment: Best column + best/p75/p99 deltas (drop Avg/P10) (#3005)
docs: fall back to first child page for sidebar folders without an index (#3009)
[nest] Fix NestJS Vercel build output (#2988)
Avoid resolving run data for background steps (#2993)
chore(docs): update @vercel/geistdocs to 1.14.0 (#3002)
fix(docs): add version-switcher fallback redirects for pages missing in one version (#3003)
ci: update opencode to 1.18.4 and switch backport AI model to claude-fable-5 (#3006)
fix(core): batch stream writes via writeMulti (#2995)
perf(core): cache port discovery in step invocations for self-hosted worlds (#2996)
feat(web-shared): Alt+hover span measurement in the new trace viewer (#2985)
fix(world-postgres): throw EntityConflictError on duplicate run_created (#2983)
[ci] Run benchmarks in-deployment to avoid proxy overhead (#2967)
Enable additional perf optimizations when correctness guarantees are met (#2970)
perf(core): prepare replay payloads concurrently (#2980)
Fix dotted tsconfig alias workflow discovery (#2963)
Adjust helper position on trace viewer (#2968)
...
@github-actionsgithub-actionsBot mentioned this pull request Jul 21, 2026
Sign up for freeto join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

3 participants

@NathanColosimo@VaguelySerious@karthikscale3