<?xml version="1.0" encoding="UTF-8"?>
<rss version="2.0" xmlns:atom="http://www.w3.org/2005/Atom" xmlns:dc="http://purl.org/dc/elements/1.1/">
  <channel>
    <title>DEV Community: irène</title>
    <description>The latest articles on DEV Community by irène (@ir3ne).</description>
    <link>https://dev.to/ir3ne</link>
    <image>
      <url>https://media2.dev.to/dynamic/image/width=90,height=90,fit=cover,gravity=auto,format=auto/https:%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Fuser%2Fprofile_image%2F1058728%2Fffebb1b0-fb0a-418d-b448-bb42f64a4552.JPG</url>
      <title>DEV Community: irène</title>
      <link>https://dev.to/ir3ne</link>
    </image>
    <atom:link rel="self" type="application/rss+xml" href="https://dev.to/feed/ir3ne"/>
    <language>en</language>
    <item>
      <title>Building a bookmark manager on top of the browser's own bookmark tree — no bookmark database required</title>
      <dc:creator>irène</dc:creator>
      <pubDate>Tue, 25 Aug 2026 15:06:26 +0000</pubDate>
      <link>https://dev.to/ir3ne/building-a-bookmark-manager-on-top-of-the-browsers-own-bookmark-tree-no-bookmark-database-gkb</link>
      <guid>https://dev.to/ir3ne/building-a-bookmark-manager-on-top-of-the-browsers-own-bookmark-tree-no-bookmark-database-gkb</guid>
      <description>&lt;p&gt;When I started building &lt;a href="https://bookma.sh/" rel="noopener noreferrer"&gt;Bookmash&lt;/a&gt;, one architectural decision shaped almost everything else: &lt;strong&gt;the browser stays the source of truth.&lt;/strong&gt;&lt;/p&gt;

&lt;p&gt;No import step. No Bookmash-side copy of your bookmarks. The extension talks directly to the browser's native bookmarks API, and the dashboard reads and writes through that same layer.&lt;/p&gt;

&lt;p&gt;Bookmash doesn't store your bookmarks, or its own representation of them, in a database. The only user data stored server-side is what's needed for the account itself, such as the user's email to give access to the dashboard.&lt;/p&gt;

&lt;p&gt;That constraint sounds simple. It wasn't free because of how browser's bookmark tree is handled.&lt;/p&gt;

&lt;p&gt;Here's what it meant when building features like Collections and MyMash without introducing a second bookmark model.&lt;/p&gt;

&lt;h2&gt;
  
  
  The problem with the native bookmark tree
&lt;/h2&gt;

&lt;p&gt;Chrome and Firefox expose bookmarks as a tree through their extension APIs.&lt;/p&gt;

&lt;p&gt;That tree reflects the browser's own structure: bookmarks live inside folders, which in turn live under browser-defined roots such as the bookmarks bar and other bookmarks.&lt;/p&gt;

&lt;p&gt;For example:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;Browser bookmarks

├── Bookmarks Bar
│   ├── Development
│   └── Daily
│
└── Other Bookmarks
    ├── Design
    └── Research
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;That separation makes sense for the browser UI, but it doesn't necessarily represent how I want to navigate those bookmarks inside another interface.&lt;/p&gt;

&lt;p&gt;I wanted Bookmash to provide a different view over that same data without reorganizing it into a Bookmash-specific structure.&lt;/p&gt;

&lt;p&gt;That meant the problem wasn't:&lt;/p&gt;

&lt;blockquote&gt;
&lt;p&gt;How do I import this tree into Bookmash?&lt;/p&gt;
&lt;/blockquote&gt;

&lt;p&gt;It was:&lt;/p&gt;

&lt;blockquote&gt;
&lt;p&gt;How do I derive a more useful interface from the tree that already exists?&lt;/p&gt;
&lt;/blockquote&gt;

&lt;h2&gt;
  
  
  Collections: a view computed from the tree
&lt;/h2&gt;

&lt;p&gt;Bookmash reads the current bookmark tree from the browser and runs a flattening operation over it.&lt;/p&gt;

&lt;p&gt;Conceptually:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;Browser tree

Bookmarks Bar
├── Development
└── Daily

Other Bookmarks
├── Design
└── Research

        ↓ flatten

Bookmash

├── Development
├── Daily
├── Design
└── Research
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;The browser's top-level separation disappears from the Bookmash view, while the meaningful folder hierarchy underneath it remains intact.&lt;/p&gt;

&lt;p&gt;Nothing needs to be copied into a Bookmash database to make that happen.&lt;/p&gt;

&lt;p&gt;The Collection view is the result of an operation over the current tree.&lt;/p&gt;

&lt;p&gt;Every time Bookmash needs that view, it starts with what the browser says exists now and derives the representation from it.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Farticles%2Fka9oprczkhz9uhepj6d7.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Farticles%2Fka9oprczkhz9uhepj6d7.png" alt="Bookmash Collections view showing folders from the browser bookmark tree" width="800" height="479"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;If a folder is renamed, moved or deleted using the browser itself, Bookmash doesn't have a second version of that folder to reconcile.&lt;/p&gt;

