How We Pinned Vercel Functions to the Tokyo Region to Improve Perceived Speed โ Eliminating the Pacific Round Trip
- engineering
- nextjs
- performance
- vercel
TL;DR
- The dashboard was slow because the Vercel function ran in the US while the database ran in Tokyo, causing a Pacific round trip on every request
- The
x-vercel-idresponse header lets you check which region a function actually executed in- By pinning the region to Tokyo via
regionsinvercel.jsonand parallelizing queries, our internal measurements went from several seconds down to roughly 0.2 seconds
"Dashboard page transitions take several seconds" โ this is a record of investigating that perceived slowness, identifying the root cause, and fixing it. We isolated the problem through actual measurement, not guesswork.
Symptoms and isolation
Page transitions took about 3 seconds. We first isolated whether the delay came from the server's initial response (TTFB) or from fetching the page's data, and found that the initial response was fast โ it was the in-page data fetching that was slow.
Each individual query itself ran in just a few milliseconds at the database level. Yet the overall process was slow. That's when we suspected the execution location (region).
Cause #1: A Pacific round trip on every request
Looking at the x-vercel-id response header, we found the function was executing in the US East region (iad1). Meanwhile, the database (Supabase) was in Tokyo. In other words, every single query triggered a round trip between Japan and the US.
The header looked like this (illustrative):
x-vercel-id: hnd1::iad1 โ Entry point is Tokyo (hnd1), but execution is in the US (iad1)
With multiple queries per request, each one added another Pacific round trip, and the latency kept stacking up.
Cause #2: Queries were awaited serially
There was a second issue: the home screen fetched several aggregate values serially (one after another). The round-trip delay was simply multiplied by the number of queries.
The fix
Pinning the region to Tokyo
We added a region setting to vercel.json so the function would run in Tokyo (hnd1).
{ "regions": ["hnd1"] }
This made x-vercel-id read hnd1::hnd1, putting both the function and the database in Tokyo. The round-trip delay was eliminated.
Parallelizing queries
We parallelized the aggregate fetches that had been awaited serially using Promise.all, and also consolidated duplicate fetches into a single call.
Results
In our internal measurements, the home screen's load time dropped from several seconds to roughly 0.2 seconds. The key point: we made the process itself faster instead of relying on caching. The data shown remains fully up to date at all times.
Lessons learned
- When "queries are fast but the screen is slow," don't just look at database speed โ suspect the physical distance (region) between the function and the database.
x-vercel-idis a quick and powerful clue for checking the execution region.- In environments with high round-trip costs, serial waiting becomes critical. Parallelization delivers a big impact.
Summary
The real cause of the perceived slowness was a round trip between the US and Tokyo. With two fixes โ pinning the region and parallelizing queries โ we dramatically improved perceived performance without adding any caching. If your SSR pages or dashboard feel slow, start by checking the relationship between your execution region and your database's location.