Skip to main content

Convex Svelte

For AI agents: see llms.txt for the complete documentation index. Markdown versions are available by adding .md to a page URL or requesting Accept: text/markdown.

Convex Svelte is the Convex client library for Svelte 5. It wraps the ConvexClient in reactive Svelte APIs, so your frontend code can:

  1. Subscribe to your queries and get live updates
  2. Call your mutations and actions
  3. Paginate through large datasets
  4. Authenticate users
  5. Server-side render data in SvelteKit
Source & issues

Source: convex/convex-svelte.


Found a bug or have a feature request? Open an issue in its issue tracker.

Follow the Svelte Quickstart to get started, or read on for the full setup.

Installation​

Install the Convex client and server library:

npm install convex convex-svelte

Svelte projects keep their code in src/, so put the Convex functions there too. Create a convex.json in your project root:

convex.json
{
"functions": "src/convex/"
}

Set up a Convex dev deployment:

npx convex dev

It prompts you to log in and create a project, saves your deployment URL, and creates the src/convex/ folder for your Convex functions.

Setup​

On SvelteKit 3, declare PUBLIC_CONVEX_URL in src/env.ts. SvelteKit 3 only exposes declared variables, through $app/env/public:

src/env.ts
import { defineEnvVars } from "@sveltejs/kit/env";

export const variables = defineEnvVars({
PUBLIC_CONVEX_URL: { public: true, static: true },
});

On SvelteKit 2, skip src/env.ts and import the variable from $env/static/public instead. The examples in these docs use SvelteKit 3.

Call setupConvex() once in a root layout component, such as +layout.svelte. It creates a ConvexClient and stores it in Svelte context, so child components can use it. The client belongs to the app: it stays open while the app runs (remounts and HMR reuse the same connection) and connects to a single deployment URL. To close it explicitly, for example in tests, call closeConvex().

src/routes/+layout.svelte
<script lang="ts">
import { setupConvex } from "convex-svelte";
import { PUBLIC_CONVEX_URL } from "$app/env/public"; // SvelteKit 2: "$env/static/public"

const client = setupConvex(PUBLIC_CONVEX_URL);
</script>

setupConvex() returns the ConvexClient, which you can use in the layout for mutations or actions, for example in an auth nav bar. In child components and .ts files, get it with getConvexClient(), see Client access.

To configure the ConvexClient, pass ConvexClientOptions as the second argument. With the SvelteKit server rendering setup, initConvex() creates the client instead, so pass the options there: setupConvex() then ignores its own.

Without SvelteKit

With plain Vite and Svelte, set VITE_CONVEX_URL in your .env file and pass import.meta.env.VITE_CONVEX_URL to setupConvex().

Fetching data​

Use useQuery() to subscribe to a Convex query. When the data changes on the server, the component updates.

src/routes/+page.svelte
<script lang="ts">
import { useQuery } from "convex-svelte";
import { api } from "../convex/_generated/api.js";

const messages = useQuery(api.messages.list, () => ({ searchWords: [] }));
</script>

{#if messages.isLoading}
Loading...
{:else if messages.error != null}
failed to load: {messages.error.toString()}
{:else}
<ul>
{#each messages.data as message}
<li>
<span>{message.author}</span>
<span>{message.body}</span>
</li>
{/each}
</ul>
{/if}

Queries, Mutations & Actions covers the rest of the reactive API: query options, skipping, mutations, actions, optimistic updates, pagination, and the client outside of components.

Next steps​