# RxDB 17.0.0 - Local-First to the Moon

> RxDB 17 introduces improved reactivity APIs, better debugging, breaking storage fixes, and multiple plugins graduating from beta.

import { PerformanceChart } from '@site/src/components/performance-chart';
import { PERFORMANCE_DATA_EXPO, PERFORMANCE_METRICS } from '@site/src/components/performance-data';
import { LinkedinBox } from '@site/src/components/linkedin-box';
import { IconVibeCoding } from '@site/src/components/icons/vibe-coding';
import { IconExperiment } from '@site/src/components/icons/experiment';
import { IconDevicePhone } from '@site/src/components/icons/device-phone';
import { IconQuickstart } from '@site/src/components/icons/quickstart';
import { HeadlineWithIcon } from '@site/src/components/headline-with-icon';

export const PERFORMANCE_METRICS_V17 = [
    { key: 'time-to-first-insert', name: 'Time to first insert', color: '#FF8BE0' },
    { key: 'insert-documents-500', name: 'Insert 500 docs (bulk)', color: '#ED168F' },
    { key: 'find-by-ids-3000', name: 'Find 3000 docs by ID (bulk)', color: '#FFB3DF' },
    { key: 'serial-inserts-50', name: 'Insert 50 docs (serial)', color: '#DE48B8' },
    { key: 'serial-find-by-id-50', name: 'Find 50 docs by ID (serial)', color: '#b2218b' },
    { key: 'find-by-query', name: 'Find 3000 docs by query', color: '#DA93E5' },
    { key: 'find-by-query-parallel-4', name: 'Find 3000 docs by query (parallel)', color: '#A94FBE' },
    { key: '4x-count', name: 'Count 3000 docs (4x)', color: '#FF59B9' }
];

export const PERFORMANCE_DATA_V17 = [
    {
        name: 'IndexedDB',
        'time-to-first-insert': 5.7,
        'insert-documents-500': 9.67,
        'find-by-ids-3000': 67.7,
        'serial-inserts-50': 18.55,
        'serial-find-by-id-50': 7.9,
        'find-by-query': 58.7,
        'find-by-query-parallel-4': 43.45,
        '4x-count': 18.5,
    },
    {
        name: 'OPFS (Worker)',
        'time-to-first-insert': 27.2,
        'insert-documents-500': 10.32,
        'find-by-ids-3000': 24.5,
        'serial-inserts-50': 7.4,
        'serial-find-by-id-50': 8.25,
        'find-by-query': 21.2,
        'find-by-query-parallel-4': 35.8,
        '4x-count': 2.95,
    },
    {
        name: 'SQLite (node:sqlite)',
        'time-to-first-insert': 5.2,
        'insert-documents-500': 8.62,
        'find-by-ids-3000': 26.41,
        'serial-inserts-50': 10.84,
        'serial-find-by-id-50': 2.67,
        'find-by-query': 19.68,
        'find-by-query-parallel-4': 20.38,
        '4x-count': 2.01,
    }
];

# <HeadlineWithIcon h1 icon={<IconQuickstart />} subtitle="Local-First to the Moon">RxDB 17.0.0</HeadlineWithIcon>

RxDB version 17 focuses on features for Vibe-Coders, **better [reactivity](../reactivity.md)**, **improved debugging and DX-for-LLMs**, performance and **important breaking storage fixes**, while also graduating several long-standing plugins out of beta.

