Adding local data
Last updated Jun 25, 2026 Whether you are using Wrangler or the Cloudflare Vite plugin ↗︎, your workflow for accessing data during local development remains the same. However, you can only populate local resources with data via the Wrangler CLI.
How it works
When you run either wrangler dev or vite ↗︎, Miniflare automatically creates local versions of your resources (like KV, D1, or R2). This means you don’t need to manually set up separate local instances for each service. However, newly created local resources won’t contain any data — you'll need to use Wrangler commands with the --local flag to populate them. Changes made to local resources won’t affect production data.
Populating local resources with data
When you first start developing, your local resources will be empty. You'll need to populate them with data using the Wrangler CLI.
KV namespaces
Syntax note
Since version 3.60.0, Wrangler supports the kv ... syntax. If you are using versions below 3.60.0, the command follows the kv:... syntax. Learn more in the Wrangler commands for KV page.
Add a single key-value pair
npmyarnpnpm
npx wrangler kv key put <KEY> <VALUE> --binding=<BINDING> --local
yarn wrangler kv key put <KEY> <VALUE> --binding=<BINDING> --local
pnpm wrangler kv key put <KEY> <VALUE> --binding=<BINDING> --local
Bulk upload
npmyarnpnpm
npx wrangler kv bulk put <FILENAME.json> --binding=<BINDING> --local
yarn wrangler kv bulk put <FILENAME.json> --binding=<BINDING> --local
pnpm wrangler kv bulk put <FILENAME.json> --binding=<BINDING> --local
R2 buckets
Upload a file
npmyarnpnpm
npx wrangler r2 object put <BUCKET>/<KEY> --file=<PATH_TO_FILE> --local
yarn wrangler r2 object put <BUCKET>/<KEY> --file=<PATH_TO_FILE> --local
pnpm wrangler r2 object put <BUCKET>/<KEY> --file=<PATH_TO_FILE> --local
You may also include other metadata.
D1 databases
Execute a SQL statement
npmyarnpnpm
npx wrangler d1 execute <DATABASE_NAME> --command="<SQL_QUERY>" --local
yarn wrangler d1 execute <DATABASE_NAME> --command="<SQL_QUERY>" --local
pnpm wrangler d1 execute <DATABASE_NAME> --command="<SQL_QUERY>" --local
Execute a SQL file
npmyarnpnpm
npx wrangler d1 execute <DATABASE_NAME> --file=./schema.sql --local
yarn wrangler d1 execute <DATABASE_NAME> --file=./schema.sql --local
pnpm wrangler d1 execute <DATABASE_NAME> --file=./schema.sql --local
Durable Objects
For Durable Objects, unlike KV, D1, and R2, there are no CLI commands to populate them with local data. To add data to Durable Objects during local development, you must write application code that creates Durable Object instances and calls methods on them that store state. This typically involves creating development endpoints or test routes that initialize your Durable Objects with the desired data.
Where local data gets stored
By default, both Wrangler and the Vite plugin store local binding data in the same location: the .wrangler/state folder in your project directory. This folder stores data in subdirectories for all local bindings: KV namespaces, R2 buckets, D1 databases, Durable Objects, etc.
Clearing local storage
You can delete the .wrangler/state folder at any time to reset your local environment, and Miniflare will recreate it the next time you run your dev command. You can also delete specific sub-folders within .wrangler/state for more targeted clean-up.
Changing the local data directory
If you prefer to specify a different directory for local storage, you can do so through the Wrangler CLI or in the Vite plugin's configuration.
Using Wrangler
Use the --persist-to flag with wrangler dev. You need to specify this flag every time you run the dev command:
npmyarnpnpm
npx wrangler dev --persist-to <DIRECTORY>
yarn wrangler dev --persist-to <DIRECTORY>
pnpm wrangler dev --persist-to <DIRECTORY>
Note
The local persistence folder (like .wrangler/state or any custom folder you set) should be added to your .gitignore to avoid committing local development data to version control.
<details>
<summary>
Using <code>--local</code> with <code>--persist-to</code>
</summary>
If you run <code>wrangler dev --persist-to <DIRECTORY></code> to specify a custom location for local data, you must also include the same <code>--persist-to <DIRECTORY></code> when running other Wrangler commands that modify local data (and be sure to include the <code>--local</code> flag).
For example, to create a KV key named <code>test</code> with a value of <code>12345</code> in a local KV namespace, run:
npmyarnpnpm
npx wrangler kv key put test 12345 --binding MY_KV_NAMESPACE --local --persist-to worker-local
yarn wrangler kv key put test 12345 --binding MY_KV_NAMESPACE --local --persist-to worker-local
pnpm wrangler kv key put test 12345 --binding MY_KV_NAMESPACE --local --persist-to worker-local
This command:
- Sets the KV key <code>test</code> to <code>12345</code> in the binding <code>MY_KV_NAMESPACE</code> (defined in your <a href="https://developers.cloudflare.com/workers/wrangler/configuration/">Wrangler configuration file</a>).
- Uses <code>--persist-to worker-local</code> to ensure the data is created in the worker-local directory instead of the default <code>.wrangler/state</code>.
- Adds the <code>--local</code> flag, indicating you want to modify local data.
If <code>--persist-to</code> is not specified, Wrangler defaults to using <code>.wrangler/state</code> for local data.
</details>
Using the Cloudflare Vite plugin
To customize where the Vite plugin stores local data, configure the persistState option in your Vite config file:
vite.config.jsjs
import { defineConfig } from "vite";
import { cloudflare } from "@cloudflare/vite-plugin";
export default defineConfig({
plugins: [
cloudflare({
persistState: { path: "./my-custom-directory" },
}),
],
});
Sharing state between tools
If you want Wrangler and the Vite plugin to share the same state, configure them to use the same persistence path.
Was this helpful?
YesNo
On this page
{"@context":"https://schema.org","@type":"WebPage","@id":"https://developers.cloudflare.com/workers/local-development/local-data/#page","headline":"Adding local data","description":"Populating local resources with data","url":"https://developers.cloudflare.com/workers/local-development/local-data/","inLanguage":"en","image":"https://developers.cloudflare.com/workers/local-development/local-data/og.png?v=7c487889b7546d0d","dateModified":"2026-06-25","publisher":{"@type":"Organization","name":"Cloudflare","description":"One platform for your apps, agents, and workforce. Build, secure, and scale without managing infrastructure","url":"https://www.cloudflare.com/","sameAs":["https://github.com/cloudflare","https://www.linkedin.com/company/cloudflare","https://x.com/cloudflare"],"logo":{"@type":"ImageObject","url":"https://developers.cloudflare.com/logo.svg"},"address":{"@type":"PostalAddress","streetAddress":"101 Townsend St","addressLocality":"San Francisco","addressRegion":"CA","postalCode":"94107","addressCountry":"US"},"contactPoint":[{"@type":"ContactPoint","contactType":"Customer Support","url":"https://support.cloudflare.com/","availableLanguage":["English"]},{"@type":"ContactPoint","contactType":"Sales","url":"https://www.cloudflare.com/contact/","availableLanguage":["English"]}]},"isPartOf":{"@type":"WebSite","@id":"https://developers.cloudflare.com/#website","name":"Cloudflare Docs","url":"https://developers.cloudflare.com/"}}
description: Expose a local Wrangler or Vite dev server over a public tunnel URL. title: Share a local dev server image: https://developers.cloudflare.com/workers/local-development/local-dev-tunnels/og.png?v=1b1ab53357b8bed6
Documentation Index
Fetch the complete documentation index at: https://developers.cloudflare.com/workers/llms.txt
Use this file to discover all available pages before exploring further.
Docs