Migrating from Vercel KV to Layerbase
Short version: Vercel KV was sunset in December 2024 and your store is an Upstash Redis database now, so what you are actually moving is an ordinary keyspace. Find the rediss:// string on the Upstash side of your project's Storage tab, paste it into the importer, and every key arrives with its type and its remaining TTL intact, read once with a non-blocking scan while your app keeps serving. There is nothing else to carry, because a KV store has no schema, no auth tables, and no functions. The cutover is one environment variable, plus a client swap if your code still imports the deprecated @vercel/kv package, which auto-serialized objects that a raw Redis client will not.
Vercel KV was Redis, with Upstash running it under the hood. It is not a product you can buy anymore: Vercel's Redis docs say "Vercel KV is no longer available. If you had an existing Vercel KV store, we automatically moved it to Upstash Redis in December 2024." So whatever your project still calls it, what you are migrating today is an Upstash Redis database reached through the Vercel Marketplace integration. The useful consequence for a migration is that there is nothing exotic to move: it is a keyspace, it speaks the Redis wire protocol, and one rediss:// connection string is enough to copy it. This post is the move, start to finish. If you are still weighing whether to leave, Vercel KV alternatives: own your Redis makes that case; this post assumes you have decided and walks the migration.
Just want it done? Start at layerbase.com/migrate/vercel-kv. You sign in, the wizard opens with Vercel KV already selected, and it reads your store once with a non-blocking scan and copies every key, type, and TTL into managed Redis (or Valkey): read-once, nothing written back to your KV store. The rest of this post is that same migration explained step by step, plus the manual path.
Contents
- What moves and what does not
- Find your connection string
- The migration, step by step
- Redis or Valkey, and the queue question
- Swap the @vercel/kv client
- The manual path
- FAQ
What moves and what does not
Your former KV store holds a Redis keyspace, and the whole keyspace moves.
Moves automatically:
- Every key, with its type preserved: strings, hashes, lists, sets, sorted sets, and streams.
- Every TTL. Expiring keys keep expiring on the same schedule after the move, so sessions, rate-limit windows, and cache entries do not suddenly become immortal.
Does not move:
- The Vercel dashboard wiring. The store is an Upstash integration on your Vercel project; migrating the data does not touch your deployment. You swap an environment variable when you are ready to cut over (see the client section).
- Nothing else, because there is nothing else. Unlike a database migration with schemas and auth, a KV move is just the keyspace. That is the whole appeal.
Find your connection string
This is the only credential you need, and it is already in your Vercel account.
In the Vercel dashboard, open your project and go to the Storage tab, then select the Redis resource. It is listed as an Upstash integration rather than a native KV product, because that is what the December 2024 move turned it into. From that page Vercel links out to the provider's own console (its storage docs list "Access provider dashboard" among the things you manage there), and the Upstash database page is where the TLS endpoint lives: Upstash shows the Endpoint, Port, and Token, which compose into a rediss:// string like:
rediss://default:<token>@<name>.upstash.io:6379That single string is enough to read the whole store. There is no separate API key and no account email to dig up, because it is a standard Redis connection string.
Vercel's labels have moved more than once since the sunset, so treat the click path as the shape of it rather than a script. As of August 2026 the store sits under Storage and the connection details live on the Upstash side.
Your environment variables may already hold the string. Projects provisioned back when this was Vercel KV often still carry KV_URL next to the KV_REST_API_* set, and newer ones get the Upstash pair instead. Neither vendor publishes a definitive list of what the integration injects today, so read your project's actual environment list rather than trusting any post, including this one. What you need is whichever variable holds a rediss:// string: the REST URL and token are HTTP credentials and will not copy a keyspace.
The migration, step by step
The fastest path is the built-in migration flow. It handles the scan and the copy for you.
Step 1: Start the migration
In the Layerbase dashboard, click New database and choose Migrating from another platform, then pick Vercel KV. (You can also open the Migrate tab on an existing blank database.)
Paste the rediss:// string you copied above. Unlike the API-key sources, there is no "list your databases" step here: the connection string points at exactly one store, so the wizard reads it directly.
Step 2: Let it copy
Layerbase provisions a Redis (or Valkey, your choice) instance and reads your store with a non-blocking SCAN, never a blocking KEYS *, so your live app keeps serving reads and writes while the copy runs. Every key is recreated with its type and remaining TTL. For a typical cache or session store this is quick; a very large keyspace takes proportionally longer.
Step 3: Grab the connection string
Open the new database in the dashboard and copy its connection string. It is a standard rediss:// URL:
rediss://layerbase:<password>@your-host.cloud.layerbase.dev:portAny standard Redis client takes it as-is.
Redis or Valkey, and the queue question
The wizard lets you land on either Redis or Valkey. They are wire-compatible, so your commands and data structures are identical on both, and the copy is the same either way. Two things help you choose:
- If you just want a Redis you own at flat pricing, either works. Valkey is the BSD-licensed Redis fork; pick it if you would rather not depend on the Redis license, or Redis if you want the exact upstream.
- If your KV store backs a message queue, pick Valkey. Layerbase's managed queue add-on, vqueue, runs on Valkey. A plain key/value copy brings your data across to either target, but if you want the queue product on the other side, Valkey is where it lives.
Whichever you pick, the pricing is flat per instance rather than per request, which is the point of moving off a metered Upstash-backed store: the bill is the same at a thousand ops a month or a billion.
Swap the @vercel/kv client
If your code already talks to KV through a standard Redis client, this is one environment variable: point REDIS_URL (or whatever you call it) at the new connection string and deploy.
The change that matters is for code using the @vercel/kv client, a REST/HTTP wrapper built for edge runtimes that npm now marks deprecated.
Before (Vercel KV client):
import { kv } from '@vercel/kv'
await kv.set('session:42', value, { ex: 3600 })
const v = await kv.get('session:42')After (standard Redis client over TCP):
import Redis from 'ioredis'
const redis = new Redis(process.env.REDIS_URL!) // rediss://...cloud.layerbase.dev:port
await redis.set('session:42', JSON.stringify(value), 'EX', 3600)
const v = JSON.parse((await redis.get('session:42')) ?? 'null')Two notes. @vercel/kv auto-serialized objects to JSON; a raw Redis client stores strings, so serialize on the way in and parse on the way out (or keep a thin wrapper that does it). And @vercel/kv exists because some edge runtimes cannot open raw TCP sockets: if you call KV from an edge function, keep that path behind a small Node API route that talks to the new instance over TCP, and use ioredis there.
The manual path
If you would rather drive the copy yourself, the source is a normal rediss:// endpoint, so redis-cli works. Use --scan (not KEYS *) so you do not block the store, and copy each key with DUMP/RESTORE to preserve type and TTL:
SRC='rediss://default:<token>@<name>.upstash.io:6379' # from the Upstash side
DST='rediss://layerbase:<password>@your-host.cloud.layerbase.dev:port'
redis-cli -u "$SRC" --scan | while read -r key; do
ttl=$(redis-cli -u "$SRC" --no-raw PTTL "$key")
dump=$(redis-cli -u "$SRC" --no-raw DUMP "$key")
redis-cli -u "$DST" RESTORE "$key" "${ttl/-1/0}" "$dump"
doneThe ${ttl/-1/0} turns a "no expiry" PTTL of -1 into the 0 that RESTORE wants for a persistent key. This loop is fine for small-to-medium stores; for a large keyspace prefer the wizard, which batches and resumes.
FAQ
Can I paste the KV REST URL and token instead of a connection string?
No. The KV_REST_API_URL and KV_REST_API_TOKEN pair are HTTP credentials for a client library, not a way to read a keyspace, so the importer will not take them. What it wants is whichever variable holds a rediss:// string: a legacy KV_URL works, and so does the TLS endpoint composed from the Endpoint, Port, and Token on the Upstash database page. Vercel KV is a connection-string source in the wizard, so there is no "list my databases" step and no account email to find.
Will the copy slow down or block my live store?
It will not. The read is a non-blocking SCAN, never a blocking KEYS *, so the store keeps serving reads and writes while every key is recreated on the new side with its type and remaining TTL. Nothing is written back to your KV store at any point, which also means the source stays intact as a rollback until you delete it yourself.
Should I land on Redis or Valkey?
Either, since they are wire-compatible and your commands and data structures are identical on both. Pick Valkey if you would rather not depend on the Redis license, or Redis if you want exact upstream. The one case that decides it: if the store backs a message queue, choose Valkey, because the managed queue add-on vqueue runs there and a key/value copy on its own does not bring a queue product with it.
Does anything on my Vercel project have to change?
Only the environment variable your code reads, and only when you are ready. Migrating the data does not touch the deployment, the Upstash integration, or the Storage tab, so the old store sits there until you remove it. Point REDIS_URL at the new rediss:// string, redeploy, confirm the app is reading the new instance, then tear down the integration.
Do I have to rewrite everything that called @vercel/kv?
Not rewrite, but do read the diff carefully in one place. The commands map straight across to ioredis with slightly different option syntax, and the trap is serialization: @vercel/kv quietly turned objects into JSON for you and a raw Redis client stores strings, so serialize on the way in and parse on the way out, or keep a thin wrapper that does it. If you call the store from an edge function, keep that path behind a small Node API route that talks TCP.
Rehearse locally first
The Layerbase CLI (formerly SpinDB) runs Valkey locally with no Docker, so you can copy into a local instance and verify before you touch production:
npm i -g layerbase
lbase create kv-test -e valkey --start
# point DST at "$(lbase url kv-test)" in the loop above, then check a few keys:
redis-cli -u "$(lbase url kv-test)" PTTL session:42Confirm your TTL-sensitive logic (sessions, rate limits, cache expiries) survived, then run the real copy into Layerbase Cloud.
Leaving Vercel KV is a keyspace copy and a one-line client swap, because it was Redis the whole time. Paste the rediss:// string, copy every key and TTL through the wizard or a --scan loop, and land on a Redis or Valkey instance you own at flat pricing. For the decision behind the move, see Vercel KV alternatives; for the same move framed from the Upstash side, which is where your data now lives, see Migrating from Upstash.
Keep reading
- Vercel KV is gone: where your data went and how to move itVercel KV was sunset and every existing store was moved into Upstash Redis in December 2024. The @vercel/kv client on npm is formally deprecated and has not shipped a release since 2024. Here is how to find out what you are actually running, and how to move it onto managed Valkey.
- Vercel KV alternatives: own your Redis in 2026Vercel KV was first-party Redis built on Upstash, and it was sunset into Upstash Redis on the Vercel Marketplace. If you want a Redis you own at flat pricing, here is how to move to managed Valkey with the rediss:// string you already have.
- Redis Cloud alternatives: pay for the modules, or stop paying for themRedis Cloud prices itself around the module story: search, JSON, time series, vector sets, Active-Active. If you use those, the bill is buying something real. If you use Redis as a cache, a session store, or a queue, you are paying the module premium for a key-value store. Here is what each tier buys, where a flat plan fits, and when to stay.
- Build the Redis backend for a WhatsApp botConversation state with TTLs, BullMQ queues for scheduled reminders, idempotency keys for retried webhooks, and per-recipient rate limits, all on one Redis-compatible Valkey.