Most applications can upgrade easily, but [**users of OPFS and filesystem-based storages must review the migration notes carefully**](#migration-from-version-16-to-17).

Lets start with the most exciting features...

## <HeadlineWithIcon h2 icon={} subtitle="Sync without Servers">User Provided Sync Endpoints</HeadlineWithIcon>

RxDB 17 introduces two new [replication](../replication.md) plugins: [Google Drive Replication](../replication-google-drive.md) and [Microsoft OneDrive Replication](../replication-microsoft-onedrive.md).

These replication plugins are the future for vibe-coded applications. They allow developers to create fully functional, cross-device applications without hosting any backend servers or managing database infrastructure. Instead of storing user data on a central server, the application syncs directly to the user's own Google or Microsoft account.

Both plugins provide:
- **Zero Backend Required:** Developers avoid server hosting costs and maintenance.
- **Privacy by Default:** Data stays in the user's personal cloud storage.
- **Real-Time Sync:** Data synchronizes instantly across all of the user's devices, keeping their computers, tablets, and phones perfectly up to date in real time.
- **Cross-App Data Sharing:** Multiple applications can easily share and sync data by connecting to the same cloud storage folder.

By using these user-provided sync endpoints, you can build and distribute complex [offline-first](../offline-first.md) applications that scale to any number of users at zero infrastructure cost. Just host your static page on Github Pages, Vercel, Cloudflare or any other static hosting provider. [Read more](../replication-google-drive.md).

## <HeadlineWithIcon h2 subtitle="Make your App AI Agent Ready">WebMCP Plugin</HeadlineWithIcon>

<LinkedinBox url="https://www.linkedin.com/embed/feed/update/urn:li:share:7434623645857046528?collapsed=1" />

RxDB 17 introduces the [WebMCP Plugin](../webmcp.md) to expose RxDB collections to AI Agents via the Web Model Context Protocol.

For years, AI interactions in the browser have relied on two ways: Either the agent renders the page and has to parse the pixels, or it has to guess the html structure. Both methods are expensive and often non-deterministic. Applications supporting WebMCP fix that by telling the Agent exactly what operations are available and how to use them.

> WebMCP provides a formalized machine interface alongside the human interface.

WebMCP is highly effective when paired with a local-first database like RxDB. Instead of hardcoding specific WebMCP tools for each user actions, you can expose the local database which gives AI Agents unlimited generic query and mutation options.

:::info
Are you a YouTuber or Influencer talking about Web Development, Offline-First, or Local-First software? We are looking for creators to collaborate with! Please reach out to us on [Twitter](https://twitter.com/pubkeypubkey) or [Discord](/chat/).
:::

## <HeadlineWithIcon h2 icon={<IconVibeCoding />}>Improvements for our Vibe-Coders</HeadlineWithIcon>

To improve vibe-coding with RxDB, we made the following DX-for-LLM improvements:

- **ADD** [https://rxdb.info/llms.txt](https://rxdb.info/llms.txt) for LLM-friendly documentation access.
- **ADD** `ERROR-MESSAGES.md` to the root of the RxDB package so your LLM knows about all possible errors.
- **ADD** Errors now contain a `cause`, `fix` and `docs` property which tells your LLM what went wrong and where to find information about possible fixes. This prevents LLMs from reaching dead-ends while debugging.
- **ADD** `@example` tags to TypeScript comments in many parts of the typings so Agents know how to use the API without reading the docs.

Also to improve vibe-coding when working with RxDB directly we added the following files:

- **ADD** [.aiexclude](https://developer.android.com/studio/gemini/aiexclude?hl=en) file to reduce context.
- **ADD** [.agent Skill](https://antigravity.google/docs/skills) to verify code changes.
- **ADD** `.claudeignore` file to reduce context.
- **ADD** `.claude/settings.json` to improve post-generation testing.
- **ADD** `CLAUDE.md`

## <HeadlineWithIcon h2 icon={<IconDevicePhone />} subtitle="Faster than SQLite">Expo Filesystem RxStorage</HeadlineWithIcon>

RxDB 17 introduces the [Expo Filesystem RxStorage](../rx-storage-filesystem-expo.md), a high-performance storage backend for React Native and Expo applications. It is built on [expo-opfs](https://www.npmjs.com/package/expo-opfs) and uses the newest Expo Filesystem API. This delivers significant performance gains over SQLite for a wide range of access patterns. Currently I work on making pull requests to the Expo Core repository to further improve the performance of the underlying api. [Read more](../rx-storage-filesystem-expo.md).

<PerformanceChart title="Expo Filesystem vs SQLite (React Native)" data={PERFORMANCE_DATA_EXPO} metrics={PERFORMANCE_METRICS} />

## <HeadlineWithIcon h2 subtitle="Harder, Better, Faster, Stronger">Performance Improvements</HeadlineWithIcon>

RxDB 17 ships with faster reads, faster writes, and lower memory usage across all storage backends. The bulk insert path, query routing, and internal data structures have been reworked to reduce CPU overhead per operation. IndexedDB now stores [attachment](../rx-attachment.md) data in a binary format for smaller on-disk size, and several memory leaks in OPFS and migration code paths have been fixed. [Read more](../rx-storage-performance.md).

<PerformanceChart title="IndexedDB, OPFS & SQLite" data={PERFORMANCE_DATA_V17} metrics={PERFORMANCE_METRICS_V17} />

## Better Framework Integrations

- **ADD** [React plugin](../react.md) for easier React integration with hooks and signals.
- **ADD** new `reactivity-angular` package to use signals in Angular.
- **CHANGE** moved `reactivity-vue` and `reactivity-preact-signals` from premium to core

## Debugging & Developer Experience

- **CHANGE** the documentation search has been migrated to [Algolia DocSearch](https://docsearch.algolia.com/) for better and faster results.
- **ADD** `context` field to all RxDB write errors for easier debugging.
- **ADD** improved OPFS [RxStorage](../rx-storage.md) error logging in `devMode`, including:
  - strict `TextDecoder` mode.
  - detailed decoding error output.
- **ADD** internal `WeakRef` TypeScript types so users no longer need to enable `ES2021.WeakRef`.
- **ADD** `RxDatabase.collections$` observable for reactive access to collections.
- **ADD** docs page about [testing with RxDB](../testing.md).
- **ADD** support for the JavaScript `using` keyword to automatically remove databases in tests.
- **ADD** correctly typed `$$` properties and `get$$()` via HKT-based `ReactivityLambda` pattern. Signals now carry the document data type (e.g. `Signal<number>` instead of `Signal<any>`).
- **ADD** enforce maximum length for indexes and primary keys (`maxLength: 2048`) because big maxLength values impact performance.

## <HeadlineWithIcon h2 icon={<IconExperiment />}>Plugins Graduating from Beta</HeadlineWithIcon>

The following plugins are **no longer in beta** and are now considered production-ready:

- [Replication Appwrite](../replication-appwrite.md)
- [Replication Supabase](../replication-supabase.md)
- [Replication MongoDB](../replication-mongodb.md)
- [RxStorage MongoDB](../rx-storage-mongodb.md)
- [RxStorage Filesystem (Node)](../rx-storage-filesystem-node.md)
- [RxStorage DenoKV](../rx-storage-denokv.md)
- [Attachment replication](../rx-attachment.md)
- [CRDT Plugin](../crdt.md)
- [RxPipeline](../rx-pipeline.md)

## Other Bugfixes, Breaking Changes and Improvements

- **FIX** [OPFS RxStorage](../rx-storage-opfs.md) memory and cleanup leaks
- **FIX** memory-mapped storage not purging deleted documents
- **FIX** `RxCollection.cleanup()` ignoring `minimumDeletedTime`
- **FIX** short primary key lengths not matching replication schema [#7587](https://github.com/pubkey/rxdb/issues/7587)
- **FIX** retry DenoKV commits when encountering `"database is locked"` errors
- **FIX** close broadcast channels and [leader election](../leader-election.md) **after** database shutdown, not during
- **FIX** migration memory leak: old collection meta doc not deleted [#7792](https://github.com/pubkey/rxdb/pull/7792)
- **CHANGE** Store data as binary in IndexedDB to use less disc space.
- **CHANGE** Pull-Only replications no longer store the server metadata on the client.
- **FIX** downstream replication issues [#7804](https://github.com/pubkey/rxdb/pull/7804)
- **FIX** add event guard to count and findByIds in _execOverDatabase [#7864](https://github.com/pubkey/rxdb/pull/7864)
- **FIX** memory leak in migratePromise() [#7787](https://github.com/pubkey/rxdb/pull/7787)
- **FIX** `exclusiveMinimum` and `exclusiveMaximum` TypeScript types corrected from `boolean` to `number` to match JSON Schema Draft 6+ [#7962](https://github.com/pubkey/rxdb/pull/7962)
- **FIX** `find()` with `$in` on the primary key now correctly uses the fast `findDocumentsById` path instead of falling back to a full storage query [#7993](https://github.com/pubkey/rxdb/pull/7993)
- **FIX** DenoKV cleanup deleting index entries with wrong key, causing orphaned indexes and flaky query crashes
- **FIX** Dexie and DenoKV RxStorages throwing errors (`DataError` / "Start key is greater than end key") on query ranges that yield no results (e.g., `$gt` and `$lt` at the same value).
- **ADD** `waitBeforePersist` option to `ReplicationPushOptions` to delay upstream persistence cycles, enabling write batching across collections and CPU-idle deferral [#7872](https://github.com/pubkey/rxdb/issues/7872)
- **CHANGE** `final` schema fields no longer need to be marked as `required`
- **UPDATE** [z-schema](https://github.com/zaggino/z-schema/blob/main/CHANGELOG.md) to version 9.
- **CHANGE** replace `appendToArray()` with `Array.concat()` for better browser-level optimizations
- **CHANGE** optimize the bulk insert hot path by inlining per-document helper calls, replacing `hasOwnProperty` checks, skipping unnecessary cloning on inserts, and using counter-based event IDs
- **ADD** ensure indexes and primary keys are validated consistently across replication schemas
- **CHANGE** Reduce `NON_PREMIUM_COLLECTION_LIMIT` from `16` to `13`.
- **ADD** Support `extendedLifetime` when using the [SharedWorker](../rx-storage-shared-worker.md).
- **FIX** remote-storage WebSocket server crash on client disconnect: handle missing connections, guard `send()` calls, and clean up stale `connectionId` entries [#8042](https://github.com/pubkey/rxdb/pull/8042)
- **FIX** CRDT plugin not blocking `modify()`, `patch()`, `incrementalRemove()`, and `update()` write paths, causing the document data and CRDT operation log to diverge silently [#8075](https://github.com/pubkey/rxdb/pull/8075)
- **FIX** false conflicts on push when using `serverOnlyFields` in the [RxServer](../rx-server.md) plugin, caused by `undefined` values in server-only fields creating phantom keys that broke `deepEqual` comparisons [#8212](https://github.com/pubkey/rxdb/issues/8212)
- **CHANGE** `toggleOnDocumentVisible` now defaults to `true` [#6810](https://github.com/pubkey/rxdb/issues/6810)
- **FIX** query results becoming incorrect when changes occur faster than query update [#7067](https://github.com/pubkey/rxdb/issues/7067)
- **CHANGE** The GitHub repository no longer contains prebuilt `dist` files. Install RxDB from npm or run the build scripts locally if you need them.
- **CHANGE** Some integrations now use optional peer dependencies. You may need to install them manually:
  - `firebase`
  - `mongodb`
  - `nats`

## Migration from version 16 to 17

RxDB 17 is mostly backward-compatible, but please review the following points before upgrading:
If you use any of the following storages, **you must migrate your data** using the [storage migrator](../migration-storage.md):

- OPFS RxStorage
- Filesystem RxStorage (Node)
- [IndexedDB RxStorage](../rx-storage-indexeddb.md) (if you use attachments)

For all other RxStorages, data created with RxDB v16 can be reused directly in RxDB v17 but it is still required to locally test compatibility before upgrading in production.

## You can help!

There are many things that can be done by **you** to improve RxDB:

- Check the [BACKLOG](https://github.com/pubkey/rxdb/blob/master/orga/BACKLOG.md) for features that would be great to have.
- Check the [breaking backlog](https://github.com/pubkey/rxdb/blob/master/orga/before-next-major.md) for breaking changes that must be implemented in the future but where I did not have the time yet.
- Check the [todos](https://github.com/pubkey/rxdb/search?q=todo) in the code. There are many small improvements that can be done for performance and build size.
- Review the code and add tests.
- Tell a friend about RxDB.