&lt;p&gt;It reads the tree again. This approach makes the dashboard always fresh.&lt;/p&gt;

&lt;p&gt;There is no:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;browser state
      ↕
sync layer
      ↕
Bookmash bookmark state
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;There is only:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;browser state
      ↓
Bookmash view
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;That distinction ended up removing an entire category of synchronization problems.&lt;/p&gt;

&lt;h2&gt;
  
  
  The cost: computation moves to read time
&lt;/h2&gt;

&lt;p&gt;Of course, not storing a derived bookmark model doesn't make the work disappear.&lt;/p&gt;

&lt;p&gt;It moves the work.&lt;/p&gt;

&lt;p&gt;A more traditional architecture could normalize the bookmark tree once, store the result, index it and query that representation later.&lt;/p&gt;

&lt;p&gt;Bookmash instead reads the current tree and transforms it when it needs to display it.&lt;/p&gt;

&lt;p&gt;So the trade-off becomes:&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;store and synchronize state on writes&lt;/strong&gt;&lt;/p&gt;

&lt;p&gt;versus&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;recompute a view from the source on reads.&lt;/strong&gt;&lt;/p&gt;

&lt;p&gt;I chose the second.&lt;/p&gt;

&lt;p&gt;For bookmark-sized datasets, the cost has been small enough that I prefer doing the computation to maintaining another stateful representation of data that already exists somewhere else.&lt;/p&gt;

&lt;p&gt;If that assumption ever stops being true, the performance side can be revisited.&lt;/p&gt;

&lt;p&gt;But I didn't want to introduce synchronization complexity before there was a reason to.&lt;/p&gt;

&lt;h2&gt;
  
  
  MyMash follows the same idea
&lt;/h2&gt;

&lt;p&gt;MyMash is Bookmash's quick-access view for bookmarks you use frequently.&lt;/p&gt;

&lt;p&gt;The important part architecturally is that adding something to MyMash doesn't create a second copy of that bookmark in a Bookmash database.&lt;/p&gt;

&lt;p&gt;The bookmark remains part of the browser's native bookmark structure.&lt;/p&gt;

&lt;p&gt;MyMash is another way of presenting and accessing that structure through Bookmash rather than a separate library of bookmarks owned by the application.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Farticles%2Fewwcz2xv3exnscd30jch.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Farticles%2Fewwcz2xv3exnscd30jch.png" alt="MyMash quick-access view for frequently used browser bookmarks" width="800" height="479"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;That distinction matters because I wanted features like MyMash to change &lt;strong&gt;how you interact with your bookmarks&lt;/strong&gt;, not where your bookmarks live.&lt;/p&gt;

&lt;p&gt;The browser still owns the bookmark data.&lt;/p&gt;

&lt;p&gt;Bookmash provides another interface over it.&lt;/p&gt;

&lt;h2&gt;
  
  
  Chrome and Firefox: similar APIs don't mean identical behavior
&lt;/h2&gt;

&lt;p&gt;One thing I underestimated was how much browser-specific behavior would still matter.&lt;/p&gt;

&lt;p&gt;Chrome and Firefox expose comparable bookmark APIs, so initially I expected most tree-related bugs to reproduce in roughly the same way.&lt;/p&gt;

&lt;p&gt;They didn't.&lt;/p&gt;

&lt;p&gt;Folder-structure edge cases and the behavior around bookmark updates were different enough that the same transformation logic could surface problems in one browser and not the other.&lt;/p&gt;

&lt;p&gt;So "works in Chrome" was never a safe proxy for "works in Firefox," even when both implementations were built around the same basic WebExtensions model.&lt;/p&gt;

&lt;p&gt;That reinforced another part of the architecture: the transformation layer should make as few assumptions as possible about what the tree &lt;em&gt;should&lt;/em&gt; look like.&lt;/p&gt;

&lt;p&gt;Read what the browser gives you, normalize what the UI actually needs, and preserve the underlying structure everywhere else.&lt;/p&gt;

&lt;h2&gt;
  
  
  Why this mattered more than it might seem
&lt;/h2&gt;

&lt;p&gt;None of this is about avoiding a database out of purity.&lt;/p&gt;

&lt;p&gt;Bookmash has server-side concerns — authentication, for example — where persistent storage makes perfect sense.&lt;/p&gt;

&lt;p&gt;Bookmarks are different.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;The browser already stores them. Bookmash doesn't need to store them again.&lt;/strong&gt;&lt;/p&gt;

&lt;p&gt;The moment Bookmash stores its own copy of the bookmark structure, it takes on responsibility for keeping that copy correct relative to a tree the user can change without going through Bookmash at all.&lt;/p&gt;

&lt;p&gt;They can edit it from the native bookmark manager.&lt;/p&gt;

&lt;p&gt;Another extension can change it.&lt;/p&gt;

&lt;p&gt;Browser sync can change it.&lt;/p&gt;

&lt;p&gt;Bookmash would then need to decide which state is current and how discrepancies should be resolved.&lt;/p&gt;

&lt;p&gt;By treating the browser tree as the source of truth and computing Bookmash's views from it, that synchronization problem largely disappears.&lt;/p&gt;

