I built a REAL Desktop App with both Tauri and Electron
By Bufferhead
Summary
## Key takeaways - **Electron's Popularity Despite Flaws**: Electron is still the most popular framework for building desktop applications with web technologies, allowing one app to run on every major platform, though it uses a lot of resources and has huge app sizes. [00:00], [00:11] - **Tauri Setup Beats Electron**: Tauri setup is smooth and integrates with modern frameworks like Next.js, SvelteKit, or Vite, while Electron lacks out-of-the-box framework integration and relies on tools like Electron Vite. [01:32], [02:12] - **Tauri Simplifies Event Handling**: Tauri resolves event handling, deep linking, and window communication with one EventEmit and one EventListener, unlike Electron's frustrating inter-process communication through preload scripts. [04:30], [05:24] - **Tauri Bundle Sizes Much Smaller**: Tauri builds are significantly smaller than Electron's across platforms because Tauri uses the system's native browser engine instead of bundling a full Chromium binary. [08:23], [08:50] - **Tauri's Browser Engine Tradeoffs**: Tauri's use of native engines like WebKit on macOS and WebKitGTK on Linux causes debugging issues, lack of extension support, and potential web tech incompatibilities, unlike Electron's consistent Chromium. [09:40], [10:31] - **Electron Chosen Over Tauri**: Despite preferring Tauri's approach to events and deep linking, the team chose Electron due to Tauri's platform inconsistencies and developer experience issues. [11:01], [11:16]
Topics Covered
- Tauri Setup Crushes Electron
- Electron IPC Nightmare vs Tauri Simplicity
- Tauri Bundles Tiny, Inherits System Browsers
- Tauri DX Plagued by WebKit Debugging
- Electron Wins Despite Tauri Promise
Full Transcript
Electron is still the most popular framework for building desktop applications, but a lot of people really hate Electron apps, and there are some really good reasons for that.
It uses a lot of resources and the app sizes are huge.
What makes Electron apps so popular though is the fact that you can simply use web technologies to build one desktop app and use it on every major platform.
But while Electron has been mostly uncontested in recent years, An alternative promises to solve at least some of those problems. Tauri is a somewhat new framework for building desktop applications with web technologies.
It promises to be small, fast and secure.
And as all of that sounded too good to be true, I decided to build my most recent application with both Tauri and Electron.
To find out if Tauri really has what it takes to overthrow the king of desktop apps.
The app I'm gonna build is a desktop application for my open source time tracking projects all the time.
We wanted a web based desktop application so we can simply reuse the components that we already built for the web app.
And this is probably the main reason why Electron is so popular in the first place.
It does not only make development faster, but it also saves companies a lot of money in development time.
Instead of JavaScript as a backend language, Taurii uses Rust.
Which is a little bit of a problem because, well, I do not know Rust, but Tauri provides a lot of JavaScript APIs as well, so as long as you don't need a lot of backend functionality, you should be fine.
At least, that's what people were saying online.
And when have people on the internet ever been wrong?
This all time desktop app will mostly send API requests to our REST API, so we don't need any fancy data handling on the backend.
Let's start with the setup.
With Tauri, the process is really smooth here.
It integrates with a lot of modern frontend frameworks like Next.
js, SvelteKit or Vite, which makes a setup with React, Svelte or Vue pretty straightforward.
You might have to update your Rust version before doing that though.
With Electron on the other hand, the story is a little bit more difficult.
There's no framework integration out of the box.
So you can either use the first party tool Electron Forge, or a community boilerplate like Electron Vite.
I went with Electron Vite, which proved to be a good decision, as Electron Forge recently marked their Vite support retroactively as experimental, which I have honestly never heard before.
Tauri clearly has the second mover advantage here, and was way easier to setup than Electron.
One of the first features that our desktop app needs is a way to log into an existing SolidTime account.
To authenticate our desktop app from our web app, we'll use something called DeepLinks, which I promise has nothing to do with selling illegal drugs online.
Operating systems allow you to register a custom protocol when installing an application.
So instead of HTTP, we can have our very own solid time protocol.
And instead of opening in a browser, this protocol will always open in our desktop application.
Like with any other URL, we can send data along with it using query parameters.
In our case, we will use those parameters to pass the authentication tokens to the desktop app and finally log in the user.
All of this is a little bit of a problem, simply because I use macOS on my primary machine, and Apple hates developers.
Registering those protocols does not work in development mode with both Tauri and Electron, because the app would have to be bundled and signed first.
But that's my fault for taking a bite of the forbidden fruit inside of Apple's walled garden.
For Tauri, there's a plugin to handle deeplinks, and in their most recent version, they even made their plugin first party.
Thankfully, there were only a few lines of code and configs that I had to copy from the docs.
to get it working, because, well, I still do not know Rust.
But the plugin also exposes JavaScript APIs directly, so I can just listen to the deep link right from the frontend.
And this is Tauri's approach to a lot of standard functionality.
The Tauri team seems very much aware of the fact that a lot of people do not run a right Rust code, and provides more and more JavaScript APIs in recent releases.
Electron's approach to this is quite a bit different.
Deep Linking is simply an example in their docs that you have to copy and paste into your application directly.
This includes custom handling for different operating systems and different configurations for whichever packaging tool you're using.
With Tauri's Deep Linking, you don't have to worry about any of that, because the plugin handles platform specific behavior and there's only one packaging tool.
Another thing that you do have to worry about when using Electron is how to send the authentication tokens from the backend to the frontend.
Because while both the backend and the frontend are powered by javascript, for security reasons only the backend has access to certain features.
This includes for example the handling of deep links or managing the visibility of windows.
And if you want to use some of those features in the frontend, you have to use Electron's inter process communication system to send events.
And let me tell you, setting up and sending those events made me feel like I'm in Java Boilerplate Code Hell all over again.
To pass an event from the Electron backend to the frontend, it has to be registered in a preload script first.
This preload script basically defines your API between the frontend and the backend, and it is just there to pass on events.
So we listen for the deep link event on the electron backend, emit an event to the preload script, listen to this event on the preload script just to emit another event to the frontend, where we also have to listen for this event from the preload script.
While you can write your own abstractions to make this a little less repetitive, and it is also important to mention that this is a security feature, it made me wanna smash my screen really bad repeatedly.
And it becomes even more confusing if you want to send an event from one window to another one.
In Electron you have to pass the event through the preload script all the way back to the backend just to send a new event all the way through another preload script back to the other window.
Maybe the most frustrating part is that Tor resolves all of this with just one EventEmit and one EventListener, providing a much smoother experience for event handling overall.
The main reason I had to deal with window to window events in the first place is because the Solid Time Desktop application has a floating window widget.
It allows you to access basic controls for starting and stopping time entries.
So it has to communicate with the main window.
And while I'm at it, let's talk about window management for a second.
With Tauri, you can configure most of the windows options in a simple config file, without having to touch Rust at all.
Electron on the other hand just uses javascript for the configuration.
Both of them were pretty easy to set up and configure.
Where did struggle however is implementing custom window drag areas.
In theory, this should be pretty easy.
For Electron there's a CSS property and for Tauri there's a data attribute.
If you set them on a DOM element and start dragging in this area, it will just drag the entire window.
In Tauri, this does unfortunately not work by default on the first click, if a different window is focused at the time.
Which is really annoying because the solid time widget window can only be dragged with custom drag areas.
And it is also the window that will be dragged around a lot on the first click.
There is a solution for this problem.
You have to add a new permission to the config file for the window, to allow dragging on the initial click.
The problem is, it took me an embarrassingly long time to figure out what is even going on, and I could only find the option buried somewhere in the docs.
You can call this a skill issue, and thankfully the docs have been updated since then.
But it also highlights a bigger problem of Taui overall.
The community is still pretty small, you will find some stackoverflow questions and blogposts explaining basic concepts, but more often than not I ended up searching through code on github to figure out how to fix something.
Electron on the other hand obviously has a huge community, and almost every question that you can ask is already answered somewhere.
A lot of the tooling I ended up using is Actually Electron community tooling as well.
Electron Wheat is a community project and electron builder.
The package and distribution solution I ended up using is a community project as well to make sure that our application runs on all sorts of different operating systems. Both T and Electron have tools to bundle up the application for distribution.
Electron Builder can even do Mighty Platform builds, which means that you can build the application for other operating systems than the one that you're compiling on.
At least as long as you do not rely on any native dependencies and the machine that you're building on is a Mac.
Because the only people that Apple hates more than developers in general are developers who use a platform that is not a Mac.
Torys build system unfortunately does not support building for operating systems other than the one that you're compiling on, as it relies heavily on native dependencies.
This might not be too big of a deal if you have a CI pipeline for distribution, but just being able to build the application for any platform locally and drop it in a VM to test it is a massive quality of life improvement.
When building those apps for different platforms, another difference between Tauri and Electron becomes very obvious.
Bundle size.
As you can see, Taurii builds are significantly smaller in comparison across the board.
Smaller bundle size is one of Taurii's biggest selling points, but the reason for the smaller bundle size has some inconvenient side effects.
Taurii has a completely different approach to browser engines.
While Electron just bundles an entire Chromium binary inside the application, which results in a huge bundle size, Taurii just uses whatever browser is installed on the system by default.
Which means on Windows it will use Edge's Blink, which is basically Chromium, on MacOS it will use Safari's WebKit, which some consider to be the new Internet Explorer, and on Linux it will use something called WebKit GTK, which you might not even have heard of before.
It is a custom WebKit engine port that ships with most Linux distributions.
Most of the UI components for the Solitaire desktop app are shared with the web app, so they should be decently optimized for all major browsers already.
But with WebKit GTK, we would have to support yet another browser engine, especially one that is not known for its great support for modern web technology.
And it also doesn't help that Safari's WebKit engine on Mac only updates when you update the entire operating system.
Why do you hate developers, Apple?
Why can you not be a little bit more like him?
Developers!
Developers!
Developers!
Developers!
Developers!
the browser.
Those different browser engines do not only affect user experience, but developer experience as well, especially when it comes to debugging.
Because Tauri just uses whatever browser engine you have installed, you're stuck with the debugging tools of that engine.
For me, that's Safari's WebKit.
And oh my god.
Those debugging tools are not great.
This was especially frustrating when testing offline mode.
In Chrome, you can simply set in the website to offline mode, but in Safari, you can not.
Also, if you rely on browser extensions in your development process, you will have a bad time with Taurii on every system.
While Electron has at least a limited support for Chrome extensions.
Tauri does not support any browser extensions at all.
But there are also good news.
The team behind Tauri is aware of the problems related to the different browser engines and is actively looking for alternatives.
One of them might be Servo, an embeddable Rust based browser engine, but it might still take a while before it becomes stable enough to power Atari desktop applications.
Another alternative that they are looking into is the Chromium embeddable framework.
As much as I would love to say that we use Rust by the way, in the end the inconsistencies between platforms and the developer experience just wasn't worth it and we will go with Electron for now.
But if Tauri continues to evolve, we'll see.
I'm happy to go back and port the application to Tauri.
I much prefer their approach to events and basic functionality like deep linking.
And there are also applications where I think Tauri in its current state can be a good fit.
If you already have a lot of experience with Rust and the application is very back end heavy with a minimal front end, Tauri will probably work just fine for you.
And if you don't need cross platform support, Or at least no support for Linux.
A lot of the issues I mentioned earlier will not impact you as much.
Taurii also recently launched a new version 2.
0, which I only tried for a short period before release, but it promises a lot of new exciting features like builds for Android and iOS.
If you want to check out the first version of the SolidTime Desktop App, you can sign up for SolidTime, the open source time tracker for your freelancer agency work, at solidtime.
io.
The desktop app itself is of course also open source, and you can find the link to the GitHub repository linked in the description down below.
If you enjoyed the video, please make sure to leave a like and subscribe if you want to see more content like this.
And maybe check out my video on how to host an open source uptime monitor on GitHub completely for free.
See you in the next video.
Loading video analysis...