In this post, I explain how I solved the challenge of syncing notes between devices offline. Using a comparison algorithm and a mobile-first design, I built a tool to manage and merge changes seamlessly. The result? A simple, efficient solution that lets me merge notes with just a few clicks.
Why importing data is complex
Imagine you have data on your device, every day you make new changes, you will add, update, and remove data. After some time, you want to move your data to another device, so you will import and add all the data, that part is simple.
The problem comes here: when making changes on both devices, some days you will work on one and some days you will work on the other. Then, you want to have all the data on both devices, but you need to manage and compare, one by one, what is added, what is removed, and what is updated, and where it’s updated. Sometimes, you need to modify the data to make the changes make sense. That process could be tedious and time-consuming, especially if you have a lot of data.
That’s why software like Git provides merge tools, which give a view of the files added, updated, and removed, and when there are updates, you can see, line by line, what has changed.
What was the problem
The problem was happening on my Royal Palace app. I had been taking notes on my desktop when I was at home, and I used to read them on my mobile when I was out. But in some cases, I needed to take new notes, so my notes were not synchronized, and I needed to spend some time to get the latest version of my notes on my devices.
Since Royal Palace is a completely offline application, we cannot rely on the server for synchronization (which could create a cost and would require authentication), similar to applications like Notion and Figma.
The research
I’ve been using VS Code for a long time, and I love its merge tool, which helped me synchronize changes from a server to local. So, I started researching how it was implemented. There is a Meyers Algorithm, which takes two strings and builds a comparison matrix where we have distance calculations between the strings. We can navigate through the distances to understand what part was added, what part was updated, and what part was removed.
The obstacles
- Test the algorithm with real data and different use cases (I didn’t want to set up the app with real data too many times as it required a lot of time).
- Allowing the user to create mixed solutions (As a user, I would like to choose parts of the current note and the imported note).
- Displaying on small screens (How would I display all the comparison data on mobile to make it useful?).
The solution
I implemented the algorithm and tested it with two strings. Then I needed to test it with real data, so I built an internal tool where I defined sets of notes to simulate the current notes and imported notes, simulating multiple use cases, see a demo here.
Then, I compared the notes based on their content to determine if they required detailed analysis (difference line by line with Meyers’ algorithm).
Current Note | Imported Note | Result |
---|---|---|
Note A | Note A | Similar content |
Note B | Note B | Different content (analyzed in detail) |
Note A | - | Note A was removed |
- | Note B | Note B was added |
After this, I had the comparison by lines only for notes which had different content. Then, I needed to consider the possibility of making mixed solutions. I could not modify Note A or Note B directly, so modiyied data structures with an aditional Note C where I save the result. Here, changes could be made in any way and restored if needed (I will add more options to build mixed solutions in the future).
Finally, in the internal merge tool, I realized I had a lot of data, but I needed to think mobile-first to make it useful. If I didn’t find the right solution, all the effort would be wasted. I remembered the mobile version of Wikipedia, where they display a lot of data in collapsible cells. It was easy to navigate through the titles and focus on a small section. I took that approach and added more contrast only to the parts the user should validate.
After many unit tests and manual tests, I deployed it 🚀.
The results
I deployed the solution and went to sleep. The next day, I needed to synchronize my notes on my mobile, so I imported, forgetting the new functionality. I noticed, on the screen, a summary of the important notes where I could see what was updated, what was added, and what was removed. Finally, I proceeded to review only the updated ones and chose which changes to keep.
Conclusion: some few clicks and I merged them 🤘.
Now I think this opens up possibilities for implementing more powerful functionalities over the merge tool. We will see what new ideas come in the future.