&lt;p&gt;The trade-off is that more work happens when the data is read.&lt;/p&gt;

&lt;p&gt;And that's the architectural lesson I've taken from building it:&lt;/p&gt;

&lt;blockquote&gt;
&lt;p&gt;&lt;strong&gt;If you're building a UI on top of data that already has an authoritative owner, think carefully before creating your own representation of that data.&lt;/strong&gt;&lt;/p&gt;
&lt;/blockquote&gt;

&lt;p&gt;You can store your own model and own the synchronization problem.&lt;/p&gt;

&lt;p&gt;Or you can derive your model from the source of truth and own the computation problem.&lt;/p&gt;

&lt;p&gt;For Bookmash, I chose the second.&lt;/p&gt;

&lt;p&gt;So far, it's been the simpler problem to own.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Farticles%2Fryikd9849r5szq1g9pyg.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.us-east-2.amazonaws.com%2Fuploads%2Farticles%2Fryikd9849r5szq1g9pyg.png" alt="Bookmash bookmark manager interface showing existing browser bookmarks" width="799" height="422"&gt;&lt;/a&gt;&lt;/p&gt;




&lt;p&gt;&lt;a href="https://bookma.sh/" rel="noopener noreferrer"&gt;Bookmash&lt;/a&gt; is a bookmark manager for Chrome and Firefox built around this architecture. There's also a &lt;a href="https://bookma.sh/demo" rel="noopener noreferrer"&gt;public demo&lt;/a&gt; if you want to see how the browser tree is presented without installing anything.&lt;/p&gt;

&lt;p&gt;I'm also happy to write a follow-up about the extension-to-dashboard communication layer or the differences I ran into between Chrome and Firefox.&lt;/p&gt;

</description>
      <category>webdev</category>
      <category>javascript</category>
      <category>architecture</category>
      <category>extensions</category>
    </item>
    <item>
      <title>JavaScript Questions and Answers - core concepts</title>
      <dc:creator>irène</dc:creator>
      <pubDate>Sat, 23 Mar 2024 07:16:47 +0000</pubDate>
      <link>https://dev.to/ir3ne/javascript-questions-and-answers-core-concepts-46ll</link>
      <guid>https://dev.to/ir3ne/javascript-questions-and-answers-core-concepts-46ll</guid>
      <description>&lt;p&gt;Hey! I want to share this collection of JavaScript core concepts. &lt;br&gt;
I created a repository for it and every contribution will be appreciated.&lt;/p&gt;

&lt;p&gt;The repository link: &lt;a href="https://github.com/ir3ne/javascript-questions-and-answers" rel="noopener noreferrer"&gt;Welcome to JavaScript Questions and Answers&lt;/a&gt;&lt;/p&gt;

&lt;h2&gt;
  
  
  Intro
&lt;/h2&gt;

&lt;p&gt;This is a collection of the concepts I have encountered throughout my career's path and the questions I have asked about them. Some questions might seem redundant but the purpose of this is to investigate, where present, the connections between different concepts that make this language so interesting and flexible. There are also practical examples of topics whose definition is known but perhaps have never been used in practice. These questions and answers can be used to prepare for an interview or for personal study and lecture.&lt;/p&gt;

&lt;p&gt;In writing the answers I was helped by AI and the book "JavaScript: The Definitive Guide" by David Flanagan.&lt;/p&gt;

&lt;h2&gt;
  
  
  Motivation
&lt;/h2&gt;

&lt;p&gt;I've encountered many times a list of questions and answers written for preparing an interview. I began to get the feeling that the answers were accurate but that the concepts were not connected.&lt;br&gt;
In the real world when we use JavaScript at work or for one of our projects it is important to understand the connection of the concepts between them. For example: what is the connection between closures and high order function? How important is the comprehension of all the event flow phases in order to understand a single event?&lt;/p&gt;

&lt;p&gt;See the connections is decisive for completing a task in the most efficient way, that's because you can understand WHY and not only HOW to do a thing in a determined way.&lt;/p&gt;

&lt;h2&gt;
  
  
  Additions
&lt;/h2&gt;

&lt;p&gt;You can find in this repository some practical example of some concept like Proxy. You can find the definition of it but have you have used it in practice? You can find practical  usages for that and understand, in some cases, you can use it as a store instead of installing new state managers.&lt;/p&gt;

&lt;h2&gt;
  
  
  Contributions
&lt;/h2&gt;

&lt;p&gt;As mentioned, this repository is open to contributions. The only thing to have in mind is the purpose is to explore the nature of a concept and not only to add a definition of it.&lt;br&gt;
I hope this can be useful for someone of you as it was for me to ask myself these questions.&lt;/p&gt;

&lt;p&gt;So, &lt;a href="https://github.com/ir3ne/javascript-questions-and-answers" rel="noopener noreferrer"&gt;Welcome to JavaScript Questions and Answers&lt;/a&gt;! 🤓&lt;/p&gt;

</description>
      <category>javascript</category>
      <category>interview</category>
      <category>webdev</category>
      <category>programming</category>
    </item>
  </channel>
</rss>
