Skip to content

WIP: Tauri SDK#902

Draft
simolus3 wants to merge 14 commits intomainfrom
tauri-plugin
Draft

WIP: Tauri SDK#902
simolus3 wants to merge 14 commits intomainfrom
tauri-plugin

Conversation

@simolus3
Copy link
Contributor

@simolus3 simolus3 commented Mar 18, 2026

This adds a Tauri SDK and demo application (see #873 for an initial discussion and motivation). Tauri is a cross-platform app library that works by having a Rust process open windows using the system's webview and then letting JavaScript invoke Rust through an IPC mechanism.

Architecture

Like all Tauri plugins, the SDK is split into a JavaScript package (@powersync/tauri-plugin) and a Rust crate (tauri-plugin-powersync). Users would depend on both to use it (the readme from the new package explains the necessary steps).
Tauri works through inter-process communication: For JavaScript to call Rust, we register commands in Rust that the JavaScript SDK can invoke through tauri APIs. Table and sync status updates are broadcast from Rust using Tauri's event mechanism (all windows would receive all updates, the SDK interprets them and invokes listeners).

Tauri has a weird permission system generating thousands of lines of JSON for access control to commands. In our SDK, we have a single command for opening and accessing databases and it's enabled by default. We might want to provide more granual restrictions in the future, but users can always remove default permissions as well so I don't think this default is inappropriate.

The PowerSync command exposes the following functionality to JavaScript:

  1. Opening databases, acquiring connections, executing SQL.
  2. Subscribing to Sync Streams.
  3. Getting the current sync status.

That's it! The rest of the SDK is implemented through @powersync/common and should work with existing APIs. Also, there are two Tauri-specific APIs:

  1. The database location can be resolved asynchronously (making it easier to open database instances synchronously since Tauri has an async method to resolve a suitable directory).
  2. There's a way to get a "handle" from a PowerSyncTauriDatabase instance that users can pass to their own Rust code. This allows their Rust app to re-use a database instance that has originally been opened in JavaScript.

Testing

Unfortunately, testing Tauri plugins is quite difficult:

  1. Both JavaScript and Rust sources can be tested independently by mocking the other half. IMHO, these tests are mostly useless because the intersection of those two is pretty much the only thing we want to cover.
  2. Tauri provides a webdriver-based approach for tests we could use, but that doesn't work on macOS. So it will be tricky for most of us to run that locally.

So at the moment, the SDK is untested. Of course, both the Rust and the JS SDK have plenty of tests on their own so it's only the protocol between Rust and JS that would benefit from tests. I've tested this manually through the demo app so far.

Limitations

Generally, everything our JavaScript SDK has to offer should be available. Currently, there's the notable exception that db.connect() doesn't work. We really want the sync to be driven in Rust for it to work across windows, and exposing a JS backend connector instance to Rust via IPC is very tricky. So for now, users would have to obtain a Rust database handle from JS and then call connect() in Rust (and also implement their connector in Rust).

Releasing

Initially, I thought we want to keep versions of the Rust crate and the JavaScript package in sync. But thinking about this some more, I don't think that's required: We update our JavaScript packages all the time, including every time @powersync/common is updated. But without any changes to the Rust code, we don't need to update the crate too. Newer versions of the JavaScript package would continue to work with older Rust code as well.

I hope changes affecting Rust code (and in particular the IPC scheme between JS and Rust) would be relatively rare. Since we have no way of expressing in JavaScript that we need a particular version of the Rust crate (and vice-versa), this would likely be a breaking change every time. I've setup tag-based automated publishing to crates.io, we'd just have to do that manually when we need it.

Demo

Bildschirmaufnahme.2026-03-18.um.18.02.42.mov

Our standard todo app in Tauri (could perhaps use some CSS 😆). Sync Streams, the sync status and queries are synced between all windows, even though those run multiple independent webviews.

TODO:

  • Wait for API improvements for Tauri SDK powersync-native#11 and 0.0.5 of the Rust SDK, remove my local dependency patch.
  • Publish the initial version of the crate and configure trusted publishing.
  • Publish the initial version of the JS package and configure trusted publishing.

@changeset-bot
Copy link

changeset-bot bot commented Mar 18, 2026

⚠️ No Changeset found

Latest commit: ca79002

Merging this PR will not cause a version bump for any packages. If these changes should not result in a new version, you're good to go. If these changes should result in a version bump, you need to add a changeset.

This PR includes no changesets

When changesets are added to this PR, you'll see the packages that this PR includes changesets for and the associated semver types

Click here to learn what changesets are, and how to add one.

Click here if you're a maintainer who wants to add a changeset to this PR

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant