<?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: Yasin ATEŞ</title>
    <description>The latest articles on DEV Community by Yasin ATEŞ (@yasinatesim).</description>
    <link>https://dev.to/yasinatesim</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.amazonaws.com%2Fuploads%2Fuser%2Fprofile_image%2F352012%2F19832fb3-282b-47a1-a109-22e6caff2a8a.jpg</url>
      <title>DEV Community: Yasin ATEŞ</title>
      <link>https://dev.to/yasinatesim</link>
    </image>
    <atom:link rel="self" type="application/rss+xml" href="https://dev.to/feed/yasinatesim"/>
    <language>en</language>
    <item>
      <title>Atomic Design in Practice: React and Storybook from Scratch 🧩</title>
      <dc:creator>Yasin ATEŞ</dc:creator>
      <pubDate>Tue, 07 Apr 2026 19:17:20 +0000</pubDate>
      <link>https://dev.to/yasinatesim/atomic-design-in-practice-react-and-storybook-from-scratch-2gkh</link>
      <guid>https://dev.to/yasinatesim/atomic-design-in-practice-react-and-storybook-from-scratch-2gkh</guid>
      <description>&lt;p&gt;Frontend projects can get messy fast as they scale. That's exactly where &lt;strong&gt;Atomic Design&lt;/strong&gt; comes in — a methodology for building UIs in a layered, controlled way. In this article, we'll cover Atomic Design from the ground up, then translate it into a real mini-project using &lt;strong&gt;React&lt;/strong&gt; and &lt;strong&gt;Storybook&lt;/strong&gt;.&lt;/p&gt;

&lt;h2&gt;
  
  
  🧩 What Is Atomic Design?
&lt;/h2&gt;

&lt;p&gt;Atomic Design is a methodology that proposes building UIs by starting from small, reusable building blocks and progressively composing them into larger structures. &lt;strong&gt;Brad Frost&lt;/strong&gt; was the first to systematize this approach, and today it's especially common in design system work.&lt;/p&gt;

&lt;p&gt;Why does it matter? Because in most projects, components start out innocent enough and then spiral into chaos with names like &lt;code&gt;HeaderFinal&lt;/code&gt;, &lt;code&gt;ProductCardNew&lt;/code&gt;, and &lt;code&gt;ProductCardUpdated&lt;/code&gt;. Atomic Design gives us a shared, unambiguous vocabulary to fight that entropy.&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.amazonaws.com%2Fuploads%2Farticles%2Fze1l1y0k4um8bfuw7cgr.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.amazonaws.com%2Fuploads%2Farticles%2Fze1l1y0k4um8bfuw7cgr.png" alt="Atomic design layers" width="720" height="402"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;Atomic Design is organized around five layers:&lt;/p&gt;

&lt;p&gt;★ &lt;strong&gt;Atom&lt;/strong&gt;&lt;br&gt;
The smallest UI building blocks at the HTML level. A &lt;code&gt;button&lt;/code&gt;, &lt;code&gt;input&lt;/code&gt;, &lt;code&gt;label&lt;/code&gt;, or a tiny &lt;code&gt;badge&lt;/code&gt; all live here.&lt;/p&gt;

&lt;p&gt;★ &lt;strong&gt;Molecule&lt;/strong&gt;&lt;br&gt;
Small groups of atoms working together to perform a meaningful task. A search box (&lt;code&gt;input + button&lt;/code&gt;) is a classic example.&lt;/p&gt;

&lt;p&gt;★ &lt;strong&gt;Organism&lt;/strong&gt;&lt;br&gt;
Larger, more meaningful UI sections composed of molecules and atoms. &lt;code&gt;Header&lt;/code&gt;, &lt;code&gt;ProductCard&lt;/code&gt;, and &lt;code&gt;Sidebar&lt;/code&gt; are good examples.&lt;/p&gt;

&lt;p&gt;★ &lt;strong&gt;Template&lt;/strong&gt;&lt;br&gt;
Defines the skeleton of a page. Focuses on layout, not content.&lt;/p&gt;

&lt;p&gt;★ &lt;strong&gt;Page&lt;/strong&gt;&lt;br&gt;
A template filled with real data. This is what the user actually sees.&lt;/p&gt;

&lt;p&gt;Worth pausing here: Atomic Design is &lt;strong&gt;not&lt;/strong&gt; just a folder-naming convention. The real goal is to separate UI responsibilities across layers and draw clear boundaries between each one.&lt;/p&gt;


&lt;h2&gt;
  
  
  🤔 Why Does It Matter?
&lt;/h2&gt;

&lt;p&gt;Imagine you're building an e-commerce app. Your homepage, category page, campaign page, and favorites screen all share very similar cards, buttons, filter areas, and header structures.&lt;/p&gt;

&lt;p&gt;If you don't organize these pieces systematically from the start, you'll soon find yourself carrying four slightly different versions of the same component. That slows down refactoring, makes testing harder, and stretches onboarding time.&lt;/p&gt;

&lt;p&gt;Here's why I reach for this approach:&lt;/p&gt;

&lt;p&gt;★ &lt;strong&gt;Reusability increases&lt;/strong&gt;&lt;br&gt;
An atom or molecule written once can be reused across different pages.&lt;/p&gt;

&lt;p&gt;★ &lt;strong&gt;Maintenance cost drops&lt;/strong&gt;&lt;br&gt;
When a design change comes in, you don't have to hunt through every file.&lt;/p&gt;

&lt;p&gt;★ &lt;strong&gt;Team communication gets clearer&lt;/strong&gt;&lt;br&gt;
The moment you can say "Is this an organism or a molecule?" you've established a shared language.&lt;/p&gt;

&lt;p&gt;★ &lt;strong&gt;It pairs beautifully with Storybook&lt;/strong&gt;&lt;br&gt;
Developing and testing components in isolation becomes much easier.&lt;/p&gt;

&lt;p&gt;★ &lt;strong&gt;Building a design system becomes tractable&lt;/strong&gt;&lt;br&gt;
Your UI library grows in a controlled way, not a chaotic one.&lt;/p&gt;

&lt;p&gt;Bottom line: Atomic Design doesn't just bring order, it brings &lt;strong&gt;long-term velocity&lt;/strong&gt;.&lt;/p&gt;


&lt;h2&gt;
  
  
  ⚛️ How Should You Think About Atomic Design in React?
&lt;/h2&gt;

&lt;p&gt;&lt;strong&gt;React&lt;/strong&gt; is a component-based JavaScript library for building UIs, which makes it a natural fit for Atomic Design. Here's how the layers map onto React:&lt;/p&gt;

&lt;p&gt;★ &lt;strong&gt;Atom&lt;/strong&gt; = Pure, small, self-contained component&lt;br&gt;
Examples: &lt;code&gt;Button&lt;/code&gt;, &lt;code&gt;Input&lt;/code&gt;&lt;/p&gt;

&lt;p&gt;★ &lt;strong&gt;Molecule&lt;/strong&gt; = Small, purposeful UI combination&lt;br&gt;
Example: &lt;code&gt;SearchBox&lt;/code&gt;&lt;/p&gt;

&lt;p&gt;★ &lt;strong&gt;Organism&lt;/strong&gt; = A larger block responsible for a specific feature area&lt;br&gt;
Examples: &lt;code&gt;Header&lt;/code&gt;, &lt;code&gt;ProductCard&lt;/code&gt;&lt;/p&gt;

&lt;p&gt;★ &lt;strong&gt;Template&lt;/strong&gt; = The layout skeleton of a page&lt;br&gt;
Example: &lt;code&gt;MainLayout&lt;/code&gt;&lt;/p&gt;

&lt;p&gt;★ &lt;strong&gt;Page&lt;/strong&gt; = The screen that works with real data and state&lt;br&gt;
Example: &lt;code&gt;HomePage&lt;/code&gt;&lt;/p&gt;

&lt;p&gt;One critical point: not every large component has to be an organism. Sometimes a clean, simple &lt;code&gt;Card&lt;/code&gt; stays comfortably at the molecule level. When deciding on a layer, look at &lt;strong&gt;responsibility&lt;/strong&gt;, not size.&lt;/p&gt;


&lt;h2&gt;
  
  
  🛠️ Setting Up the Project
&lt;/h2&gt;

&lt;p&gt;Enough theory, let's get our hands dirty. We'll scaffold a base React project first, then add Storybook to enable a component-driven development workflow.&lt;/p&gt;
&lt;h3&gt;
  
  
  Step 1: Scaffold the React project
&lt;/h3&gt;

&lt;p&gt;&lt;strong&gt;Vite&lt;/strong&gt; is a frontend toolchain that provides a fast dev server and a modern build experience. The commands below create a new React project and spin it up locally.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;npm create vite@latest atomic-design-react &lt;span class="nt"&gt;--&lt;/span&gt; &lt;span class="nt"&gt;--template&lt;/span&gt; react
&lt;span class="nb"&gt;cd &lt;/span&gt;atomic-design-react
npm &lt;span class="nb"&gt;install
&lt;/span&gt;npm run dev
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Key parts:&lt;/p&gt;

&lt;p&gt;★ &lt;code&gt;npm create vite@latest&lt;/code&gt; generates the new project scaffold.&lt;br&gt;
★ &lt;code&gt;--template react&lt;/code&gt; selects the preconfigured React template.&lt;br&gt;
★ &lt;code&gt;npm run dev&lt;/code&gt; starts the development server.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Expected result:&lt;/strong&gt; A blank React application running in your browser.&lt;/p&gt;
&lt;h3&gt;
  
  
  Step 2: Add Storybook
&lt;/h3&gt;

&lt;p&gt;&lt;strong&gt;Storybook&lt;/strong&gt; is a tool that lets you develop and document UI components in isolation, independent of your application.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;npx storybook@latest init
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Once installation is complete, launch Storybook with:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;npm run storybook
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;A few things worth noting:&lt;/p&gt;

&lt;p&gt;★ The &lt;code&gt;init&lt;/code&gt; command analyzes your project structure and auto-generates the necessary config files.&lt;br&gt;
★ &lt;code&gt;npm run storybook&lt;/code&gt; lets you view components in a dedicated, sandboxed environment.&lt;br&gt;
★ This setup is especially powerful for verifying each atomic layer in isolation.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Expected result:&lt;/strong&gt; The Storybook UI opens in your browser and displays some example stories.&lt;/p&gt;


&lt;h2&gt;
  
  
  📁 Setting Up the Folder Structure
&lt;/h2&gt;

&lt;p&gt;A messy folder structure will wear down even the best component architecture over time.&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.amazonaws.com%2Fuploads%2Farticles%2Fyifwr6v3x99wvxgs7a79.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.amazonaws.com%2Fuploads%2Farticles%2Fyifwr6v3x99wvxgs7a79.png" alt="React folder structure for storybook" width="720" height="402"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;The structure below is a solid starting point for mid-sized projects.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;src/
  components/
    atoms/
      Button.jsx
      Input.jsx
    molecules/
      SearchBox.jsx
    organisms/
      Header.jsx
      ProductCard.jsx
    templates/
      MainLayout.jsx
  pages/
    HomePage.jsx
  data/
    products.js
  App.jsx
  main.jsx
  styles.css
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;A few things to pay attention to:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;code&gt;components/atoms&lt;/code&gt; holds the smallest, most general-purpose pieces.&lt;/li&gt;
&lt;li&gt;
&lt;code&gt;molecules&lt;/code&gt; combines atoms but stays at a controlled size.&lt;/li&gt;
&lt;li&gt;
&lt;code&gt;organisms&lt;/code&gt; contains larger UI blocks that carry real business value.&lt;/li&gt;
&lt;li&gt;
&lt;code&gt;templates&lt;/code&gt; defines layout, not real page data.&lt;/li&gt;
&lt;li&gt;
&lt;code&gt;pages&lt;/code&gt; is where actual state and data flow begins.&lt;/li&gt;
&lt;/ul&gt;




&lt;h2&gt;
  
  
  🧪 Atom-Level Components
&lt;/h2&gt;

&lt;p&gt;At the atom level, the goal is simple: write small, reusable, self-contained pieces. Components here should be as independent as possible.&lt;/p&gt;

&lt;h3&gt;
  
  
  &lt;code&gt;Button.jsx&lt;/code&gt;
&lt;/h3&gt;



&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight jsx"&gt;&lt;code&gt;&lt;span class="c1"&gt;// src/components/atoms/Button.jsx&lt;/span&gt;
&lt;span class="k"&gt;export&lt;/span&gt; &lt;span class="k"&gt;default&lt;/span&gt; &lt;span class="kd"&gt;function&lt;/span&gt; &lt;span class="nf"&gt;Button&lt;/span&gt;&lt;span class="p"&gt;({&lt;/span&gt;
  &lt;span class="nx"&gt;children&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
  &lt;span class="nx"&gt;variant&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;primary&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
  &lt;span class="nx"&gt;type&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;button&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
  &lt;span class="nx"&gt;onClick&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;span class="p"&gt;})&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
  &lt;span class="k"&gt;return &lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;
    &lt;span class="p"&gt;&amp;lt;&lt;/span&gt;&lt;span class="nt"&gt;button&lt;/span&gt;
      &lt;span class="na"&gt;type&lt;/span&gt;&lt;span class="p"&gt;=&lt;/span&gt;&lt;span class="si"&gt;{&lt;/span&gt;&lt;span class="nx"&gt;type&lt;/span&gt;&lt;span class="si"&gt;}&lt;/span&gt;
      &lt;span class="na"&gt;className&lt;/span&gt;&lt;span class="p"&gt;=&lt;/span&gt;&lt;span class="si"&gt;{&lt;/span&gt;&lt;span class="s2"&gt;`button button--&lt;/span&gt;&lt;span class="p"&gt;${&lt;/span&gt;&lt;span class="nx"&gt;variant&lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="s2"&gt;`&lt;/span&gt;&lt;span class="si"&gt;}&lt;/span&gt;
      &lt;span class="na"&gt;onClick&lt;/span&gt;&lt;span class="p"&gt;=&lt;/span&gt;&lt;span class="si"&gt;{&lt;/span&gt;&lt;span class="nx"&gt;onClick&lt;/span&gt;&lt;span class="si"&gt;}&lt;/span&gt;
    &lt;span class="p"&gt;&amp;gt;&lt;/span&gt;
      &lt;span class="si"&gt;{&lt;/span&gt;&lt;span class="nx"&gt;children&lt;/span&gt;&lt;span class="si"&gt;}&lt;/span&gt;
    &lt;span class="p"&gt;&amp;lt;/&lt;/span&gt;&lt;span class="nt"&gt;button&lt;/span&gt;&lt;span class="p"&gt;&amp;gt;&lt;/span&gt;
  &lt;span class="p"&gt;);&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Key points:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;code&gt;variant = "primary"&lt;/code&gt; gives the button a default style type.&lt;/li&gt;
&lt;li&gt;
&lt;code&gt;children&lt;/code&gt; keeps the button content flexible.&lt;/li&gt;
&lt;li&gt;At the atom level, the job is purely to render. No business logic.&lt;/li&gt;
&lt;/ul&gt;

&lt;h3&gt;
  
  
  &lt;code&gt;Input.jsx&lt;/code&gt;
&lt;/h3&gt;



&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight jsx"&gt;&lt;code&gt;&lt;span class="c1"&gt;// src/components/atoms/Input.jsx&lt;/span&gt;
&lt;span class="k"&gt;export&lt;/span&gt; &lt;span class="k"&gt;default&lt;/span&gt; &lt;span class="kd"&gt;function&lt;/span&gt; &lt;span class="nf"&gt;Input&lt;/span&gt;&lt;span class="p"&gt;({&lt;/span&gt;
  &lt;span class="nx"&gt;value&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
  &lt;span class="nx"&gt;onChange&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
  &lt;span class="nx"&gt;placeholder&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;Search...&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
  &lt;span class="p"&gt;...&lt;/span&gt;&lt;span class="nx"&gt;props&lt;/span&gt;
&lt;span class="p"&gt;})&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
  &lt;span class="k"&gt;return &lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;
    &lt;span class="p"&gt;&amp;lt;&lt;/span&gt;&lt;span class="nt"&gt;input&lt;/span&gt;
      &lt;span class="na"&gt;className&lt;/span&gt;&lt;span class="p"&gt;=&lt;/span&gt;&lt;span class="s"&gt;"input"&lt;/span&gt;
      &lt;span class="na"&gt;value&lt;/span&gt;&lt;span class="p"&gt;=&lt;/span&gt;&lt;span class="si"&gt;{&lt;/span&gt;&lt;span class="nx"&gt;value&lt;/span&gt;&lt;span class="si"&gt;}&lt;/span&gt;
      &lt;span class="na"&gt;onChange&lt;/span&gt;&lt;span class="p"&gt;=&lt;/span&gt;&lt;span class="si"&gt;{&lt;/span&gt;&lt;span class="nx"&gt;onChange&lt;/span&gt;&lt;span class="si"&gt;}&lt;/span&gt;
      &lt;span class="na"&gt;placeholder&lt;/span&gt;&lt;span class="p"&gt;=&lt;/span&gt;&lt;span class="si"&gt;{&lt;/span&gt;&lt;span class="nx"&gt;placeholder&lt;/span&gt;&lt;span class="si"&gt;}&lt;/span&gt;
      &lt;span class="si"&gt;{&lt;/span&gt;&lt;span class="p"&gt;...&lt;/span&gt;&lt;span class="nx"&gt;props&lt;/span&gt;&lt;span class="si"&gt;}&lt;/span&gt;
    &lt;span class="p"&gt;/&amp;gt;&lt;/span&gt;
  &lt;span class="p"&gt;);&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Key points:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;code&gt;...props&lt;/code&gt; keeps the input flexible for future use cases.&lt;/li&gt;
&lt;li&gt;
&lt;code&gt;value&lt;/code&gt; and &lt;code&gt;onChange&lt;/code&gt; come from the outside, so the component is controlled.&lt;/li&gt;
&lt;li&gt;No unnecessary state at the atom level.&lt;/li&gt;
&lt;/ul&gt;

&lt;blockquote&gt;
&lt;p&gt;💡 The simpler your atoms, the more freedom you have at higher layers.&lt;/p&gt;
&lt;/blockquote&gt;




&lt;h2&gt;
  
  
  🧬 Molecule-Level Components
&lt;/h2&gt;

&lt;p&gt;At the molecule layer, we're building small but purposeful combinations. A standalone &lt;code&gt;Input&lt;/code&gt; is just a field. A &lt;code&gt;SearchBox&lt;/code&gt; represents a specific user intent.&lt;/p&gt;

&lt;h3&gt;
  
  
  &lt;code&gt;SearchBox.jsx&lt;/code&gt;
&lt;/h3&gt;



&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight jsx"&gt;&lt;code&gt;&lt;span class="c1"&gt;// src/components/molecules/SearchBox.jsx&lt;/span&gt;
&lt;span class="k"&gt;import&lt;/span&gt; &lt;span class="nx"&gt;Button&lt;/span&gt; &lt;span class="k"&gt;from&lt;/span&gt; &lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;../atoms/Button&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
&lt;span class="k"&gt;import&lt;/span&gt; &lt;span class="nx"&gt;Input&lt;/span&gt; &lt;span class="k"&gt;from&lt;/span&gt; &lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;../atoms/Input&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;

&lt;span class="k"&gt;export&lt;/span&gt; &lt;span class="k"&gt;default&lt;/span&gt; &lt;span class="kd"&gt;function&lt;/span&gt; &lt;span class="nf"&gt;SearchBox&lt;/span&gt;&lt;span class="p"&gt;({&lt;/span&gt; &lt;span class="nx"&gt;query&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="nx"&gt;onQueryChange&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="nx"&gt;onSearch&lt;/span&gt; &lt;span class="p"&gt;})&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
  &lt;span class="k"&gt;return &lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;
    &lt;span class="p"&gt;&amp;lt;&lt;/span&gt;&lt;span class="nt"&gt;div&lt;/span&gt; &lt;span class="na"&gt;className&lt;/span&gt;&lt;span class="p"&gt;=&lt;/span&gt;&lt;span class="s"&gt;"search-box"&lt;/span&gt;&lt;span class="p"&gt;&amp;gt;&lt;/span&gt;
      &lt;span class="p"&gt;&amp;lt;&lt;/span&gt;&lt;span class="nc"&gt;Input&lt;/span&gt;
        &lt;span class="na"&gt;value&lt;/span&gt;&lt;span class="p"&gt;=&lt;/span&gt;&lt;span class="si"&gt;{&lt;/span&gt;&lt;span class="nx"&gt;query&lt;/span&gt;&lt;span class="si"&gt;}&lt;/span&gt;
        &lt;span class="na"&gt;onChange&lt;/span&gt;&lt;span class="p"&gt;=&lt;/span&gt;&lt;span class="si"&gt;{&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;event&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="o"&gt;=&amp;gt;&lt;/span&gt; &lt;span class="nf"&gt;onQueryChange&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;event&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;target&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;value&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="si"&gt;}&lt;/span&gt;
        &lt;span class="na"&gt;placeholder&lt;/span&gt;&lt;span class="p"&gt;=&lt;/span&gt;&lt;span class="s"&gt;"Search products"&lt;/span&gt;
      &lt;span class="p"&gt;/&amp;gt;&lt;/span&gt;
      &lt;span class="p"&gt;&amp;lt;&lt;/span&gt;&lt;span class="nc"&gt;Button&lt;/span&gt; &lt;span class="na"&gt;onClick&lt;/span&gt;&lt;span class="p"&gt;=&lt;/span&gt;&lt;span class="si"&gt;{&lt;/span&gt;&lt;span class="nx"&gt;onSearch&lt;/span&gt;&lt;span class="si"&gt;}&lt;/span&gt;&lt;span class="p"&gt;&amp;gt;&lt;/span&gt;Search&lt;span class="p"&gt;&amp;lt;/&lt;/span&gt;&lt;span class="nc"&gt;Button&lt;/span&gt;&lt;span class="p"&gt;&amp;gt;&lt;/span&gt;
    &lt;span class="p"&gt;&amp;lt;/&lt;/span&gt;&lt;span class="nt"&gt;div&lt;/span&gt;&lt;span class="p"&gt;&amp;gt;&lt;/span&gt;
  &lt;span class="p"&gt;);&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Design decisions worth calling out:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;code&gt;SearchBox&lt;/code&gt; holds no internal state. It delegates control to the page layer.&lt;/li&gt;
&lt;li&gt;
&lt;code&gt;Input&lt;/code&gt; and &lt;code&gt;Button&lt;/code&gt; remain atoms; they simply come together here.&lt;/li&gt;
&lt;li&gt;This component now does meaningful work on the page, which is why treating it as a molecule makes sense.&lt;/li&gt;
&lt;/ul&gt;




&lt;h2&gt;
  
  
  🏗️ Organism-Level Components
&lt;/h2&gt;

&lt;p&gt;At the organism layer, we're building more significant UI sections. Components here represent a distinct, recognizable region of the page.&lt;/p&gt;

&lt;h3&gt;
  
  
  &lt;code&gt;Header.jsx&lt;/code&gt;
&lt;/h3&gt;



&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight jsx"&gt;&lt;code&gt;&lt;span class="c1"&gt;// src/components/organisms/Header.jsx&lt;/span&gt;
&lt;span class="k"&gt;import&lt;/span&gt; &lt;span class="nx"&gt;Button&lt;/span&gt; &lt;span class="k"&gt;from&lt;/span&gt; &lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;../atoms/Button&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
&lt;span class="k"&gt;import&lt;/span&gt; &lt;span class="nx"&gt;SearchBox&lt;/span&gt; &lt;span class="k"&gt;from&lt;/span&gt; &lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;../molecules/SearchBox&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;

&lt;span class="k"&gt;export&lt;/span&gt; &lt;span class="k"&gt;default&lt;/span&gt; &lt;span class="kd"&gt;function&lt;/span&gt; &lt;span class="nf"&gt;Header&lt;/span&gt;&lt;span class="p"&gt;({&lt;/span&gt; &lt;span class="nx"&gt;query&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="nx"&gt;onQueryChange&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="nx"&gt;onSearch&lt;/span&gt; &lt;span class="p"&gt;})&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
  &lt;span class="k"&gt;return &lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;
    &lt;span class="p"&gt;&amp;lt;&lt;/span&gt;&lt;span class="nt"&gt;header&lt;/span&gt; &lt;span class="na"&gt;className&lt;/span&gt;&lt;span class="p"&gt;=&lt;/span&gt;&lt;span class="s"&gt;"header"&lt;/span&gt;&lt;span class="p"&gt;&amp;gt;&lt;/span&gt;
      &lt;span class="p"&gt;&amp;lt;&lt;/span&gt;&lt;span class="nt"&gt;div&lt;/span&gt; &lt;span class="na"&gt;className&lt;/span&gt;&lt;span class="p"&gt;=&lt;/span&gt;&lt;span class="s"&gt;"header__brand"&lt;/span&gt;&lt;span class="p"&gt;&amp;gt;&lt;/span&gt;ShopSphere&lt;span class="p"&gt;&amp;lt;/&lt;/span&gt;&lt;span class="nt"&gt;div&lt;/span&gt;&lt;span class="p"&gt;&amp;gt;&lt;/span&gt;
      &lt;span class="p"&gt;&amp;lt;&lt;/span&gt;&lt;span class="nc"&gt;SearchBox&lt;/span&gt;
        &lt;span class="na"&gt;query&lt;/span&gt;&lt;span class="p"&gt;=&lt;/span&gt;&lt;span class="si"&gt;{&lt;/span&gt;&lt;span class="nx"&gt;query&lt;/span&gt;&lt;span class="si"&gt;}&lt;/span&gt;
        &lt;span class="na"&gt;onQueryChange&lt;/span&gt;&lt;span class="p"&gt;=&lt;/span&gt;&lt;span class="si"&gt;{&lt;/span&gt;&lt;span class="nx"&gt;onQueryChange&lt;/span&gt;&lt;span class="si"&gt;}&lt;/span&gt;
        &lt;span class="na"&gt;onSearch&lt;/span&gt;&lt;span class="p"&gt;=&lt;/span&gt;&lt;span class="si"&gt;{&lt;/span&gt;&lt;span class="nx"&gt;onSearch&lt;/span&gt;&lt;span class="si"&gt;}&lt;/span&gt;
      &lt;span class="p"&gt;/&amp;gt;&lt;/span&gt;
      &lt;span class="p"&gt;&amp;lt;&lt;/span&gt;&lt;span class="nc"&gt;Button&lt;/span&gt; &lt;span class="na"&gt;variant&lt;/span&gt;&lt;span class="p"&gt;=&lt;/span&gt;&lt;span class="s"&gt;"secondary"&lt;/span&gt;&lt;span class="p"&gt;&amp;gt;&lt;/span&gt;My Cart&lt;span class="p"&gt;&amp;lt;/&lt;/span&gt;&lt;span class="nc"&gt;Button&lt;/span&gt;&lt;span class="p"&gt;&amp;gt;&lt;/span&gt;
    &lt;span class="p"&gt;&amp;lt;/&lt;/span&gt;&lt;span class="nt"&gt;header&lt;/span&gt;&lt;span class="p"&gt;&amp;gt;&lt;/span&gt;
  &lt;span class="p"&gt;);&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Key things to notice:&lt;/p&gt;

&lt;p&gt;★ &lt;code&gt;Header&lt;/code&gt; is no longer a single atom or molecule. It's a larger UI section.&lt;br&gt;
★ It uses both a molecule and an atom internally.&lt;br&gt;
★ The brand area, search area, and cart action come together to form a functional region.&lt;/p&gt;

&lt;h3&gt;
  
  
  &lt;code&gt;ProductCard.jsx&lt;/code&gt;
&lt;/h3&gt;



&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight jsx"&gt;&lt;code&gt;&lt;span class="c1"&gt;// src/components/organisms/ProductCard.jsx&lt;/span&gt;
&lt;span class="k"&gt;import&lt;/span&gt; &lt;span class="nx"&gt;Button&lt;/span&gt; &lt;span class="k"&gt;from&lt;/span&gt; &lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;../atoms/Button&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;

&lt;span class="k"&gt;export&lt;/span&gt; &lt;span class="k"&gt;default&lt;/span&gt; &lt;span class="kd"&gt;function&lt;/span&gt; &lt;span class="nf"&gt;ProductCard&lt;/span&gt;&lt;span class="p"&gt;({&lt;/span&gt; &lt;span class="nx"&gt;product&lt;/span&gt; &lt;span class="p"&gt;})&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
  &lt;span class="k"&gt;return &lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;
    &lt;span class="p"&gt;&amp;lt;&lt;/span&gt;&lt;span class="nt"&gt;article&lt;/span&gt; &lt;span class="na"&gt;className&lt;/span&gt;&lt;span class="p"&gt;=&lt;/span&gt;&lt;span class="s"&gt;"product-card"&lt;/span&gt;&lt;span class="p"&gt;&amp;gt;&lt;/span&gt;
      &lt;span class="p"&gt;&amp;lt;&lt;/span&gt;&lt;span class="nt"&gt;div&lt;/span&gt; &lt;span class="na"&gt;className&lt;/span&gt;&lt;span class="p"&gt;=&lt;/span&gt;&lt;span class="s"&gt;"product-card__emoji"&lt;/span&gt; &lt;span class="na"&gt;aria-hidden&lt;/span&gt;&lt;span class="p"&gt;=&lt;/span&gt;&lt;span class="s"&gt;"true"&lt;/span&gt;&lt;span class="p"&gt;&amp;gt;&lt;/span&gt;
        &lt;span class="si"&gt;{&lt;/span&gt;&lt;span class="nx"&gt;product&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;emoji&lt;/span&gt;&lt;span class="si"&gt;}&lt;/span&gt;
      &lt;span class="p"&gt;&amp;lt;/&lt;/span&gt;&lt;span class="nt"&gt;div&lt;/span&gt;&lt;span class="p"&gt;&amp;gt;&lt;/span&gt;
      &lt;span class="p"&gt;&amp;lt;&lt;/span&gt;&lt;span class="nt"&gt;h3&lt;/span&gt; &lt;span class="na"&gt;className&lt;/span&gt;&lt;span class="p"&gt;=&lt;/span&gt;&lt;span class="s"&gt;"product-card__title"&lt;/span&gt;&lt;span class="p"&gt;&amp;gt;&lt;/span&gt;&lt;span class="si"&gt;{&lt;/span&gt;&lt;span class="nx"&gt;product&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;title&lt;/span&gt;&lt;span class="si"&gt;}&lt;/span&gt;&lt;span class="p"&gt;&amp;lt;/&lt;/span&gt;&lt;span class="nt"&gt;h3&lt;/span&gt;&lt;span class="p"&gt;&amp;gt;&lt;/span&gt;
      &lt;span class="p"&gt;&amp;lt;&lt;/span&gt;&lt;span class="nt"&gt;p&lt;/span&gt; &lt;span class="na"&gt;className&lt;/span&gt;&lt;span class="p"&gt;=&lt;/span&gt;&lt;span class="s"&gt;"product-card__description"&lt;/span&gt;&lt;span class="p"&gt;&amp;gt;&lt;/span&gt;&lt;span class="si"&gt;{&lt;/span&gt;&lt;span class="nx"&gt;product&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;description&lt;/span&gt;&lt;span class="si"&gt;}&lt;/span&gt;&lt;span class="p"&gt;&amp;lt;/&lt;/span&gt;&lt;span class="nt"&gt;p&lt;/span&gt;&lt;span class="p"&gt;&amp;gt;&lt;/span&gt;
      &lt;span class="p"&gt;&amp;lt;&lt;/span&gt;&lt;span class="nt"&gt;div&lt;/span&gt; &lt;span class="na"&gt;className&lt;/span&gt;&lt;span class="p"&gt;=&lt;/span&gt;&lt;span class="s"&gt;"product-card__footer"&lt;/span&gt;&lt;span class="p"&gt;&amp;gt;&lt;/span&gt;
        &lt;span class="p"&gt;&amp;lt;&lt;/span&gt;&lt;span class="nt"&gt;strong&lt;/span&gt;&lt;span class="p"&gt;&amp;gt;&lt;/span&gt;&lt;span class="si"&gt;{&lt;/span&gt;&lt;span class="nx"&gt;product&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;price&lt;/span&gt;&lt;span class="si"&gt;}&lt;/span&gt; TL&lt;span class="p"&gt;&amp;lt;/&lt;/span&gt;&lt;span class="nt"&gt;strong&lt;/span&gt;&lt;span class="p"&gt;&amp;gt;&lt;/span&gt;
        &lt;span class="p"&gt;&amp;lt;&lt;/span&gt;&lt;span class="nc"&gt;Button&lt;/span&gt;&lt;span class="p"&gt;&amp;gt;&lt;/span&gt;Add to Cart&lt;span class="p"&gt;&amp;lt;/&lt;/span&gt;&lt;span class="nc"&gt;Button&lt;/span&gt;&lt;span class="p"&gt;&amp;gt;&lt;/span&gt;
      &lt;span class="p"&gt;&amp;lt;/&lt;/span&gt;&lt;span class="nt"&gt;div&lt;/span&gt;&lt;span class="p"&gt;&amp;gt;&lt;/span&gt;
    &lt;span class="p"&gt;&amp;lt;/&lt;/span&gt;&lt;span class="nt"&gt;article&lt;/span&gt;&lt;span class="p"&gt;&amp;gt;&lt;/span&gt;
  &lt;span class="p"&gt;);&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Key points:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;The &lt;code&gt;product&lt;/code&gt; object gains real meaning at the organism level.&lt;/li&gt;
&lt;li&gt;
&lt;code&gt;Button&lt;/code&gt; is reused as an atom.&lt;/li&gt;
&lt;li&gt;The card represents a standalone, significant UI unit on the page, which is why it belongs at the organism level.&lt;/li&gt;
&lt;/ul&gt;




&lt;h2&gt;
  
  
  📐 Template and Page Layers
&lt;/h2&gt;

&lt;p&gt;This is where most people get confused. Template and page are not the same thing.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Template&lt;/strong&gt; defines the structure of a page.&lt;br&gt;
&lt;strong&gt;Page&lt;/strong&gt; is that structure filled with real data and state.&lt;/p&gt;

&lt;h3&gt;
  
  
  &lt;code&gt;MainLayout.jsx&lt;/code&gt;
&lt;/h3&gt;



&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight jsx"&gt;&lt;code&gt;&lt;span class="c1"&gt;// src/components/templates/MainLayout.jsx&lt;/span&gt;
&lt;span class="k"&gt;import&lt;/span&gt; &lt;span class="nx"&gt;Header&lt;/span&gt; &lt;span class="k"&gt;from&lt;/span&gt; &lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;../organisms/Header&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;

&lt;span class="k"&gt;export&lt;/span&gt; &lt;span class="k"&gt;default&lt;/span&gt; &lt;span class="kd"&gt;function&lt;/span&gt; &lt;span class="nf"&gt;MainLayout&lt;/span&gt;&lt;span class="p"&gt;({&lt;/span&gt;
  &lt;span class="nx"&gt;query&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
  &lt;span class="nx"&gt;onQueryChange&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
  &lt;span class="nx"&gt;onSearch&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
  &lt;span class="nx"&gt;children&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;span class="p"&gt;})&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
  &lt;span class="k"&gt;return &lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;
    &lt;span class="p"&gt;&amp;lt;&lt;/span&gt;&lt;span class="nt"&gt;div&lt;/span&gt; &lt;span class="na"&gt;className&lt;/span&gt;&lt;span class="p"&gt;=&lt;/span&gt;&lt;span class="s"&gt;"layout"&lt;/span&gt;&lt;span class="p"&gt;&amp;gt;&lt;/span&gt;
      &lt;span class="p"&gt;&amp;lt;&lt;/span&gt;&lt;span class="nc"&gt;Header&lt;/span&gt;
        &lt;span class="na"&gt;query&lt;/span&gt;&lt;span class="p"&gt;=&lt;/span&gt;&lt;span class="si"&gt;{&lt;/span&gt;&lt;span class="nx"&gt;query&lt;/span&gt;&lt;span class="si"&gt;}&lt;/span&gt;
        &lt;span class="na"&gt;onQueryChange&lt;/span&gt;&lt;span class="p"&gt;=&lt;/span&gt;&lt;span class="si"&gt;{&lt;/span&gt;&lt;span class="nx"&gt;onQueryChange&lt;/span&gt;&lt;span class="si"&gt;}&lt;/span&gt;
        &lt;span class="na"&gt;onSearch&lt;/span&gt;&lt;span class="p"&gt;=&lt;/span&gt;&lt;span class="si"&gt;{&lt;/span&gt;&lt;span class="nx"&gt;onSearch&lt;/span&gt;&lt;span class="si"&gt;}&lt;/span&gt;
      &lt;span class="p"&gt;/&amp;gt;&lt;/span&gt;
      &lt;span class="p"&gt;&amp;lt;&lt;/span&gt;&lt;span class="nt"&gt;main&lt;/span&gt; &lt;span class="na"&gt;className&lt;/span&gt;&lt;span class="p"&gt;=&lt;/span&gt;&lt;span class="s"&gt;"layout__content"&lt;/span&gt;&lt;span class="p"&gt;&amp;gt;&lt;/span&gt;&lt;span class="si"&gt;{&lt;/span&gt;&lt;span class="nx"&gt;children&lt;/span&gt;&lt;span class="si"&gt;}&lt;/span&gt;&lt;span class="p"&gt;&amp;lt;/&lt;/span&gt;&lt;span class="nt"&gt;main&lt;/span&gt;&lt;span class="p"&gt;&amp;gt;&lt;/span&gt;
    &lt;span class="p"&gt;&amp;lt;/&lt;/span&gt;&lt;span class="nt"&gt;div&lt;/span&gt;&lt;span class="p"&gt;&amp;gt;&lt;/span&gt;
  &lt;span class="p"&gt;);&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;What makes this structure important:&lt;/p&gt;

&lt;p&gt;★ &lt;code&gt;children&lt;/code&gt; keeps the template flexible and composable.&lt;br&gt;
★ &lt;code&gt;MainLayout&lt;/code&gt; establishes layout but has no awareness of product data.&lt;br&gt;
★ This separation pays real dividends as projects grow.&lt;/p&gt;

&lt;p&gt;A template should be as content-agnostic as possible. Data, filtering logic, and page-level behavior belong in the page layer.&lt;/p&gt;




&lt;h2&gt;
  
  
  🛍️ Sample Project: Building a Mini E-Commerce UI
&lt;/h2&gt;

&lt;p&gt;Now let's wire together all the layers we've built into a real working page.&lt;/p&gt;

&lt;h3&gt;
  
  
  Step 1: Create the mock product data
&lt;/h3&gt;



&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="c1"&gt;// src/data/products.js&lt;/span&gt;
&lt;span class="k"&gt;export&lt;/span&gt; &lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;products&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="p"&gt;[&lt;/span&gt;
  &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="na"&gt;id&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
    &lt;span class="na"&gt;emoji&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;⌨️&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
    &lt;span class="na"&gt;title&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;Mechanical Keyboard&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
    &lt;span class="na"&gt;description&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;Hot-swappable, compact keyboard with RGB support.&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
    &lt;span class="na"&gt;price&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="mi"&gt;2499&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
  &lt;span class="p"&gt;},&lt;/span&gt;
  &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="na"&gt;id&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="mi"&gt;2&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
    &lt;span class="na"&gt;emoji&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;🖱️&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
    &lt;span class="na"&gt;title&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;Gaming Mouse&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
    &lt;span class="na"&gt;description&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;Lightweight body, high DPI, and low latency.&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
    &lt;span class="na"&gt;price&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="mi"&gt;1499&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
  &lt;span class="p"&gt;},&lt;/span&gt;
  &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="na"&gt;id&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="mi"&gt;3&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
    &lt;span class="na"&gt;emoji&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;🎧&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
    &lt;span class="na"&gt;title&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;Wireless Headset&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
    &lt;span class="na"&gt;description&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;Long battery life with low-latency connectivity.&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
    &lt;span class="na"&gt;price&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="mi"&gt;3299&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
  &lt;span class="p"&gt;},&lt;/span&gt;
&lt;span class="p"&gt;];&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Why this matters:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;We can test the page layer independently from a real API.&lt;/li&gt;
&lt;li&gt;The same mock data can be reused in Storybook stories.&lt;/li&gt;
&lt;li&gt;Data flow is easy to reason about during development.&lt;/li&gt;
&lt;/ul&gt;

&lt;h3&gt;
  
  
  Step 2: Write the &lt;code&gt;HomePage&lt;/code&gt; component
&lt;/h3&gt;



&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight jsx"&gt;&lt;code&gt;&lt;span class="c1"&gt;// src/pages/HomePage.jsx&lt;/span&gt;
&lt;span class="k"&gt;import&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt; &lt;span class="nx"&gt;useMemo&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="nx"&gt;useState&lt;/span&gt; &lt;span class="p"&gt;}&lt;/span&gt; &lt;span class="k"&gt;from&lt;/span&gt; &lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;react&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
&lt;span class="k"&gt;import&lt;/span&gt; &lt;span class="nx"&gt;ProductCard&lt;/span&gt; &lt;span class="k"&gt;from&lt;/span&gt; &lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;../components/organisms/ProductCard&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
&lt;span class="k"&gt;import&lt;/span&gt; &lt;span class="nx"&gt;MainLayout&lt;/span&gt; &lt;span class="k"&gt;from&lt;/span&gt; &lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;../components/templates/MainLayout&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
&lt;span class="k"&gt;import&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt; &lt;span class="nx"&gt;products&lt;/span&gt; &lt;span class="p"&gt;}&lt;/span&gt; &lt;span class="k"&gt;from&lt;/span&gt; &lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;../data/products&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;

&lt;span class="k"&gt;export&lt;/span&gt; &lt;span class="k"&gt;default&lt;/span&gt; &lt;span class="kd"&gt;function&lt;/span&gt; &lt;span class="nf"&gt;HomePage&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
  &lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="nx"&gt;query&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="nx"&gt;setQuery&lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nf"&gt;useState&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="dl"&gt;""&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;

  &lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;filteredProducts&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nf"&gt;useMemo&lt;/span&gt;&lt;span class="p"&gt;(()&lt;/span&gt; &lt;span class="o"&gt;=&amp;gt;&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="k"&gt;return&lt;/span&gt; &lt;span class="nx"&gt;products&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;filter&lt;/span&gt;&lt;span class="p"&gt;((&lt;/span&gt;&lt;span class="nx"&gt;product&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="o"&gt;=&amp;gt;&lt;/span&gt;
      &lt;span class="nx"&gt;product&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;title&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;toLowerCase&lt;/span&gt;&lt;span class="p"&gt;().&lt;/span&gt;&lt;span class="nf"&gt;includes&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;query&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;toLowerCase&lt;/span&gt;&lt;span class="p"&gt;())&lt;/span&gt;
    &lt;span class="p"&gt;);&lt;/span&gt;
  &lt;span class="p"&gt;},&lt;/span&gt; &lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="nx"&gt;query&lt;/span&gt;&lt;span class="p"&gt;]);&lt;/span&gt;

  &lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;handleSearch&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="p"&gt;()&lt;/span&gt; &lt;span class="o"&gt;=&amp;gt;&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="nx"&gt;console&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;log&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s2"&gt;`Searching for: &lt;/span&gt;&lt;span class="p"&gt;${&lt;/span&gt;&lt;span class="nx"&gt;query&lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="s2"&gt;`&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;
  &lt;span class="p"&gt;};&lt;/span&gt;

  &lt;span class="k"&gt;return &lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;
    &lt;span class="p"&gt;&amp;lt;&lt;/span&gt;&lt;span class="nc"&gt;MainLayout&lt;/span&gt;
      &lt;span class="na"&gt;query&lt;/span&gt;&lt;span class="p"&gt;=&lt;/span&gt;&lt;span class="si"&gt;{&lt;/span&gt;&lt;span class="nx"&gt;query&lt;/span&gt;&lt;span class="si"&gt;}&lt;/span&gt;
      &lt;span class="na"&gt;onQueryChange&lt;/span&gt;&lt;span class="p"&gt;=&lt;/span&gt;&lt;span class="si"&gt;{&lt;/span&gt;&lt;span class="nx"&gt;setQuery&lt;/span&gt;&lt;span class="si"&gt;}&lt;/span&gt;
      &lt;span class="na"&gt;onSearch&lt;/span&gt;&lt;span class="p"&gt;=&lt;/span&gt;&lt;span class="si"&gt;{&lt;/span&gt;&lt;span class="nx"&gt;handleSearch&lt;/span&gt;&lt;span class="si"&gt;}&lt;/span&gt;
    &lt;span class="p"&gt;&amp;gt;&lt;/span&gt;
      &lt;span class="p"&gt;&amp;lt;&lt;/span&gt;&lt;span class="nt"&gt;section&lt;/span&gt; &lt;span class="na"&gt;className&lt;/span&gt;&lt;span class="p"&gt;=&lt;/span&gt;&lt;span class="s"&gt;"page-intro"&lt;/span&gt;&lt;span class="p"&gt;&amp;gt;&lt;/span&gt;
        &lt;span class="p"&gt;&amp;lt;&lt;/span&gt;&lt;span class="nt"&gt;h1&lt;/span&gt;&lt;span class="p"&gt;&amp;gt;&lt;/span&gt;Featured Products&lt;span class="p"&gt;&amp;lt;/&lt;/span&gt;&lt;span class="nt"&gt;h1&lt;/span&gt;&lt;span class="p"&gt;&amp;gt;&lt;/span&gt;
        &lt;span class="p"&gt;&amp;lt;&lt;/span&gt;&lt;span class="nt"&gt;p&lt;/span&gt;&lt;span class="p"&gt;&amp;gt;&lt;/span&gt;A sample catalog screen built with the Atomic Design approach.&lt;span class="p"&gt;&amp;lt;/&lt;/span&gt;&lt;span class="nt"&gt;p&lt;/span&gt;&lt;span class="p"&gt;&amp;gt;&lt;/span&gt;
      &lt;span class="p"&gt;&amp;lt;/&lt;/span&gt;&lt;span class="nt"&gt;section&lt;/span&gt;&lt;span class="p"&gt;&amp;gt;&lt;/span&gt;
      &lt;span class="p"&gt;&amp;lt;&lt;/span&gt;&lt;span class="nt"&gt;section&lt;/span&gt; &lt;span class="na"&gt;className&lt;/span&gt;&lt;span class="p"&gt;=&lt;/span&gt;&lt;span class="s"&gt;"product-grid"&lt;/span&gt;&lt;span class="p"&gt;&amp;gt;&lt;/span&gt;
        &lt;span class="si"&gt;{&lt;/span&gt;&lt;span class="nx"&gt;filteredProducts&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;map&lt;/span&gt;&lt;span class="p"&gt;((&lt;/span&gt;&lt;span class="nx"&gt;product&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="o"&gt;=&amp;gt;&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;
          &lt;span class="p"&gt;&amp;lt;&lt;/span&gt;&lt;span class="nc"&gt;ProductCard&lt;/span&gt; &lt;span class="na"&gt;key&lt;/span&gt;&lt;span class="p"&gt;=&lt;/span&gt;&lt;span class="si"&gt;{&lt;/span&gt;&lt;span class="nx"&gt;product&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;id&lt;/span&gt;&lt;span class="si"&gt;}&lt;/span&gt; &lt;span class="na"&gt;product&lt;/span&gt;&lt;span class="p"&gt;=&lt;/span&gt;&lt;span class="si"&gt;{&lt;/span&gt;&lt;span class="nx"&gt;product&lt;/span&gt;&lt;span class="si"&gt;}&lt;/span&gt; &lt;span class="p"&gt;/&amp;gt;&lt;/span&gt;
        &lt;span class="p"&gt;))&lt;/span&gt;&lt;span class="si"&gt;}&lt;/span&gt;
      &lt;span class="p"&gt;&amp;lt;/&lt;/span&gt;&lt;span class="nt"&gt;section&lt;/span&gt;&lt;span class="p"&gt;&amp;gt;&lt;/span&gt;
    &lt;span class="p"&gt;&amp;lt;/&lt;/span&gt;&lt;span class="nc"&gt;MainLayout&lt;/span&gt;&lt;span class="p"&gt;&amp;gt;&lt;/span&gt;
  &lt;span class="p"&gt;);&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Most critical points:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Real &lt;code&gt;state&lt;/code&gt; lives here. We're at the right layer.&lt;/li&gt;
&lt;li&gt;Filtering logic is resolved at the page level.&lt;/li&gt;
&lt;li&gt;
&lt;code&gt;MainLayout&lt;/code&gt; handles layout only; it doesn't manage data.&lt;/li&gt;
&lt;/ul&gt;

&lt;h3&gt;
  
  
  Step 3: Wire up the application entry point
&lt;/h3&gt;



&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight jsx"&gt;&lt;code&gt;&lt;span class="c1"&gt;// src/App.jsx&lt;/span&gt;
&lt;span class="k"&gt;import&lt;/span&gt; &lt;span class="nx"&gt;HomePage&lt;/span&gt; &lt;span class="k"&gt;from&lt;/span&gt; &lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;./pages/HomePage&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
&lt;span class="k"&gt;import&lt;/span&gt; &lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;./styles.css&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;

&lt;span class="k"&gt;export&lt;/span&gt; &lt;span class="k"&gt;default&lt;/span&gt; &lt;span class="kd"&gt;function&lt;/span&gt; &lt;span class="nf"&gt;App&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
  &lt;span class="k"&gt;return&lt;/span&gt; &lt;span class="p"&gt;&amp;lt;&lt;/span&gt;&lt;span class="nc"&gt;HomePage&lt;/span&gt; &lt;span class="p"&gt;/&amp;gt;;&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Small file, but it matters:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;code&gt;App&lt;/code&gt; now renders the page-level screen.&lt;/li&gt;
&lt;li&gt;Global styles are loaded from a single location.&lt;/li&gt;
&lt;li&gt;The atomic layers are properly connected from top to bottom.&lt;/li&gt;
&lt;/ul&gt;

&lt;h3&gt;
  
  
  Step 4: Add minimal styles
&lt;/h3&gt;



&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight css"&gt;&lt;code&gt;&lt;span class="c"&gt;/* src/styles.css */&lt;/span&gt;
&lt;span class="nd"&gt;:root&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
  &lt;span class="nl"&gt;font-family&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="n"&gt;Inter&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;system-ui&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="nb"&gt;sans-serif&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
  &lt;span class="nl"&gt;color&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="m"&gt;#e2e8f0&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
  &lt;span class="nl"&gt;background&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="m"&gt;#0f172a&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;

&lt;span class="o"&gt;*&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
  &lt;span class="nl"&gt;box-sizing&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="n"&gt;border-box&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;

&lt;span class="nt"&gt;body&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
  &lt;span class="nl"&gt;margin&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="m"&gt;0&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;

&lt;span class="nc"&gt;.layout__content&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
  &lt;span class="nl"&gt;max-width&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="m"&gt;1100px&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
  &lt;span class="nl"&gt;margin&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="m"&gt;0&lt;/span&gt; &lt;span class="nb"&gt;auto&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
  &lt;span class="nl"&gt;padding&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="m"&gt;32px&lt;/span&gt; &lt;span class="m"&gt;20px&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;

&lt;span class="nc"&gt;.header&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
  &lt;span class="nl"&gt;display&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="n"&gt;flex&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
  &lt;span class="nl"&gt;align-items&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="nb"&gt;center&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
  &lt;span class="nl"&gt;justify-content&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="n"&gt;space-between&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
  &lt;span class="py"&gt;gap&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="m"&gt;16px&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
  &lt;span class="nl"&gt;padding&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="m"&gt;20px&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
  &lt;span class="nl"&gt;border-bottom&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="m"&gt;1px&lt;/span&gt; &lt;span class="nb"&gt;solid&lt;/span&gt; &lt;span class="m"&gt;#1e293b&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
  &lt;span class="nl"&gt;background&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="m"&gt;#111827&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;

&lt;span class="nc"&gt;.header__brand&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
  &lt;span class="nl"&gt;font-size&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="m"&gt;20px&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
  &lt;span class="nl"&gt;font-weight&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="m"&gt;700&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;

&lt;span class="nc"&gt;.search-box&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
  &lt;span class="nl"&gt;display&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="n"&gt;flex&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
  &lt;span class="py"&gt;gap&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="m"&gt;12px&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
  &lt;span class="nl"&gt;flex&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="m"&gt;1&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
  &lt;span class="nl"&gt;max-width&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="m"&gt;520px&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;

&lt;span class="nc"&gt;.input&lt;/span&gt;&lt;span class="o"&gt;,&lt;/span&gt;
&lt;span class="nc"&gt;.button&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
  &lt;span class="nl"&gt;border-radius&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="m"&gt;12px&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
  &lt;span class="nl"&gt;border&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="m"&gt;1px&lt;/span&gt; &lt;span class="nb"&gt;solid&lt;/span&gt; &lt;span class="m"&gt;#334155&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
  &lt;span class="nl"&gt;padding&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="m"&gt;12px&lt;/span&gt; &lt;span class="m"&gt;16px&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;

&lt;span class="nc"&gt;.input&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
  &lt;span class="nl"&gt;flex&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="m"&gt;1&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
  &lt;span class="nl"&gt;background&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="m"&gt;#0f172a&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
  &lt;span class="nl"&gt;color&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="m"&gt;#e2e8f0&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;

&lt;span class="nc"&gt;.button&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
  &lt;span class="nl"&gt;cursor&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="nb"&gt;pointer&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
  &lt;span class="nl"&gt;color&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="no"&gt;white&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
  &lt;span class="nl"&gt;background&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="m"&gt;#2563eb&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;

&lt;span class="nc"&gt;.button--secondary&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
  &lt;span class="nl"&gt;background&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="m"&gt;#334155&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;

&lt;span class="nc"&gt;.page-intro&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
  &lt;span class="nl"&gt;margin-bottom&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="m"&gt;24px&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;

&lt;span class="nc"&gt;.product-grid&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
  &lt;span class="nl"&gt;display&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="n"&gt;grid&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
  &lt;span class="py"&gt;grid-template-columns&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="nb"&gt;repeat&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;auto-fit&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;minmax&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="m"&gt;240px&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="m"&gt;1&lt;/span&gt;&lt;span class="n"&gt;fr&lt;/span&gt;&lt;span class="p"&gt;));&lt;/span&gt;
  &lt;span class="py"&gt;gap&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="m"&gt;16px&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;

&lt;span class="nc"&gt;.product-card&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
  &lt;span class="nl"&gt;padding&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="m"&gt;20px&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
  &lt;span class="nl"&gt;border&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="m"&gt;1px&lt;/span&gt; &lt;span class="nb"&gt;solid&lt;/span&gt; &lt;span class="m"&gt;#1e293b&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
  &lt;span class="nl"&gt;border-radius&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="m"&gt;18px&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
  &lt;span class="nl"&gt;background&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="m"&gt;#111827&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;

&lt;span class="nc"&gt;.product-card__emoji&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
  &lt;span class="nl"&gt;font-size&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="m"&gt;40px&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
  &lt;span class="nl"&gt;margin-bottom&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="m"&gt;12px&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;

&lt;span class="nc"&gt;.product-card__footer&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
  &lt;span class="nl"&gt;display&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="n"&gt;flex&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
  &lt;span class="nl"&gt;align-items&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="nb"&gt;center&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
  &lt;span class="nl"&gt;justify-content&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="n"&gt;space-between&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
  &lt;span class="nl"&gt;margin-top&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="m"&gt;16px&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Worth noting:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;The dark theme makes component boundaries more visible.&lt;/li&gt;
&lt;li&gt;The &lt;code&gt;product-grid&lt;/code&gt; layout lets you inspect card organisms comfortably.&lt;/li&gt;
&lt;li&gt;Variant classes like &lt;code&gt;button--secondary&lt;/code&gt; demonstrate the flexibility built at the atom level.&lt;/li&gt;
&lt;/ul&gt;

&lt;blockquote&gt;
&lt;p&gt;📝 I realized I've been defaulting to SCSS and CSS Modules in almost all my recent articles. For a real Storybook project I'd still go with CSS Modules, but this time I wanted to mix things up and bring back some old-school vibes 🥲 so I went with BEM throughout.&lt;/p&gt;
&lt;/blockquote&gt;




&lt;h2&gt;
  
  
  👀 Isolated Component Development with Storybook
&lt;/h2&gt;

&lt;p&gt;So why is Storybook so valuable here? Because it lets you test each layer of your Atomic Design system individually, without any dependency on the running 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.amazonaws.com%2Fuploads%2Farticles%2Fkzr4sv2ev4b9lx4k0m77.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.amazonaws.com%2Fuploads%2Farticles%2Fkzr4sv2ev4b9lx4k0m77.png" alt="Isolated components with storybook" width="720" height="393"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;Even before the app is up, you can validate &lt;code&gt;Button&lt;/code&gt;, &lt;code&gt;SearchBox&lt;/code&gt;, or &lt;code&gt;ProductCard&lt;/code&gt; in complete isolation.&lt;/p&gt;

&lt;h3&gt;
  
  
  Step 1: Write a story for &lt;code&gt;Button&lt;/code&gt;
&lt;/h3&gt;



&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="c1"&gt;// src/components/atoms/Button.stories.js&lt;/span&gt;
&lt;span class="k"&gt;import&lt;/span&gt; &lt;span class="nx"&gt;Button&lt;/span&gt; &lt;span class="k"&gt;from&lt;/span&gt; &lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;./Button&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;

&lt;span class="k"&gt;export&lt;/span&gt; &lt;span class="k"&gt;default&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
  &lt;span class="na"&gt;title&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;Atoms/Button&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
  &lt;span class="na"&gt;component&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="nx"&gt;Button&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
  &lt;span class="na"&gt;args&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="na"&gt;children&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;Add to Cart&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
    &lt;span class="na"&gt;variant&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;primary&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
  &lt;span class="p"&gt;},&lt;/span&gt;
&lt;span class="p"&gt;};&lt;/span&gt;

&lt;span class="k"&gt;export&lt;/span&gt; &lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;Primary&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="p"&gt;{};&lt;/span&gt;

&lt;span class="k"&gt;export&lt;/span&gt; &lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;Secondary&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
  &lt;span class="na"&gt;args&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="na"&gt;children&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;Details&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
    &lt;span class="na"&gt;variant&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;secondary&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
  &lt;span class="p"&gt;},&lt;/span&gt;
&lt;span class="p"&gt;};&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Things to pay attention to:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;code&gt;title: "Atoms/Button"&lt;/code&gt; categorizes the component according to its atomic layer.&lt;/li&gt;
&lt;li&gt;
&lt;code&gt;args&lt;/code&gt; makes it trivial to test different variations quickly.&lt;/li&gt;
&lt;li&gt;Defining multiple visual states for the same atom becomes effortless.&lt;/li&gt;
&lt;/ul&gt;

&lt;h3&gt;
  
  
  Step 2: Write a story for &lt;code&gt;ProductCard&lt;/code&gt;
&lt;/h3&gt;



&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="c1"&gt;// src/components/organisms/ProductCard.stories.js&lt;/span&gt;
&lt;span class="k"&gt;import&lt;/span&gt; &lt;span class="nx"&gt;ProductCard&lt;/span&gt; &lt;span class="k"&gt;from&lt;/span&gt; &lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;./ProductCard&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;

&lt;span class="k"&gt;export&lt;/span&gt; &lt;span class="k"&gt;default&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
  &lt;span class="na"&gt;title&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;Organisms/ProductCard&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
  &lt;span class="na"&gt;component&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="nx"&gt;ProductCard&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
  &lt;span class="na"&gt;args&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="na"&gt;product&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
      &lt;span class="na"&gt;id&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
      &lt;span class="na"&gt;emoji&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;⌨️&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
      &lt;span class="na"&gt;title&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;Mechanical Keyboard&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
      &lt;span class="na"&gt;description&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;Hot-swappable, compact keyboard with RGB support.&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
      &lt;span class="na"&gt;price&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="mi"&gt;2499&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
    &lt;span class="p"&gt;},&lt;/span&gt;
  &lt;span class="p"&gt;},&lt;/span&gt;
&lt;span class="p"&gt;};&lt;/span&gt;

&lt;span class="k"&gt;export&lt;/span&gt; &lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;Default&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="p"&gt;{};&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Key takeaways:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Organism-level components can also be tested independently of the page.&lt;/li&gt;
&lt;li&gt;We can develop without waiting on a real API by using mock data.&lt;/li&gt;
&lt;li&gt;Visual regression checks and UI reviews become much more manageable.&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;When Storybook and Atomic Design work together, producing, testing, and sharing components becomes significantly easier.&lt;/p&gt;




&lt;h2&gt;
  
  
  ⚖️ Pros and Cons of Atomic Design
&lt;/h2&gt;

&lt;p&gt;Like any solid approach, Atomic Design has both strengths and trade-offs. Rather than applying it blindly, it's worth understanding what it gives you and where it introduces overhead.&lt;/p&gt;

&lt;h3&gt;
  
  
  Pros
&lt;/h3&gt;

&lt;p&gt;★ Component boundaries become much clearer.&lt;br&gt;
★ Reusability increases significantly.&lt;br&gt;
★ Storybook, testing, and design system workflows get stronger.&lt;br&gt;
★ Large teams develop a shared UI vocabulary.&lt;br&gt;
★ Refactoring becomes safer and more predictable.&lt;/p&gt;

&lt;h3&gt;
  
  
  Cons
&lt;/h3&gt;

&lt;p&gt;★ Can feel over-engineered for small or single-screen apps.&lt;br&gt;
★ Misinterpreting the layers leads to unnecessary file sprawl.&lt;br&gt;
★ Over-decomposing every component can slow down initial development velocity.&lt;br&gt;
★ Requires some upfront discipline, especially for teams new to the approach.&lt;/p&gt;

&lt;p&gt;To be direct about it: Atomic Design is not a silver bullet. But for UI-heavy projects with real growth potential, it provides an exceptionally strong foundation.&lt;/p&gt;




&lt;h2&gt;
  
  
  😅 Common Mistakes
&lt;/h2&gt;

&lt;p&gt;Here are the most frequent mistakes I see when teams adopt this approach:&lt;/p&gt;

&lt;p&gt;★ &lt;strong&gt;Atomizing everything&lt;/strong&gt;&lt;br&gt;
A component isn't automatically an atom just because it's small. What matters is its responsibility.&lt;/p&gt;

&lt;p&gt;★ &lt;strong&gt;Confusing templates and pages&lt;/strong&gt;&lt;br&gt;
Layout knowledge belongs in the template. Data and behavior belong in the page.&lt;/p&gt;

&lt;p&gt;★ &lt;strong&gt;Embedding business logic in atoms&lt;/strong&gt;&lt;br&gt;
Atom-level components should stay as pure as possible.&lt;/p&gt;

&lt;p&gt;★ &lt;strong&gt;Treating the folder structure as the end goal&lt;/strong&gt;&lt;br&gt;
Atomic Design exists for sustainable UI architecture, not for aesthetic folder organization.&lt;/p&gt;

&lt;p&gt;★ &lt;strong&gt;Using Storybook purely as a showcase&lt;/strong&gt;&lt;br&gt;
The real value is in developing components in isolation and catching edge cases early.&lt;/p&gt;

&lt;p&gt;Another critical mistake shows up in naming. The moment you see &lt;code&gt;Card2&lt;/code&gt;, &lt;code&gt;HeaderNew&lt;/code&gt;, or &lt;code&gt;ButtonLatest&lt;/code&gt;, stop and reconsider.&lt;/p&gt;




&lt;h2&gt;
  
  
  🤔 When Should You Use It?
&lt;/h2&gt;

&lt;p&gt;Atomic Design shines especially in projects where component count is growing and reusable UI pieces are multiplying. When combined with React, the approach feels even more natural because you're already working in a component-based world.&lt;/p&gt;

&lt;p&gt;If you're building a small, single-screen app, you probably don't need this many layers. But if you're building a design system, if different teams are sharing the same UI pieces, or if the project is scaling quickly, Atomic Design becomes a very compelling choice.&lt;/p&gt;

&lt;p&gt;Think of Atomic Design not just as theory, but as a daily development practice. When paired with React and Storybook, you end up with a frontend architecture that is more organized, more readable, and far more scalable.&lt;/p&gt;




&lt;h2&gt;
  
  
  📬 Feedback
&lt;/h2&gt;

&lt;p&gt;While writing this article, I used GPT 5.4 High for research, source selection, and copyediting. Images were generated with Gemini 3 Pro Preview 2k (Nano Banana Pro).&lt;/p&gt;

&lt;p&gt;I genuinely welcome feedback, suggestions, and criticism. If you'd like to get in touch, you can reach me via the social links on &lt;a href="https://yasinates.com/iletisim" rel="noopener noreferrer"&gt;my website&lt;/a&gt; or connect with me on &lt;a href="https://linkedin.com/in/yasinatesim" rel="noopener noreferrer"&gt;LinkedIn&lt;/a&gt;.&lt;/p&gt;

&lt;p&gt;Best, Yasin 🤗&lt;/p&gt;




&lt;h2&gt;
  
  
  📚 References
&lt;/h2&gt;

&lt;ol&gt;
&lt;li&gt;
&lt;a href="https://atomicdesign.bradfrost.com/" rel="noopener noreferrer"&gt;Atomic Design by Brad Frost&lt;/a&gt; - Used to clarify the core concepts and layer definitions of the Atomic Design methodology.&lt;/li&gt;
&lt;li&gt;
&lt;a href="https://react.dev/" rel="noopener noreferrer"&gt;React Documentation&lt;/a&gt; - Used for React component architecture, state management, and foundational patterns.&lt;/li&gt;
&lt;li&gt;
&lt;a href="https://storybook.js.org/docs/get-started/frameworks/react-vite" rel="noopener noreferrer"&gt;Storybook for React&lt;/a&gt; - Referenced for Storybook setup and React integration.&lt;/li&gt;
&lt;li&gt;
&lt;a href="https://vite.dev/guide/" rel="noopener noreferrer"&gt;Vite Guide&lt;/a&gt; - Used to verify the Vite setup flow for bootstrapping the React project quickly.&lt;/li&gt;
&lt;li&gt;
&lt;a href="https://storybook.js.org/docs/writing-stories" rel="noopener noreferrer"&gt;Storybook Writing Stories&lt;/a&gt; - Used to clarify how story files should be structured and written.&lt;/li&gt;
&lt;li&gt;
&lt;a href="https://getbem.com/" rel="noopener noreferrer"&gt;BEM CSS Convention&lt;/a&gt; - The CSS methodology used throughout the article.&lt;/li&gt;
&lt;/ol&gt;

</description>
      <category>storybook</category>
      <category>react</category>
      <category>atomicdesign</category>
      <category>frontend</category>
    </item>
    <item>
      <title>Monorepo Architecture with pnpm Workspace, Turborepo &amp; Changesets 📦</title>
      <dc:creator>Yasin ATEŞ</dc:creator>
      <pubDate>Wed, 01 Apr 2026 17:10:00 +0000</pubDate>
      <link>https://dev.to/yasinatesim/monorepo-architecture-with-pnpm-workspace-turborepo-changesets-g0j</link>
      <guid>https://dev.to/yasinatesim/monorepo-architecture-with-pnpm-workspace-turborepo-changesets-g0j</guid>
      <description>&lt;p&gt;When you're developing a project with multiple packages, managing each one in its own repo can quickly turn into a nightmare. In this article, we'll set up a monorepo architecture from scratch using &lt;strong&gt;pnpm workspace&lt;/strong&gt;, speed up build processes with &lt;strong&gt;Turborepo&lt;/strong&gt;, and build an automated NPM publish pipeline with &lt;strong&gt;Changesets&lt;/strong&gt;.&lt;/p&gt;




&lt;h2&gt;
  
  
  🏗️ What Is a Monorepo?
&lt;/h2&gt;

&lt;p&gt;Let's say you're building a design system. You have a core package, a theme package, and a utils package. Now imagine keeping all of these in &lt;strong&gt;separate repositories&lt;/strong&gt;.&lt;/p&gt;

&lt;p&gt;When you fix a bug in the core package, what happens? You switch to the theme repo and update the dependency. Then you switch to the utils repo. You open separate PRs for each, wait for separate CI/CD pipelines, and publish separately. Even with just three packages, this process is exhausting — with ten, it's a total nightmare.&lt;/p&gt;

&lt;p&gt;This is exactly where the &lt;strong&gt;monorepo&lt;/strong&gt; comes in.&lt;/p&gt;

&lt;p&gt;A monorepo is an architectural approach that houses multiple projects &lt;strong&gt;under a single repository&lt;/strong&gt;. All your packages live in the same repo, share the same commit history, and can easily reference each other.&lt;/p&gt;

&lt;p&gt;So why does this matter? Let's look at a few key advantages:&lt;/p&gt;

&lt;p&gt;★ &lt;strong&gt;Code sharing in one place:&lt;/strong&gt; Shared utilities, types, and configurations are instantly available to all packages. No need to wait for an NPM publish.&lt;/p&gt;

&lt;p&gt;★ &lt;strong&gt;Atomic changes:&lt;/strong&gt; You can make a change that affects multiple packages in a single commit. No more cross-repo PR synchronization headaches.&lt;/p&gt;

&lt;p&gt;★ &lt;strong&gt;Consistent tooling:&lt;/strong&gt; ESLint, Prettier, and TypeScript configurations are managed from a single source. The question "Why does this repo have different rules?" becomes a thing of the past.&lt;/p&gt;

&lt;p&gt;★ &lt;strong&gt;Easy onboarding:&lt;/strong&gt; When a new developer joins the project, a single &lt;code&gt;git clone&lt;/code&gt; and &lt;code&gt;pnpm install&lt;/code&gt; brings up the entire ecosystem.&lt;/p&gt;




&lt;h2&gt;
  
  
  🔧 Setting Up a pnpm Workspace
&lt;/h2&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.amazonaws.com%2Fuploads%2Farticles%2Fnjtwoqxuhs6nj5ue2w8e.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.amazonaws.com%2Fuploads%2Farticles%2Fnjtwoqxuhs6nj5ue2w8e.png" alt="pnpm workspace setup" width="800" height="436"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;pnpm&lt;/strong&gt; stands out among Node.js package managers for its monorepo support. Unlike npm and yarn, its &lt;strong&gt;content-addressable store&lt;/strong&gt; keeps all dependencies in a global store and links them into your projects via hard links. This saves a massive amount of disk space.&lt;/p&gt;

&lt;p&gt;Let's walk through setting up a monorepo architecture with pnpm workspace using a sample project.&lt;/p&gt;

&lt;h3&gt;
  
  
  Step 1: Install pnpm and Initialize the Project
&lt;/h3&gt;

&lt;p&gt;Install pnpm globally:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;npm &lt;span class="nb"&gt;install&lt;/span&gt; &lt;span class="nt"&gt;-g&lt;/span&gt; pnpm
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Then initialize a new monorepo project:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;&lt;span class="nb"&gt;mkdir &lt;/span&gt;my-design-system
&lt;span class="nb"&gt;cd &lt;/span&gt;my-design-system
pnpm init
git init
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;★ The &lt;code&gt;pnpm init&lt;/code&gt; command creates a &lt;code&gt;package.json&lt;/code&gt; file at the root level.&lt;/p&gt;

&lt;p&gt;★ This file will serve as the main entry point for your monorepo. All workspace scripts will be managed from here.&lt;/p&gt;

&lt;h3&gt;
  
  
  Step 2: Create pnpm-workspace.yaml
&lt;/h3&gt;

&lt;p&gt;Create a &lt;code&gt;pnpm-workspace.yaml&lt;/code&gt; file in the project root:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight yaml"&gt;&lt;code&gt;&lt;span class="na"&gt;packages&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt;
  &lt;span class="pi"&gt;-&lt;/span&gt; &lt;span class="s2"&gt;"&lt;/span&gt;&lt;span class="s"&gt;packages/*"&lt;/span&gt;
  &lt;span class="pi"&gt;-&lt;/span&gt; &lt;span class="s2"&gt;"&lt;/span&gt;&lt;span class="s"&gt;apps/*"&lt;/span&gt;
  &lt;span class="pi"&gt;-&lt;/span&gt; &lt;span class="s2"&gt;"&lt;/span&gt;&lt;span class="s"&gt;website"&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;★ The &lt;code&gt;packages/*&lt;/code&gt; expression defines each folder under the &lt;code&gt;packages&lt;/code&gt; directory as a separate workspace package.&lt;/p&gt;

&lt;p&gt;★ &lt;code&gt;apps/*&lt;/code&gt; includes applications, and &lt;code&gt;website&lt;/code&gt; adds the documentation site to the workspace.&lt;/p&gt;

&lt;p&gt;★ Without this file, pnpm won't recognize your project as a monorepo.&lt;/p&gt;

&lt;h3&gt;
  
  
  Step 3: Configure the Root package.json
&lt;/h3&gt;

&lt;p&gt;Configure the root &lt;code&gt;package.json&lt;/code&gt; for the monorepo:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight json"&gt;&lt;code&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="w"&gt;
  &lt;/span&gt;&lt;span class="nl"&gt;"name"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"my-design-system"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt;
  &lt;/span&gt;&lt;span class="nl"&gt;"private"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="kc"&gt;true&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt;
  &lt;/span&gt;&lt;span class="nl"&gt;"scripts"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="w"&gt;
    &lt;/span&gt;&lt;span class="nl"&gt;"dev"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"turbo run dev"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt;
    &lt;/span&gt;&lt;span class="nl"&gt;"build"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"turbo run build"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt;
    &lt;/span&gt;&lt;span class="nl"&gt;"test"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"turbo run test"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt;
    &lt;/span&gt;&lt;span class="nl"&gt;"lint"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"turbo run lint"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt;
    &lt;/span&gt;&lt;span class="nl"&gt;"clean"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"turbo run clean"&lt;/span&gt;&lt;span class="w"&gt;
  &lt;/span&gt;&lt;span class="p"&gt;},&lt;/span&gt;&lt;span class="w"&gt;
  &lt;/span&gt;&lt;span class="nl"&gt;"devDependencies"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="w"&gt;
    &lt;/span&gt;&lt;span class="nl"&gt;"turbo"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"^2.3.1"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt;
    &lt;/span&gt;&lt;span class="nl"&gt;"typescript"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"^5.7.2"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt;
    &lt;/span&gt;&lt;span class="nl"&gt;"tsup"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"^8.3.5"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt;
    &lt;/span&gt;&lt;span class="nl"&gt;"vitest"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"^2.1.6"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt;
    &lt;/span&gt;&lt;span class="nl"&gt;"prettier"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"^3.4.1"&lt;/span&gt;&lt;span class="w"&gt;
  &lt;/span&gt;&lt;span class="p"&gt;},&lt;/span&gt;&lt;span class="w"&gt;
  &lt;/span&gt;&lt;span class="nl"&gt;"packageManager"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"pnpm@9.14.2"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt;
  &lt;/span&gt;&lt;span class="nl"&gt;"engines"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="w"&gt;
    &lt;/span&gt;&lt;span class="nl"&gt;"node"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"&amp;gt;=18.0.0"&lt;/span&gt;&lt;span class="w"&gt;
  &lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;★ &lt;code&gt;"private": true&lt;/code&gt; is a critical setting. It prevents the root package from being accidentally published to NPM.&lt;/p&gt;

&lt;p&gt;★ The &lt;code&gt;"packageManager"&lt;/code&gt; field ensures that everyone who clones the project uses the same pnpm version. &lt;strong&gt;Corepack&lt;/strong&gt; reads this field and automatically activates the correct package manager.&lt;/p&gt;

&lt;p&gt;★ Shared devDependencies (like TypeScript and Prettier) are installed at the root, so individual packages don't need to install them separately.&lt;/p&gt;

&lt;h3&gt;
  
  
  Step 4: Create the Project Structure
&lt;/h3&gt;

&lt;p&gt;Now let's create the folder structure:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;&lt;span class="nb"&gt;mkdir&lt;/span&gt; &lt;span class="nt"&gt;-p&lt;/span&gt; packages/core
&lt;span class="nb"&gt;mkdir&lt;/span&gt; &lt;span class="nt"&gt;-p&lt;/span&gt; packages/utils
&lt;span class="nb"&gt;mkdir&lt;/span&gt; &lt;span class="nt"&gt;-p&lt;/span&gt; packages/theme
&lt;span class="nb"&gt;mkdir&lt;/span&gt; &lt;span class="nt"&gt;-p&lt;/span&gt; apps/docs
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;A typical monorepo structure looks like this:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;my-design-system/
├── packages/
│   ├── core/               # Core library
│   ├── utils/              # Shared utility functions
│   └── theme/              # Theme and style definitions
├── apps/
│   └── docs/               # Documentation app
├── .changeset/             # Changesets configuration
├── .github/                # CI/CD workflows
├── package.json            # Root workspace config
├── pnpm-workspace.yaml     # Workspace definition
├── turbo.json              # Turborepo pipeline
├── tsconfig.base.json      # Shared TypeScript config
└── pnpm-lock.yaml          # Lock file
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;★ Libraries and shared modules live under &lt;code&gt;packages/&lt;/code&gt;. Each one can be published as an independent npm package.&lt;/p&gt;

&lt;p&gt;★ Applications that consume these packages go under &lt;code&gt;apps/&lt;/code&gt;.&lt;/p&gt;

&lt;p&gt;★ Configuration files at the root apply across the entire monorepo.&lt;/p&gt;

&lt;p&gt;You also need to initialize each sub-package. For example, for &lt;code&gt;packages/core&lt;/code&gt;:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;&lt;span class="nb"&gt;cd &lt;/span&gt;packages/core
pnpm init
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;This creates a &lt;code&gt;package.json&lt;/code&gt; for each package. Using namespaced package names is a good practice:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight json"&gt;&lt;code&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="w"&gt;
  &lt;/span&gt;&lt;span class="nl"&gt;"name"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"@myds/core"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt;
  &lt;/span&gt;&lt;span class="nl"&gt;"version"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"0.1.0"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt;
  &lt;/span&gt;&lt;span class="nl"&gt;"main"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"dist/index.js"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt;
  &lt;/span&gt;&lt;span class="nl"&gt;"types"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"dist/index.d.ts"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt;
  &lt;/span&gt;&lt;span class="nl"&gt;"scripts"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="w"&gt;
    &lt;/span&gt;&lt;span class="nl"&gt;"build"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"tsup src/index.ts --format cjs,esm --dts"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt;
    &lt;/span&gt;&lt;span class="nl"&gt;"dev"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"tsup src/index.ts --format cjs,esm --dts --watch"&lt;/span&gt;&lt;span class="w"&gt;
  &lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;★ Scoped names like &lt;code&gt;@myds/core&lt;/code&gt; prevent namespace collisions on NPM.&lt;/p&gt;

&lt;p&gt;★ The &lt;code&gt;main&lt;/code&gt; and &lt;code&gt;types&lt;/code&gt; fields ensure that other packages resolve the correct files when importing this package.&lt;/p&gt;

&lt;p&gt;★ &lt;strong&gt;tsup&lt;/strong&gt; is a great tool for quickly bundling TypeScript packages. It produces output in both CJS and ESM formats.&lt;/p&gt;




&lt;h2&gt;
  
  
  🔗 Cross-Package Dependency Management with the workspace Protocol
&lt;/h2&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.amazonaws.com%2Fuploads%2Farticles%2Fott1e2blkvaqfnkv9wlv.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.amazonaws.com%2Fuploads%2Farticles%2Fott1e2blkvaqfnkv9wlv.png" alt="pnpm workspace* protocol" width="800" height="436"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;One of the most powerful features of a monorepo is the ability for packages to reference each other &lt;strong&gt;locally&lt;/strong&gt;. pnpm achieves this through the &lt;code&gt;workspace:&lt;/code&gt; protocol.&lt;/p&gt;

&lt;p&gt;Let's make this concrete with an example. Say the &lt;code&gt;@myds/theme&lt;/code&gt; package depends on &lt;code&gt;@myds/core&lt;/code&gt;. You'd define this dependency like so:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight json"&gt;&lt;code&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="w"&gt;
  &lt;/span&gt;&lt;span class="nl"&gt;"name"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"@myds/theme"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt;
  &lt;/span&gt;&lt;span class="nl"&gt;"version"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"0.4.0"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt;
  &lt;/span&gt;&lt;span class="nl"&gt;"dependencies"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="w"&gt;
    &lt;/span&gt;&lt;span class="nl"&gt;"@myds/core"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"workspace:*"&lt;/span&gt;&lt;span class="w"&gt;
  &lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;★ The &lt;code&gt;workspace:*&lt;/code&gt; expression tells pnpm: "Don't download this package from the npm registry — use the local version from the workspace."&lt;br&gt;
★ During development, packages are linked together via symlinks. Any change you make in core is instantly reflected in theme.&lt;/p&gt;

&lt;p&gt;But what happens at publish time? Here's the beauty of pnpm: when you run &lt;code&gt;pnpm publish&lt;/code&gt;, &lt;code&gt;workspace:*&lt;/code&gt; is automatically converted to the actual version number.&lt;/p&gt;

&lt;p&gt;So while &lt;code&gt;package.json&lt;/code&gt; looks like this during development:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight json"&gt;&lt;code&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="w"&gt;
  &lt;/span&gt;&lt;span class="nl"&gt;"dependencies"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="w"&gt;
    &lt;/span&gt;&lt;span class="nl"&gt;"@myds/core"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"workspace:*"&lt;/span&gt;&lt;span class="w"&gt;
  &lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;It becomes this when published to NPM:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight json"&gt;&lt;code&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="w"&gt;
  &lt;/span&gt;&lt;span class="nl"&gt;"dependencies"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="w"&gt;
    &lt;/span&gt;&lt;span class="nl"&gt;"@myds/core"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"0.4.0"&lt;/span&gt;&lt;span class="w"&gt;
  &lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;h3&gt;
  
  
  Variants of the workspace Protocol
&lt;/h3&gt;

&lt;p&gt;pnpm offers several workspace protocol variants:&lt;/p&gt;

&lt;p&gt;★ &lt;strong&gt;&lt;code&gt;workspace:*&lt;/code&gt;&lt;/strong&gt; is the most commonly used variant. It means "use whatever version is currently in the workspace." At publish time, it resolves to an exact version (e.g., &lt;code&gt;"0.4.0"&lt;/code&gt;).&lt;/p&gt;

&lt;p&gt;★ &lt;strong&gt;&lt;code&gt;workspace:^&lt;/code&gt;&lt;/strong&gt; resolves to a caret range at publish time (e.g., &lt;code&gt;"^0.4.0"&lt;/code&gt;). This allows minor and patch updates.&lt;/p&gt;

&lt;p&gt;★ &lt;strong&gt;&lt;code&gt;workspace:~&lt;/code&gt;&lt;/strong&gt; resolves to a tilde range at publish time (e.g., &lt;code&gt;"~0.4.0"&lt;/code&gt;). This allows only patch updates.&lt;/p&gt;

&lt;p&gt;Here's my take on when to use which: if you always publish all packages together, &lt;code&gt;workspace:*&lt;/code&gt; is sufficient. But if you want consumers to be able to mix different versions, &lt;code&gt;workspace:^&lt;/code&gt; offers more flexibility.&lt;/p&gt;

&lt;h3&gt;
  
  
  Adding Dependencies Between Packages
&lt;/h3&gt;

&lt;p&gt;To add one workspace package as a dependency of another, use the &lt;code&gt;--filter&lt;/code&gt; flag:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;pnpm add @myds/core &lt;span class="nt"&gt;--filter&lt;/span&gt; @myds/theme
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;★ The &lt;code&gt;--filter&lt;/code&gt; flag runs the command only in the specified package.&lt;/p&gt;

&lt;p&gt;★ pnpm automatically adds the dependency as &lt;code&gt;workspace:^&lt;/code&gt; (if it exists in the workspace).&lt;/p&gt;

&lt;p&gt;You can also run scripts across all dependents of a specific package:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;&lt;span class="c"&gt;# Build @myds/core and all packages that depend on it&lt;/span&gt;
pnpm &lt;span class="nt"&gt;--filter&lt;/span&gt; &lt;span class="s2"&gt;"@myds/core..."&lt;/span&gt; build
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;To add a dependency to the root workspace, use the &lt;code&gt;--workspace-root&lt;/code&gt; (or &lt;code&gt;-w&lt;/code&gt; for short) flag:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;pnpm add &lt;span class="nt"&gt;-D&lt;/span&gt; typescript &lt;span class="nt"&gt;--workspace-root&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;






&lt;h2&gt;
  
  
  ⚡ Build Orchestration with Turborepo
&lt;/h2&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.amazonaws.com%2Fuploads%2Farticles%2Fxlmya1hnukudaxfkywij.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.amazonaws.com%2Fuploads%2Farticles%2Fxlmya1hnukudaxfkywij.png" alt="turborepo" width="800" height="436"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;While pnpm workspace alone is sufficient for package management and linking, build processes get more complex as the number of packages grows. Questions like "Which package should be built first?" and "Do we really need to rebuild packages that haven't changed?" start to come up.&lt;/p&gt;

&lt;p&gt;This is exactly where &lt;strong&gt;Turborepo&lt;/strong&gt; steps in. Turborepo is a &lt;strong&gt;build system&lt;/strong&gt; developed by Vercel that works directly with pnpm workspace. It reads pnpm's workspace structure, analyzes the dependency graph between packages, and optimizes tasks accordingly. It has two core features:&lt;/p&gt;

&lt;p&gt;★ &lt;strong&gt;Smart task scheduling:&lt;/strong&gt; It analyzes the dependency graph between packages and automatically determines the build order. Packages that don't depend on each other are run &lt;strong&gt;in parallel&lt;/strong&gt;.&lt;/p&gt;

&lt;p&gt;★ &lt;strong&gt;Hard caching:&lt;/strong&gt; If a package hasn't changed, it restores the previous build output from cache. While the first build might take 30 seconds, a cached build can complete in &lt;strong&gt;0.2 seconds&lt;/strong&gt;.&lt;/p&gt;

&lt;h3&gt;
  
  
  Let's Set Up Turborepo
&lt;/h3&gt;

&lt;p&gt;Add turbo to the root &lt;code&gt;package.json&lt;/code&gt;:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;pnpm add &lt;span class="nt"&gt;-D&lt;/span&gt; turbo &lt;span class="nt"&gt;--workspace-root&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;★ The &lt;code&gt;--workspace-root&lt;/code&gt; flag (or &lt;code&gt;-w&lt;/code&gt; for short) installs the package at the root workspace, making turbo available across the entire monorepo.&lt;/p&gt;

&lt;h3&gt;
  
  
  turbo.json Configuration
&lt;/h3&gt;

&lt;p&gt;Create a &lt;code&gt;turbo.json&lt;/code&gt; file at the project root:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight json"&gt;&lt;code&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="w"&gt;
  &lt;/span&gt;&lt;span class="nl"&gt;"$schema"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"https://turbo.build/schema.json"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt;
  &lt;/span&gt;&lt;span class="nl"&gt;"tasks"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="w"&gt;
    &lt;/span&gt;&lt;span class="nl"&gt;"build"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="w"&gt;
      &lt;/span&gt;&lt;span class="nl"&gt;"dependsOn"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="s2"&gt;"^build"&lt;/span&gt;&lt;span class="p"&gt;],&lt;/span&gt;&lt;span class="w"&gt;
      &lt;/span&gt;&lt;span class="nl"&gt;"outputs"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="s2"&gt;"dist/**"&lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt;&lt;span class="w"&gt;
    &lt;/span&gt;&lt;span class="p"&gt;},&lt;/span&gt;&lt;span class="w"&gt;
    &lt;/span&gt;&lt;span class="nl"&gt;"dev"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="w"&gt;
      &lt;/span&gt;&lt;span class="nl"&gt;"cache"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="kc"&gt;false&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt;
      &lt;/span&gt;&lt;span class="nl"&gt;"persistent"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="kc"&gt;true&lt;/span&gt;&lt;span class="w"&gt;
    &lt;/span&gt;&lt;span class="p"&gt;},&lt;/span&gt;&lt;span class="w"&gt;
    &lt;/span&gt;&lt;span class="nl"&gt;"test"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="w"&gt;
      &lt;/span&gt;&lt;span class="nl"&gt;"dependsOn"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="s2"&gt;"build"&lt;/span&gt;&lt;span class="p"&gt;],&lt;/span&gt;&lt;span class="w"&gt;
      &lt;/span&gt;&lt;span class="nl"&gt;"outputs"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;[]&lt;/span&gt;&lt;span class="w"&gt;
    &lt;/span&gt;&lt;span class="p"&gt;},&lt;/span&gt;&lt;span class="w"&gt;
    &lt;/span&gt;&lt;span class="nl"&gt;"test:watch"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="w"&gt;
      &lt;/span&gt;&lt;span class="nl"&gt;"cache"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="kc"&gt;false&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt;
      &lt;/span&gt;&lt;span class="nl"&gt;"persistent"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="kc"&gt;true&lt;/span&gt;&lt;span class="w"&gt;
    &lt;/span&gt;&lt;span class="p"&gt;},&lt;/span&gt;&lt;span class="w"&gt;
    &lt;/span&gt;&lt;span class="nl"&gt;"lint"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="w"&gt;
      &lt;/span&gt;&lt;span class="nl"&gt;"outputs"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;[]&lt;/span&gt;&lt;span class="w"&gt;
    &lt;/span&gt;&lt;span class="p"&gt;},&lt;/span&gt;&lt;span class="w"&gt;
    &lt;/span&gt;&lt;span class="nl"&gt;"clean"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="w"&gt;
      &lt;/span&gt;&lt;span class="nl"&gt;"cache"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="kc"&gt;false&lt;/span&gt;&lt;span class="w"&gt;
    &lt;/span&gt;&lt;span class="p"&gt;},&lt;/span&gt;&lt;span class="w"&gt;
    &lt;/span&gt;&lt;span class="nl"&gt;"check-types"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="w"&gt;
      &lt;/span&gt;&lt;span class="nl"&gt;"dependsOn"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="s2"&gt;"^build"&lt;/span&gt;&lt;span class="p"&gt;],&lt;/span&gt;&lt;span class="w"&gt;
      &lt;/span&gt;&lt;span class="nl"&gt;"outputs"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;[]&lt;/span&gt;&lt;span class="w"&gt;
    &lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="w"&gt;
  &lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Let's pause here and understand something important: the &lt;code&gt;^&lt;/code&gt; in &lt;code&gt;"dependsOn": ["^build"]&lt;/code&gt; is crucial. It means "run my dependencies' build task first, then build me." So before &lt;code&gt;@myds/theme&lt;/code&gt; is built, its dependency &lt;code&gt;@myds/core&lt;/code&gt; gets built first.&lt;/p&gt;

&lt;p&gt;★ &lt;code&gt;"outputs": ["dist/**"]&lt;/code&gt; tells Turborepo which files to cache. On the next build, if the source code hasn't changed, the &lt;code&gt;dist/&lt;/code&gt; folder is restored from cache.&lt;/p&gt;

&lt;p&gt;★ &lt;code&gt;"cache": false&lt;/code&gt; disables caching for certain tasks. Caching doesn't make sense for long-running (persistent) tasks like dev servers.&lt;/p&gt;

&lt;p&gt;★ &lt;code&gt;"persistent": true&lt;/code&gt; keeps the task running in the background. This is necessary for scenarios like dev servers and watch mode.&lt;/p&gt;

&lt;p&gt;Now you can build all packages with a single command:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;pnpm build
&lt;span class="c"&gt;# This runs turbo run build&lt;/span&gt;
&lt;span class="c"&gt;# Turborepo analyzes the dependency graph&lt;/span&gt;
&lt;span class="c"&gt;# Builds in order: first core, then theme, then utils...&lt;/span&gt;
&lt;span class="c"&gt;# Restores unchanged packages from cache&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;






&lt;h2&gt;
  
  
  🦋 Version Management with Changesets
&lt;/h2&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.amazonaws.com%2Fuploads%2Farticles%2Fgl58iueeawl63maro6ks.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.amazonaws.com%2Fuploads%2Farticles%2Fgl58iueeawl63maro6ks.png" alt="Changesets" width="800" height="436"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;One of the trickiest aspects of a monorepo is version management. You have multiple packages, each potentially with its own independent version number. How do you decide which one to bump and when, or how to generate the changelog?&lt;/p&gt;

&lt;p&gt;This is exactly where &lt;strong&gt;Changesets&lt;/strong&gt; comes in. Changesets is a versioning tool that lets you record each change as a small markdown file.&lt;/p&gt;

&lt;h3&gt;
  
  
  Step 1: Install Changesets
&lt;/h3&gt;



&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;pnpm add &lt;span class="nt"&gt;-D&lt;/span&gt; @changesets/cli &lt;span class="nt"&gt;--workspace-root&lt;/span&gt;
pnpm changeset init
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;★ The &lt;code&gt;changeset init&lt;/code&gt; command creates a &lt;code&gt;.changeset/&lt;/code&gt; directory in your project.&lt;br&gt;
★ Inside this directory, you'll find a &lt;code&gt;config.json&lt;/code&gt; and a &lt;code&gt;README.md&lt;/code&gt; file.&lt;/p&gt;
&lt;h3&gt;
  
  
  Step 2: Configure Changesets
&lt;/h3&gt;

&lt;p&gt;Configure the &lt;code&gt;.changeset/config.json&lt;/code&gt; file for your project:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight json"&gt;&lt;code&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="w"&gt;
  &lt;/span&gt;&lt;span class="nl"&gt;"$schema"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"https://unpkg.com/@changesets/config@2.3.0/schema.json"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt;
  &lt;/span&gt;&lt;span class="nl"&gt;"changelog"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="w"&gt;
    &lt;/span&gt;&lt;span class="s2"&gt;"@changesets/changelog-github"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt;
    &lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="nl"&gt;"repo"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"your-org/your-monorepo"&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="w"&gt;
  &lt;/span&gt;&lt;span class="p"&gt;],&lt;/span&gt;&lt;span class="w"&gt;
  &lt;/span&gt;&lt;span class="nl"&gt;"commit"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="kc"&gt;false&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt;
  &lt;/span&gt;&lt;span class="nl"&gt;"fixed"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;[],&lt;/span&gt;&lt;span class="w"&gt;
  &lt;/span&gt;&lt;span class="nl"&gt;"linked"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;[[&lt;/span&gt;&lt;span class="s2"&gt;"@myds/*"&lt;/span&gt;&lt;span class="p"&gt;]],&lt;/span&gt;&lt;span class="w"&gt;
  &lt;/span&gt;&lt;span class="nl"&gt;"access"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"public"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt;
  &lt;/span&gt;&lt;span class="nl"&gt;"baseBranch"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"master"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt;
  &lt;/span&gt;&lt;span class="nl"&gt;"updateInternalDependencies"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"patch"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;&lt;span class="w"&gt;
  &lt;/span&gt;&lt;span class="nl"&gt;"ignore"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;[]&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Let's break down each of these settings:&lt;/p&gt;

&lt;p&gt;★ In the &lt;strong&gt;&lt;code&gt;changelog&lt;/code&gt;&lt;/strong&gt; section, we're using &lt;code&gt;@changesets/changelog-github&lt;/code&gt;. This automatically adds PR links and contributor information to the changelog. Let's install this package as well:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;pnpm add &lt;span class="nt"&gt;-D&lt;/span&gt; @changesets/changelog-github &lt;span class="nt"&gt;--workspace-root&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;★ The &lt;strong&gt;&lt;code&gt;linked&lt;/code&gt;&lt;/strong&gt; field is very important. &lt;code&gt;[["@myds/*"]]&lt;/code&gt; tells Changesets that the versions of all packages under the &lt;code&gt;@myds&lt;/code&gt; scope are linked together. If one gets a major bump, they all do.&lt;/p&gt;

&lt;p&gt;★ &lt;strong&gt;&lt;code&gt;"access": "public"&lt;/code&gt;&lt;/strong&gt; ensures that scoped packages (like &lt;code&gt;@myds/core&lt;/code&gt;) are published as public on NPM. Without this setting, scoped packages default to private and will throw an error during publish.&lt;/p&gt;

&lt;p&gt;★ &lt;strong&gt;&lt;code&gt;"updateInternalDependencies": "patch"&lt;/code&gt;&lt;/strong&gt; automatically applies a patch bump to the internal dependency versions of packages that depend on an updated package.&lt;/p&gt;

&lt;p&gt;★ &lt;strong&gt;&lt;code&gt;"baseBranch": "master"&lt;/code&gt;&lt;/strong&gt; determines which branch Changesets uses as its baseline. Depending on your project, this could be &lt;code&gt;main&lt;/code&gt; or &lt;code&gt;master&lt;/code&gt;.&lt;/p&gt;

&lt;h3&gt;
  
  
  Step 3: Create a Changeset
&lt;/h3&gt;

&lt;p&gt;When you make a change, create a changeset file before opening a PR:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;pnpm changeset
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;This launches an interactive wizard:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;🦋  Which packages would you like to include?
  ◯ @myds/core
  ◯ @myds/theme
  ◯ @myds/utils

🦋  Which packages should have a major bump?
🦋  Which packages should have a minor bump?

🦋  Summary: Added dark mode support to the core package
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;This wizard creates a randomly named markdown file in the &lt;code&gt;.changeset/&lt;/code&gt; directory:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight markdown"&gt;&lt;code&gt;&lt;span class="nn"&gt;---&lt;/span&gt;
&lt;span class="s2"&gt;"&lt;/span&gt;&lt;span class="s"&gt;@myds/core"&lt;/span&gt;&lt;span class="err"&gt;:&lt;/span&gt; &lt;span class="s"&gt;minor&lt;/span&gt;
&lt;span class="s2"&gt;"&lt;/span&gt;&lt;span class="s"&gt;@myds/theme"&lt;/span&gt;&lt;span class="err"&gt;:&lt;/span&gt; &lt;span class="s"&gt;patch&lt;/span&gt;
&lt;span class="nn"&gt;---&lt;/span&gt;

Added dark mode support to the core package. Updated related color variables in the theme package.
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;★ The frontmatter section specifies which package gets bumped at which level.&lt;br&gt;
★ The text below becomes the description added to the changelog.&lt;br&gt;
★ This file is included in the commit and submitted for review along with the PR.&lt;/p&gt;
&lt;h3&gt;
  
  
  Step 4: Apply the Versions
&lt;/h3&gt;

&lt;p&gt;Once all changesets have been collected, apply the versions:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;pnpm changeset version
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;★ This command reads all changeset files.&lt;br&gt;
★ Updates the version numbers in the relevant packages' &lt;code&gt;package.json&lt;/code&gt; files.&lt;br&gt;
★ Automatically creates/updates each package's &lt;code&gt;CHANGELOG.md&lt;/code&gt;.&lt;br&gt;
★ Deletes the consumed changeset files.&lt;/p&gt;
&lt;h3&gt;
  
  
  Step 5: Publish
&lt;/h3&gt;

&lt;p&gt;After versions have been applied, publish:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;pnpm changeset publish
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;This publishes all changed packages to the NPM registry. But are you going to do this manually every time? Of course not! In the next section, we'll automate this entire process 😁&lt;/p&gt;




&lt;h2&gt;
  
  
  🚀 Automated NPM Publishing with GitHub Actions
&lt;/h2&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.amazonaws.com%2Fuploads%2Farticles%2Fylux5h8ngjk3bm4110ym.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.amazonaws.com%2Fuploads%2Farticles%2Fylux5h8ngjk3bm4110ym.png" alt="auto npm pusblish with github actions" width="800" height="436"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;Enough theory — time to get our hands dirty! 🛠️ The real power of Changesets shines when combined with GitHub Actions. Let's build a CI/CD pipeline step by step.&lt;/p&gt;

&lt;h3&gt;
  
  
  Step 1: Create an NPM Token
&lt;/h3&gt;

&lt;p&gt;First, you need to create an &lt;strong&gt;Automation Token&lt;/strong&gt; on NPM:&lt;/p&gt;

&lt;p&gt;★ Go to your profile settings on &lt;a href="https://npmjs.com" rel="noopener noreferrer"&gt;npmjs.com&lt;/a&gt;.&lt;/p&gt;

&lt;p&gt;★ In the &lt;strong&gt;Access Tokens&lt;/strong&gt; section, select &lt;strong&gt;Generate New Token&lt;/strong&gt;.&lt;/p&gt;

&lt;p&gt;★ Set the token type to &lt;strong&gt;Automation&lt;/strong&gt;. This type allows publishing without requiring 2FA.&lt;/p&gt;

&lt;p&gt;★ Copy the generated token (it's only shown once!).&lt;/p&gt;

&lt;h3&gt;
  
  
  Step 2: Add Tokens to GitHub Secrets
&lt;/h3&gt;

&lt;p&gt;In your GitHub repo, go to &lt;strong&gt;Settings &amp;gt; Secrets and variables &amp;gt; Actions&lt;/strong&gt; and add the following secret:&lt;/p&gt;

&lt;p&gt;★ &lt;strong&gt;&lt;code&gt;NPM_TOKEN&lt;/code&gt;&lt;/strong&gt;: The NPM automation token you just created.&lt;/p&gt;

&lt;p&gt;&lt;code&gt;GITHUB_TOKEN&lt;/code&gt; is automatically provided by GitHub for every workflow run, so you don't need to set it up manually.&lt;/p&gt;

&lt;h3&gt;
  
  
  Step 3: Configure Repository Permissions
&lt;/h3&gt;

&lt;p&gt;In your GitHub repo, go to &lt;strong&gt;Settings &amp;gt; Actions &amp;gt; General&lt;/strong&gt;:&lt;/p&gt;

&lt;p&gt;★ Under &lt;strong&gt;Workflow permissions&lt;/strong&gt;, enable the &lt;strong&gt;"Read and write permissions"&lt;/strong&gt; option.&lt;/p&gt;

&lt;p&gt;★ Check the &lt;strong&gt;"Allow GitHub Actions to create and approve pull requests"&lt;/strong&gt; checkbox.&lt;/p&gt;

&lt;p&gt;Without these settings, the Changesets bot won't be able to create PRs.&lt;/p&gt;

&lt;h3&gt;
  
  
  Step 4: Create the Release Workflow File
&lt;/h3&gt;

&lt;p&gt;Now create the &lt;code&gt;.github/workflows/release.yml&lt;/code&gt; file:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight yaml"&gt;&lt;code&gt;&lt;span class="na"&gt;name&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;Release&lt;/span&gt;

&lt;span class="na"&gt;on&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt;
  &lt;span class="na"&gt;push&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt;
    &lt;span class="na"&gt;branches&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt;
      &lt;span class="pi"&gt;-&lt;/span&gt; &lt;span class="s"&gt;master&lt;/span&gt;

&lt;span class="na"&gt;concurrency&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt;
  &lt;span class="na"&gt;group&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;${{ github.workflow }}-${{ github.ref }}&lt;/span&gt;
  &lt;span class="na"&gt;cancel-in-progress&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="kc"&gt;false&lt;/span&gt;

&lt;span class="na"&gt;permissions&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt;
  &lt;span class="na"&gt;contents&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;write&lt;/span&gt;
  &lt;span class="na"&gt;pull-requests&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;write&lt;/span&gt;
  &lt;span class="na"&gt;packages&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;write&lt;/span&gt;
  &lt;span class="na"&gt;id-token&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;write&lt;/span&gt;

&lt;span class="na"&gt;jobs&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt;
  &lt;span class="na"&gt;release&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt;
    &lt;span class="na"&gt;name&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;Release&lt;/span&gt;
    &lt;span class="na"&gt;runs-on&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;ubuntu-latest&lt;/span&gt;
    &lt;span class="na"&gt;steps&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt;
      &lt;span class="pi"&gt;-&lt;/span&gt; &lt;span class="na"&gt;name&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;Checkout Repo&lt;/span&gt;
        &lt;span class="na"&gt;uses&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;actions/checkout@v4&lt;/span&gt;
        &lt;span class="na"&gt;with&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt;
          &lt;span class="na"&gt;fetch-depth&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="m"&gt;0&lt;/span&gt;

      &lt;span class="pi"&gt;-&lt;/span&gt; &lt;span class="na"&gt;name&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;Setup pnpm&lt;/span&gt;
        &lt;span class="na"&gt;uses&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;pnpm/action-setup@v4&lt;/span&gt;

      &lt;span class="pi"&gt;-&lt;/span&gt; &lt;span class="na"&gt;name&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;Setup Node.js&lt;/span&gt;
        &lt;span class="na"&gt;uses&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;actions/setup-node@v4&lt;/span&gt;
        &lt;span class="na"&gt;with&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt;
          &lt;span class="na"&gt;node-version&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="m"&gt;20&lt;/span&gt;
          &lt;span class="na"&gt;cache&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"&lt;/span&gt;&lt;span class="s"&gt;pnpm"&lt;/span&gt;
          &lt;span class="na"&gt;registry-url&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"&lt;/span&gt;&lt;span class="s"&gt;https://registry.npmjs.org"&lt;/span&gt;

      &lt;span class="pi"&gt;-&lt;/span&gt; &lt;span class="na"&gt;name&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;Install Dependencies&lt;/span&gt;
        &lt;span class="na"&gt;run&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;pnpm install --frozen-lockfile&lt;/span&gt;

      &lt;span class="pi"&gt;-&lt;/span&gt; &lt;span class="na"&gt;name&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;Build All Packages&lt;/span&gt;
        &lt;span class="na"&gt;run&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;pnpm build&lt;/span&gt;

      &lt;span class="pi"&gt;-&lt;/span&gt; &lt;span class="na"&gt;name&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;Create Release Pull Request or Publish&lt;/span&gt;
        &lt;span class="na"&gt;id&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;changesets&lt;/span&gt;
        &lt;span class="na"&gt;uses&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;changesets/action@v1&lt;/span&gt;
        &lt;span class="na"&gt;with&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt;
          &lt;span class="na"&gt;commit&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"&lt;/span&gt;&lt;span class="s"&gt;chore:&lt;/span&gt;&lt;span class="nv"&gt; &lt;/span&gt;&lt;span class="s"&gt;update&lt;/span&gt;&lt;span class="nv"&gt; &lt;/span&gt;&lt;span class="s"&gt;versions"&lt;/span&gt;
          &lt;span class="na"&gt;title&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"&lt;/span&gt;&lt;span class="s"&gt;chore:&lt;/span&gt;&lt;span class="nv"&gt; &lt;/span&gt;&lt;span class="s"&gt;update&lt;/span&gt;&lt;span class="nv"&gt; &lt;/span&gt;&lt;span class="s"&gt;versions"&lt;/span&gt;
          &lt;span class="na"&gt;publish&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;pnpm run ci:publish&lt;/span&gt;
        &lt;span class="na"&gt;env&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt;
          &lt;span class="na"&gt;GITHUB_TOKEN&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;${{ secrets.GITHUB_TOKEN }}&lt;/span&gt;
          &lt;span class="na"&gt;NPM_TOKEN&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;${{ secrets.NPM_TOKEN }}&lt;/span&gt;
          &lt;span class="na"&gt;NODE_AUTH_TOKEN&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;${{ secrets.NPM_TOKEN }}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;There's a lot going on in this workflow. Let's break it down piece by piece:&lt;/p&gt;

&lt;p&gt;★ The &lt;strong&gt;&lt;code&gt;concurrency&lt;/code&gt;&lt;/strong&gt; setting prevents multiple release workflows from running simultaneously. If a new push comes in while a publish is in progress, the old workflow isn't cancelled — instead, the new one waits in the queue.&lt;/p&gt;

&lt;p&gt;★ The &lt;strong&gt;&lt;code&gt;permissions&lt;/code&gt;&lt;/strong&gt; block gives the workflow the authority to write to the repo, create PRs, and publish packages.&lt;/p&gt;

&lt;p&gt;★ &lt;strong&gt;&lt;code&gt;fetch-depth: 0&lt;/code&gt;&lt;/strong&gt; pulls the full git history. Changesets needs the commit history to calculate versions.&lt;/p&gt;

&lt;p&gt;★ &lt;strong&gt;&lt;code&gt;pnpm/action-setup@v4&lt;/code&gt;&lt;/strong&gt; installs pnpm in the CI environment. It reads the &lt;code&gt;packageManager&lt;/code&gt; field from &lt;code&gt;package.json&lt;/code&gt; to install the correct version.&lt;/p&gt;

&lt;p&gt;★ &lt;strong&gt;&lt;code&gt;--frozen-lockfile&lt;/code&gt;&lt;/strong&gt; is a critical flag for CI. It installs the exact same dependencies as specified in the lock file. If &lt;code&gt;pnpm-lock.yaml&lt;/code&gt; is out of date, it throws an error.&lt;/p&gt;

&lt;p&gt;★ &lt;strong&gt;&lt;code&gt;changesets/action@v1&lt;/code&gt;&lt;/strong&gt; is the action that does all the heavy lifting. It handles two different scenarios:&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Scenario A:&lt;/strong&gt; If there are pending changeset files in the &lt;code&gt;.changeset/&lt;/code&gt; directory, it creates or updates a &lt;strong&gt;"Version Packages"&lt;/strong&gt; PR. This PR contains the version bumps and changelog updates.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Scenario B:&lt;/strong&gt; If there are no pending changesets (i.e., after the Version Packages PR has been merged), it runs the &lt;code&gt;publish&lt;/code&gt; command to publish the packages to NPM.&lt;/p&gt;

&lt;h3&gt;
  
  
  Step 5: Define the ci:publish Script
&lt;/h3&gt;

&lt;p&gt;Add the publish script to the root &lt;code&gt;package.json&lt;/code&gt;:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight json"&gt;&lt;code&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="w"&gt;
  &lt;/span&gt;&lt;span class="nl"&gt;"scripts"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="w"&gt;
    &lt;/span&gt;&lt;span class="nl"&gt;"ci:publish"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;&lt;span class="w"&gt; &lt;/span&gt;&lt;span class="s2"&gt;"pnpm publish -r --access public"&lt;/span&gt;&lt;span class="w"&gt;
  &lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="w"&gt;
&lt;/span&gt;&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;★ The &lt;code&gt;-r&lt;/code&gt; flag (recursive) publishes all workspace packages.&lt;br&gt;
★ &lt;code&gt;--access public&lt;/code&gt; ensures that scoped packages are published as public.&lt;/p&gt;

&lt;h3&gt;
  
  
  Changeset Bot
&lt;/h3&gt;

&lt;p&gt;Optionally, you can install the &lt;strong&gt;Changeset Bot&lt;/strong&gt; from &lt;a href="https://github.com/apps/changeset-bot" rel="noopener noreferrer"&gt;github.com/apps/changeset-bot&lt;/a&gt; on your repo. This bot checks whether PRs include a changeset file and leaves a warning comment if they don't.&lt;/p&gt;




&lt;h2&gt;
  
  
  🎯 Demo: The Tuvix.js Monorepo Project
&lt;/h2&gt;

&lt;p&gt;If you'd like to see the entire architecture described in this article in action, check out the &lt;strong&gt;Tuvix.js&lt;/strong&gt; project I've been developing. Tuvix.js is a lightweight micro frontend framework that uses exactly the stack covered in this article:&lt;/p&gt;

&lt;p&gt;★ &lt;strong&gt;pnpm workspace&lt;/strong&gt; managing 14+ packages in a single repo&lt;/p&gt;

&lt;p&gt;★ &lt;strong&gt;Turborepo&lt;/strong&gt; for build orchestration and caching&lt;/p&gt;

&lt;p&gt;★ &lt;strong&gt;Changesets&lt;/strong&gt; for version management and automated NPM publishing&lt;/p&gt;

&lt;p&gt;★ &lt;strong&gt;GitHub Actions&lt;/strong&gt; for the CI/CD pipeline&lt;/p&gt;

&lt;p&gt;You can explore the &lt;code&gt;pnpm-workspace.yaml&lt;/code&gt;, &lt;code&gt;turbo.json&lt;/code&gt;, &lt;code&gt;.changeset/config.json&lt;/code&gt;, and GitHub Actions workflow files directly in the repository.&lt;/p&gt;

&lt;p&gt;Check out the repo here 👇&lt;/p&gt;

&lt;p&gt;&lt;a href="https://github.com/yasinatesim/tuvix.js" rel="noopener noreferrer"&gt;github.com/yasinatesim/tuvix.js&lt;/a&gt;&lt;/p&gt;




&lt;h2&gt;
  
  
  📬 Feedback
&lt;/h2&gt;

&lt;p&gt;While writing this article, I used my own notes for identifying sources and research, the Claude Opus 4.6 model for proofreading and additional research, and the Gemini 3 Pro Preview 2k (Nano Banana Pro) model for generating images.&lt;/p&gt;

&lt;p&gt;I welcome any advice, suggestions, or feedback on this article. If you'd like to get in touch, you can reach me through my social media links on &lt;a href="https://yasinates.com/iletisim" rel="noopener noreferrer"&gt;my website&lt;/a&gt; or via &lt;a href="https://linkedin.com/in/yasinatesim" rel="noopener noreferrer"&gt;LinkedIn&lt;/a&gt;.&lt;/p&gt;

&lt;p&gt;Best, Yasin 🤗&lt;/p&gt;




&lt;h2&gt;
  
  
  📚 Resources Used While Writing This Article
&lt;/h2&gt;

&lt;ol&gt;
&lt;li&gt;
&lt;a href="https://pnpm.io/workspaces" rel="noopener noreferrer"&gt;pnpm Workspaces&lt;/a&gt; — Official documentation for pnpm's workspace feature&lt;/li&gt;
&lt;li&gt;
&lt;a href="https://pnpm.io/next/using-changesets" rel="noopener noreferrer"&gt;Using Changesets with pnpm&lt;/a&gt; — Guide on Changesets integration with pnpm&lt;/li&gt;
&lt;li&gt;
&lt;a href="https://turborepo.dev/docs/crafting-your-repository/structuring-a-repository" rel="noopener noreferrer"&gt;Turborepo - Structuring a Repository&lt;/a&gt; — Turborepo's monorepo structuring documentation&lt;/li&gt;
&lt;li&gt;
&lt;a href="https://github.com/changesets/action" rel="noopener noreferrer"&gt;Changesets GitHub Action&lt;/a&gt; — Official Changesets GitHub Action repository and usage guide&lt;/li&gt;
&lt;li&gt;
&lt;a href="https://github.com/yasinatesim/tuvix.js" rel="noopener noreferrer"&gt;Tuvix.js GitHub Repository&lt;/a&gt; — My micro frontend framework, this is monorepo project referenced in this article&lt;/li&gt;
&lt;/ol&gt;

</description>
      <category>monorepo</category>
      <category>pnpm</category>
      <category>turborepo</category>
      <category>github</category>
    </item>
    <item>
      <title>From Zero to Advanced: The Git Version Control System ☕️</title>
      <dc:creator>Yasin ATEŞ</dc:creator>
      <pubDate>Tue, 17 Mar 2026 19:15:00 +0000</pubDate>
      <link>https://dev.to/yasinatesim/from-zero-to-advanced-the-git-version-control-system-59am</link>
      <guid>https://dev.to/yasinatesim/from-zero-to-advanced-the-git-version-control-system-59am</guid>
      <description>&lt;h2&gt;
  
  
  What is Git? 🤔
&lt;/h2&gt;

&lt;p&gt;Git is a distributed version control system used to track changes in files over time during software development.&lt;/p&gt;

&lt;h2&gt;
  
  
  A Brief History of Git 📖
&lt;/h2&gt;

&lt;p&gt;Git was developed by &lt;strong&gt;Linus Torvalds&lt;/strong&gt;, the creator of Linux, in 2005.&lt;/p&gt;

&lt;p&gt;The Linux project had been using BitKeeper, a proprietary version control system, under a free license since 2002. In 2005, BitKeeper's company alleged that Linux developer Andrew Tridgell had reverse-engineered their protocol, and subsequently revoked the project's free license. Linus Torvalds then decided to write his own version control system, and Git was born.&lt;/p&gt;

&lt;h2&gt;
  
  
  Why Version Control? 🧐
&lt;/h2&gt;

&lt;p&gt;When working alone, manual backups may be enough. However, when multiple people work on the same project, tracking who changed what and when becomes difficult. A version control system automates this process and solves the following problems:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Maintains different versions of files&lt;/li&gt;
&lt;li&gt;Enables multiple developers to work on the same codebase concurrently&lt;/li&gt;
&lt;li&gt;Makes it easy to revert to a previous version when something goes wrong&lt;/li&gt;
&lt;li&gt;Provides a complete audit trail of changes&lt;/li&gt;
&lt;/ul&gt;

&lt;h2&gt;
  
  
  How Does Git Work? ⚙️
&lt;/h2&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.amazonaws.com%2Fuploads%2Farticles%2F2v3h9rzrtnchmki0j16c.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.amazonaws.com%2Fuploads%2Farticles%2F2v3h9rzrtnchmki0j16c.png" alt="How Does Git Work" width="800" height="446"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;Git consists of three fundamental layers:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;strong&gt;Working Directory:&lt;/strong&gt; The local directory where your files reside and where you actively work.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Staging Area:&lt;/strong&gt; An intermediate area where changes are staged before being committed to the repository. Think of it as a preparation area for the next commit.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Repository (Repo):&lt;/strong&gt; The repository where committed changes are stored. It is the &lt;code&gt;.git&lt;/code&gt; folder in your project directory.&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;&lt;strong&gt;The basic workflow is:&lt;/strong&gt;&lt;/p&gt;

&lt;ol&gt;
&lt;li&gt;You make changes in the working directory&lt;/li&gt;
&lt;li&gt;You add those changes to the staging area with &lt;code&gt;git add&lt;/code&gt;
&lt;/li&gt;
&lt;li&gt;You create a commit from the staged changes with &lt;code&gt;git commit&lt;/code&gt;
&lt;/li&gt;
&lt;/ol&gt;

&lt;h2&gt;
  
  
  Installation 💻
&lt;/h2&gt;

&lt;p&gt;You can download and install the appropriate version for your operating system from &lt;a href="https://git-scm.com" rel="noopener noreferrer"&gt;git-scm.com&lt;/a&gt;.&lt;/p&gt;

&lt;p&gt;To verify the installation, run the following command in your terminal:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;git &lt;span class="nt"&gt;--version&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;h2&gt;
  
  
  Configuration (git config) 🔧
&lt;/h2&gt;

&lt;p&gt;Before using Git, you should configure your user information. This information is recorded with every commit.&lt;/p&gt;

&lt;h3&gt;
  
  
  ★ Global Configuration
&lt;/h3&gt;

&lt;p&gt;The default configuration that applies to &lt;strong&gt;all&lt;/strong&gt; Git repositories on your machine is defined as follows:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;git config &lt;span class="nt"&gt;--global&lt;/span&gt; user.name &lt;span class="s2"&gt;"Yasin"&lt;/span&gt;
git config &lt;span class="nt"&gt;--global&lt;/span&gt; user.email &lt;span class="s2"&gt;"yasinatesim@gmail.com"&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;h3&gt;
  
  
  ★ Local Configuration
&lt;/h3&gt;

&lt;p&gt;The configuration that applies only to the &lt;strong&gt;current&lt;/strong&gt; repository. If a global setting with the same name exists, the local setting overrides it:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;git config &lt;span class="nt"&gt;--local&lt;/span&gt; user.name &lt;span class="s2"&gt;"Beril"&lt;/span&gt;
git config &lt;span class="nt"&gt;--local&lt;/span&gt; user.email &lt;span class="s2"&gt;"beril@yasinates.com"&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;💡 In this example, Git uses "Yasin" by default for all repositories on this machine, but in one specific project, the local configuration overrides the global one, and Git uses "Beril" for that repository.&lt;/p&gt;

&lt;h3&gt;
  
  
  ★ Useful Additional Settings
&lt;/h3&gt;



&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;&lt;span class="c"&gt;# Set default branch name to main&lt;/span&gt;
git config &lt;span class="nt"&gt;--global&lt;/span&gt; init.defaultBranch main

&lt;span class="c"&gt;# Set VS Code as the default editor&lt;/span&gt;
git config &lt;span class="nt"&gt;--global&lt;/span&gt; core.editor &lt;span class="s2"&gt;"code --wait"&lt;/span&gt;

&lt;span class="c"&gt;# Enable colored output&lt;/span&gt;
git config &lt;span class="nt"&gt;--global&lt;/span&gt; color.ui auto

&lt;span class="c"&gt;# Use rebase by default during pull&lt;/span&gt;
git config &lt;span class="nt"&gt;--global&lt;/span&gt; pull.rebase &lt;span class="nb"&gt;true&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;h3&gt;
  
  
  ★ Git Alias (Shortcuts)
&lt;/h3&gt;

&lt;p&gt;You can define shortcuts for frequently used commands:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;git config &lt;span class="nt"&gt;--global&lt;/span&gt; alias.st status
git config &lt;span class="nt"&gt;--global&lt;/span&gt; alias.co checkout
git config &lt;span class="nt"&gt;--global&lt;/span&gt; alias.br branch
git config &lt;span class="nt"&gt;--global&lt;/span&gt; alias.cm &lt;span class="s2"&gt;"commit -m"&lt;/span&gt;
git config &lt;span class="nt"&gt;--global&lt;/span&gt; alias.lg &lt;span class="s2"&gt;"log --oneline --graph --decorate --all"&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Now you can type &lt;code&gt;git st&lt;/code&gt; instead of &lt;code&gt;git status&lt;/code&gt;, and &lt;code&gt;git co&lt;/code&gt; instead of &lt;code&gt;git checkout&lt;/code&gt;.&lt;/p&gt;

&lt;h3&gt;
  
  
  ★ Checking Configurations
&lt;/h3&gt;

&lt;p&gt;To check all configurations:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;git config &lt;span class="nt"&gt;--list&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;h2&gt;
  
  
  Creating a Repository (git init) 📂
&lt;/h2&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.amazonaws.com%2Fuploads%2Farticles%2Fe81yknp4ladu37c9h01r.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.amazonaws.com%2Fuploads%2Farticles%2Fe81yknp4ladu37c9h01r.png" alt="Creating a Git Repository" width="800" height="339"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;To turn your working directory into a Git repository, navigate to the target directory in the terminal and run:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;git init
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;This command creates a hidden folder named &lt;code&gt;.git&lt;/code&gt; in your directory. All of Git's data (commit history, branch information, configuration, etc.) is stored in this folder. The default branch name will be either &lt;code&gt;master&lt;/code&gt; or &lt;code&gt;main&lt;/code&gt;, depending on your Git version and configuration. Nowadays, platforms like GitHub default to &lt;code&gt;main&lt;/code&gt;. You may also see the branch name displayed in your terminal prompt (for example, &lt;code&gt;(main)&lt;/code&gt;), depending on your shell configuration.&lt;/p&gt;

&lt;p&gt;💡 The concept of branches is covered in more detail later in this article.&lt;/p&gt;

&lt;h2&gt;
  
  
  Tracking File Status (git status) 🔍
&lt;/h2&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.amazonaws.com%2Fuploads%2Farticles%2Fy0reqoebigqi2r6nkrk9.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.amazonaws.com%2Fuploads%2Farticles%2Fy0reqoebigqi2r6nkrk9.png" alt="Git Tracking File Status" width="800" height="436"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;To see the current status of the repository:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;git status
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;This command shows which files have changed, which files are in the staging area, and which files are not yet tracked by Git (untracked).&lt;/p&gt;

&lt;p&gt;Right after &lt;code&gt;git init&lt;/code&gt;, it will report that there are no commits yet and suggest using &lt;code&gt;git add&lt;/code&gt;. Think of &lt;code&gt;git status&lt;/code&gt; as your compass in Git — when in doubt, run it.&lt;/p&gt;

&lt;h2&gt;
  
  
  Adding Changes to the Staging Area (git add) ➕
&lt;/h2&gt;

&lt;p&gt;Let's start by creating a file. Create a file named &lt;code&gt;names.txt&lt;/code&gt; in your working directory:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;Eda
Beyza
Tuvana
Melis
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;When you run &lt;code&gt;git status&lt;/code&gt;, Git will show this file as &lt;strong&gt;untracked&lt;/strong&gt;. To add this file to the staging area, in other words, to tell Git to track it:&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Add a single file:&lt;/strong&gt;&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;git add names.txt
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;&lt;strong&gt;Add all changes at once:&lt;/strong&gt;&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;git add &lt;span class="nb"&gt;.&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;⚠️ While &lt;code&gt;git add .&lt;/code&gt; is practical, it can accidentally add irrelevant files to the staging area. Especially in large projects, it's a good habit to check &lt;code&gt;git status&lt;/code&gt; first.&lt;/p&gt;

&lt;h2&gt;
  
  
  Reviewing Staging Area Changes 👀
&lt;/h2&gt;

&lt;p&gt;Run &lt;code&gt;git status&lt;/code&gt; again after the &lt;code&gt;git add&lt;/code&gt; command:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;git status
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;You will now see your file listed under &lt;strong&gt;"Changes to be committed."&lt;/strong&gt; Git automatically classifies the type of changes in the staging area.&lt;/p&gt;

&lt;h3&gt;
  
  
  ★ Change Types
&lt;/h3&gt;

&lt;p&gt;&lt;strong&gt;New File (new file):&lt;/strong&gt; A newly added file that was not previously tracked by Git.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;Changes to be committed:
    new file:   names.txt
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;&lt;strong&gt;Modified File (modified):&lt;/strong&gt; A file previously tracked by Git whose content has changed.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;Changes not staged for commit:
    modified:   names.txt
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;To discard the modification:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;git restore names.txt
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;&lt;strong&gt;Deleted File (deleted):&lt;/strong&gt; A file tracked by Git that has been deleted.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;Changes not staged for commit:
    deleted:    names.txt
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;To restore the deleted file:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;git restore names.txt
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;h3&gt;
  
  
  ★ Removing from the Staging Area
&lt;/h3&gt;

&lt;p&gt;To remove a file that was accidentally added to the staging area (unstage it):&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;git restore &lt;span class="nt"&gt;--staged&lt;/span&gt; names.txt
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;💡 In older resources, you may see &lt;code&gt;git reset HEAD &amp;lt;file&amp;gt;&lt;/code&gt; for unstaging. In modern Git, &lt;code&gt;git restore --staged&lt;/code&gt; is recommended instead.&lt;/p&gt;

&lt;p&gt;If you want Git to &lt;strong&gt;completely stop tracking&lt;/strong&gt; a file (the file is not deleted from disk, but Git no longer tracks it):&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;git &lt;span class="nb"&gt;rm&lt;/span&gt; &lt;span class="nt"&gt;--cached&lt;/span&gt; names.txt
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;This command is especially useful for removing files from version control after they have been added to &lt;code&gt;.gitignore&lt;/code&gt;.&lt;/p&gt;

&lt;h3&gt;
  
  
  ★ More About the "git add" Command
&lt;/h3&gt;

&lt;p&gt;&lt;strong&gt;Partial staging (&lt;code&gt;-p&lt;/code&gt;):&lt;/strong&gt; Shows changes in the file hunk by hunk and asks which ones you want to add:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;git add &lt;span class="nt"&gt;-p&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;This command offers options for each change block:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;code&gt;y&lt;/code&gt; — Add this block&lt;/li&gt;
&lt;li&gt;
&lt;code&gt;n&lt;/code&gt; — Do not add this block&lt;/li&gt;
&lt;li&gt;
&lt;code&gt;s&lt;/code&gt; — Split the block into smaller pieces&lt;/li&gt;
&lt;li&gt;
&lt;code&gt;q&lt;/code&gt; — Quit&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;This allows you to add only part of the changes in a file to the staging area.&lt;/p&gt;

&lt;p&gt;📌 For all parameters of the &lt;code&gt;git add&lt;/code&gt; command: &lt;a href="https://git-scm.com/docs/git-add" rel="noopener noreferrer"&gt;git-scm.com/docs/git-add&lt;/a&gt;&lt;/p&gt;

&lt;h2&gt;
  
  
  Committing Changes (git commit) 📸
&lt;/h2&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.amazonaws.com%2Fuploads%2Farticles%2Ftd0nyhyrj96dn8e7xa0j.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.amazonaws.com%2Fuploads%2Farticles%2Ftd0nyhyrj96dn8e7xa0j.png" alt="Saving to Git" width="800" height="446"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;To create a commit from the staged changes:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;git commit
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Running this command without parameters opens the default text editor (usually Vim) and prompts you to enter a commit message. To exit Vim, type &lt;code&gt;:wq&lt;/code&gt; and press Enter.&lt;/p&gt;

&lt;h3&gt;
  
  
  ★ "git commit" Command Parameters
&lt;/h3&gt;

&lt;p&gt;&lt;strong&gt;&lt;code&gt;-m&lt;/code&gt; parameter&lt;/strong&gt; — Lets you write the commit message directly in the terminal:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;git commit &lt;span class="nt"&gt;-m&lt;/span&gt; &lt;span class="s2"&gt;"Names file created"&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;&lt;strong&gt;&lt;code&gt;-a&lt;/code&gt; parameter&lt;/strong&gt; — Commits only &lt;strong&gt;modified&lt;/strong&gt; tracked files directly, without using &lt;code&gt;git add&lt;/code&gt;. ⚠️ It does &lt;strong&gt;not&lt;/strong&gt; add new (untracked) files:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;git commit &lt;span class="nt"&gt;-am&lt;/span&gt; &lt;span class="s2"&gt;"Names edited"&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;&lt;strong&gt;&lt;code&gt;--amend&lt;/code&gt; parameter&lt;/strong&gt; — Edits the most recent commit message or updates the most recent commit with additional changes:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;git commit &lt;span class="nt"&gt;--amend&lt;/span&gt; &lt;span class="nt"&gt;-m&lt;/span&gt; &lt;span class="s2"&gt;"Corrected commit message"&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;⚠️ &lt;code&gt;--amend&lt;/code&gt; changes the commit hash. If you amend commits that have already been pushed, a force push is required. Use this carefully on shared branches.&lt;/p&gt;

&lt;p&gt;📌 For all parameters of the &lt;code&gt;git commit&lt;/code&gt; command: &lt;a href="https://git-scm.com/docs/git-commit" rel="noopener noreferrer"&gt;git-scm.com/docs/git-commit&lt;/a&gt;&lt;/p&gt;

&lt;h3&gt;
  
  
  ★ How to Write a Good Commit Message?
&lt;/h3&gt;

&lt;p&gt;💡 This is one of the most important sections of the article. One of the most common mistakes in Git is writing poor commit messages. A well-written commit message makes the project's history easier to read and makes collaboration much easier.&lt;/p&gt;

&lt;p&gt;What makes a good commit message?&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Short and descriptive (under 50 characters is ideal)&lt;/li&gt;
&lt;li&gt;Describes what changed&lt;/li&gt;
&lt;li&gt;Use imperative verbs such as: "fix", "add", "update"&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;Example:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;❌ Bad: &lt;code&gt;changes&lt;/code&gt;
&lt;/li&gt;
&lt;li&gt;✅ Good: &lt;code&gt;Fix validation error in user login form&lt;/code&gt;
&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;💡 In large projects, teams, or open source projects, linters are often used to standardize commit messages.&lt;/p&gt;

&lt;h3&gt;
  
  
  ★ Commit Message Standards (Conventional Commits)
&lt;/h3&gt;

&lt;p&gt;In larger projects, commit messages are often written according to a standard format. These standards:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Make commit history easier to read&lt;/li&gt;
&lt;li&gt;Enable automatic changelog generation&lt;/li&gt;
&lt;li&gt;Can integrate with CI/CD processes&lt;/li&gt;
&lt;li&gt;Are compatible with semantic versioning&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;The &lt;strong&gt;Conventional Commits&lt;/strong&gt; standard is widely used for this purpose.&lt;/p&gt;

&lt;h3&gt;
  
  
  ★ Commit Format
&lt;/h3&gt;



&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;feat(auth): add user login system
fix(player): fix audio dropout issue
docs(readme): update installation steps
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;ul&gt;
&lt;li&gt;
&lt;strong&gt;feat&lt;/strong&gt; — A new feature&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;fix&lt;/strong&gt; — A bug fix&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;docs&lt;/strong&gt; — Documentation changes&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;style&lt;/strong&gt; — Code format changes (lint, whitespace, etc.)&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;refactor&lt;/strong&gt; — Refactoring that does not change behavior&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;test&lt;/strong&gt; — Tests added or updated&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;chore&lt;/strong&gt; — Build, config, or utility tasks&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;ci&lt;/strong&gt; — CI/CD pipeline changes&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;perf&lt;/strong&gt; — Performance improvements&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;build&lt;/strong&gt; — Build system or dependency changes&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;To automatically check this standard:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;strong&gt;commitlint&lt;/strong&gt; → lints commit messages&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Commitizen&lt;/strong&gt; → provides interactive help when writing commits&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;💡 Every commit must be reachable from a branch, tag, or HEAD reference. Commits that are no longer referenced are eventually cleaned up by Git's &lt;strong&gt;garbage collection&lt;/strong&gt; mechanism after a certain amount of time (often around 90 days by default). Garbage collection is covered later in this article.&lt;/p&gt;

&lt;h2&gt;
  
  
  Viewing Commit History (git log) 📜
&lt;/h2&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.amazonaws.com%2Fuploads%2Farticles%2Fzxfzv661cgkmao9x62ud.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.amazonaws.com%2Fuploads%2Farticles%2Fzxfzv661cgkmao9x62ud.png" alt="Viewing Commit History" width="800" height="800"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;To view the commit history:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;git log
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Example output:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;commit a1b2c3d4e5f6 (HEAD -&amp;gt; main)
Author: Rabia Kaya &amp;lt;rabia@example.com&amp;gt;
Date:   Mon Jun 9 2025

    Names file created
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;h3&gt;
  
  
  ★ Frequently Used Parameters
&lt;/h3&gt;



&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;git log &lt;span class="nt"&gt;--oneline&lt;/span&gt;                        &lt;span class="c"&gt;# Each commit shown on a single line&lt;/span&gt;
git log &lt;span class="nt"&gt;--graph&lt;/span&gt;                          &lt;span class="c"&gt;# Branch structure drawn as ASCII art&lt;/span&gt;
git log &lt;span class="nt"&gt;--oneline&lt;/span&gt; &lt;span class="nt"&gt;--graph&lt;/span&gt; &lt;span class="nt"&gt;--decorate&lt;/span&gt; &lt;span class="nt"&gt;--all&lt;/span&gt;  &lt;span class="c"&gt;# Visual history with branch/tag pointers&lt;/span&gt;
git log &lt;span class="nt"&gt;-n&lt;/span&gt; 5                             &lt;span class="c"&gt;# Only the last 5 commits&lt;/span&gt;
git log &lt;span class="nt"&gt;--author&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="s2"&gt;"Rabia"&lt;/span&gt;                 &lt;span class="c"&gt;# Commits by a specific author&lt;/span&gt;
git log &lt;span class="nt"&gt;--&lt;/span&gt; names.txt                     &lt;span class="c"&gt;# History of a specific file&lt;/span&gt;
git log &lt;span class="nt"&gt;--follow&lt;/span&gt; &lt;span class="nt"&gt;--&lt;/span&gt; names.txt            &lt;span class="c"&gt;# Tracks history even if the file was renamed&lt;/span&gt;
git log &lt;span class="nt"&gt;--since&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="s2"&gt;"2025-01-01"&lt;/span&gt;             &lt;span class="c"&gt;# Commits after a specific date&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;The commit hashes shown in &lt;code&gt;git log&lt;/code&gt; output (for example, &lt;code&gt;a1b2c3d&lt;/code&gt;) can be used with commands such as &lt;code&gt;git checkout&lt;/code&gt;, &lt;code&gt;git reset&lt;/code&gt;, and &lt;code&gt;git revert&lt;/code&gt; to reference specific commits.&lt;/p&gt;

&lt;p&gt;📌 For all parameters of the &lt;code&gt;git log&lt;/code&gt; command: &lt;a href="https://git-scm.com/docs/git-log" rel="noopener noreferrer"&gt;git-scm.com/docs/git-log&lt;/a&gt;&lt;/p&gt;

&lt;h2&gt;
  
  
  Viewing Differences (git diff) 🔎
&lt;/h2&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.amazonaws.com%2Fuploads%2Farticles%2Fxf39gxv48vx1bo9ckfb6.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.amazonaws.com%2Fuploads%2Farticles%2Fxf39gxv48vx1bo9ckfb6.png" alt="Viewing Differences of Git" width="800" height="800"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;To inspect line-by-line changes:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;git diff
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;This command shows the differences between changes in the working directory and the staging area.&lt;/p&gt;

&lt;h3&gt;
  
  
  ★ Different Comparison Scenarios
&lt;/h3&gt;



&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;git diff                         &lt;span class="c"&gt;# Working directory vs staging area&lt;/span&gt;
git diff &lt;span class="nt"&gt;--staged&lt;/span&gt;                &lt;span class="c"&gt;# Staging area vs last commit&lt;/span&gt;
git diff &lt;span class="nt"&gt;--cached&lt;/span&gt;                &lt;span class="c"&gt;# Equivalent to --staged&lt;/span&gt;
git diff HEAD                    &lt;span class="c"&gt;# Working directory vs last commit&lt;/span&gt;
git diff &amp;lt;commit1&amp;gt; &amp;lt;commit2&amp;gt;     &lt;span class="c"&gt;# Differences between two commits&lt;/span&gt;
git diff main..new-feature       &lt;span class="c"&gt;# Differences between two branches&lt;/span&gt;
git diff &lt;span class="nt"&gt;--&lt;/span&gt; names.txt            &lt;span class="c"&gt;# Differences for a specific file only&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;&lt;strong&gt;Reading the output:&lt;/strong&gt;&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight diff"&gt;&lt;code&gt;&lt;span class="gd"&gt;- Tuvana       # Deleted line (red)
&lt;/span&gt;&lt;span class="gi"&gt;+ Beril        # Added line (green)
&lt;/span&gt;&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;📌 For all parameters of the &lt;code&gt;git diff&lt;/code&gt; command: &lt;a href="https://git-scm.com/docs/git-diff" rel="noopener noreferrer"&gt;git-scm.com/docs/git-diff&lt;/a&gt;&lt;/p&gt;

&lt;h2&gt;
  
  
  File Deletion and Moving (git rm &amp;amp; git mv) 🗑️
&lt;/h2&gt;

&lt;h3&gt;
  
  
  ★ git rm
&lt;/h3&gt;

&lt;p&gt;To delete a file tracked by Git from both your filesystem and Git’s index:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;git &lt;span class="nb"&gt;rm &lt;/span&gt;names.txt
git commit &lt;span class="nt"&gt;-m&lt;/span&gt; &lt;span class="s2"&gt;"names.txt deleted"&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;To remove a file from version control only, without deleting it from disk:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;git &lt;span class="nb"&gt;rm&lt;/span&gt; &lt;span class="nt"&gt;--cached&lt;/span&gt; names.txt
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;h3&gt;
  
  
  ★ git mv
&lt;/h3&gt;

&lt;p&gt;To move or rename a file:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;git &lt;span class="nb"&gt;mv &lt;/span&gt;old-name.txt new-name.txt
git commit &lt;span class="nt"&gt;-m&lt;/span&gt; &lt;span class="s2"&gt;"File renamed"&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;💡 Git actually detects file renames through content similarity. &lt;code&gt;git mv&lt;/code&gt; does the same thing as deleting the file and adding it again with a new name behind the scenes, but using a single command is more convenient.&lt;/p&gt;

&lt;h2&gt;
  
  
  Branching (git branch) 🌿
&lt;/h2&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.amazonaws.com%2Fuploads%2Farticles%2Fcl871b8iqkisp4lszwfa.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.amazonaws.com%2Fuploads%2Farticles%2Fcl871b8iqkisp4lszwfa.png" alt="Git Branching" width="800" height="446"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;Branches allow you to create independent workspaces within the same project. A branch is an independent line of development created from the current state of another branch. This lets you develop features or fix bugs without affecting the main codebase.&lt;/p&gt;

&lt;p&gt;Historically, Git initialized repositories with &lt;code&gt;master&lt;/code&gt; as the default branch name. Today, many teams and platforms use &lt;code&gt;main&lt;/code&gt; instead. In this article, the examples use &lt;code&gt;main&lt;/code&gt;.&lt;/p&gt;

&lt;h3&gt;
  
  
  ★ Listing Branches
&lt;/h3&gt;



&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;git branch              &lt;span class="c"&gt;# Lists local branches&lt;/span&gt;
git branch &lt;span class="nt"&gt;-a&lt;/span&gt;           &lt;span class="c"&gt;# Lists all, including remote-tracking branches&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;💡 References such as &lt;code&gt;remotes/origin/main&lt;/code&gt; in &lt;code&gt;git branch -a&lt;/code&gt; output are not the remote branch itself, but local tracking references updated after the last fetch or pull.&lt;/p&gt;

&lt;h3&gt;
  
  
  ★ Creating a Branch
&lt;/h3&gt;



&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;git branch new-names
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;After running this command, if you run &lt;code&gt;git branch&lt;/code&gt; again, you will see that the &lt;code&gt;new-names&lt;/code&gt; branch has been created. However, you are still on the &lt;code&gt;main&lt;/code&gt; branch; see the next section for switching branches.&lt;/p&gt;

&lt;h3&gt;
  
  
  ★ Deleting a Branch
&lt;/h3&gt;



&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;git branch &lt;span class="nt"&gt;-d&lt;/span&gt; new-names     &lt;span class="c"&gt;# Deletes a merged branch&lt;/span&gt;
git branch &lt;span class="nt"&gt;-D&lt;/span&gt; new-names     &lt;span class="c"&gt;# Force-deletes it (even if not merged)&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;h3&gt;
  
  
  ★ Renaming a Branch
&lt;/h3&gt;



&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;git branch &lt;span class="nt"&gt;-m&lt;/span&gt; old-name new-name
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;h2&gt;
  
  
  Switching Between Branches and Commits (git checkout / git switch) 🔄
&lt;/h2&gt;

&lt;p&gt;In Git version 2.23, the two different responsibilities of &lt;code&gt;git checkout&lt;/code&gt; (branch switching and file restoration) were separated. &lt;code&gt;git switch&lt;/code&gt; is recommended for switching branches, and &lt;code&gt;git restore&lt;/code&gt; is recommended for restoring files. However, &lt;code&gt;git checkout&lt;/code&gt; still works for both.&lt;/p&gt;

&lt;h3&gt;
  
  
  ★ Switching Between Branches
&lt;/h3&gt;



&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;git checkout new-names
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;or in Git 2.23+:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;git switch new-names
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;&lt;strong&gt;Shortcut — Create and Switch:&lt;/strong&gt;&lt;/p&gt;

&lt;p&gt;To create a new branch and switch to it without running &lt;code&gt;git branch&lt;/code&gt; separately:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;git checkout &lt;span class="nt"&gt;-b&lt;/span&gt; new-names
&lt;span class="c"&gt;# or&lt;/span&gt;
git switch &lt;span class="nt"&gt;-c&lt;/span&gt; new-names
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;h3&gt;
  
  
  ★ Switching to a Commit
&lt;/h3&gt;

&lt;p&gt;You can return to the state of any commit using its hash from the &lt;code&gt;git log&lt;/code&gt; output:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;git checkout a1b2c3d
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;⚠️ This places you in a &lt;strong&gt;detached HEAD&lt;/strong&gt; state. In this state, commits you make are not attached to any branch, and they can become difficult to recover later if you switch away without creating a branch. If you want to preserve your changes, create a new branch:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;git checkout &lt;span class="nt"&gt;-b&lt;/span&gt; rescue-branch
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;💡 The HEAD and detached HEAD concepts are explained in more detail later in this article.&lt;/p&gt;

&lt;h3&gt;
  
  
  ★ Getting a File from a Specific Commit or Branch
&lt;/h3&gt;

&lt;p&gt;To bring a file's state from a specific commit or branch into your working directory:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;&lt;span class="c"&gt;# Get the file state from a specific commit&lt;/span&gt;
git checkout a1b2c3d &lt;span class="nt"&gt;--&lt;/span&gt; names.txt

&lt;span class="c"&gt;# Get the file state from another branch&lt;/span&gt;
git checkout main &lt;span class="nt"&gt;--&lt;/span&gt; names.txt
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;This command copies the file into your working directory and staging area. You do not leave your current branch.&lt;/p&gt;

&lt;p&gt;💡 In older resources, you may see &lt;code&gt;git checkout -- &amp;lt;file&amp;gt;&lt;/code&gt; for file restoration. In modern usage, &lt;code&gt;git restore&lt;/code&gt; is recommended instead.&lt;/p&gt;

&lt;h2&gt;
  
  
  Merging Branches (git merge) 🤝
&lt;/h2&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.amazonaws.com%2Fuploads%2Farticles%2Fvkt13vfmxwfjw36aqpkg.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.amazonaws.com%2Fuploads%2Farticles%2Fvkt13vfmxwfjw36aqpkg.png" alt="Git Merging Branches" width="800" height="339"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;The &lt;code&gt;git merge&lt;/code&gt; command is used to merge changes from one branch into another.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Example scenario:&lt;/strong&gt;&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;&lt;span class="c"&gt;# Create a new branch and switch to it&lt;/span&gt;
git checkout &lt;span class="nt"&gt;-b&lt;/span&gt; new-names

&lt;span class="c"&gt;# Add "Rabia" to names.txt and commit the change&lt;/span&gt;
git add &lt;span class="nb"&gt;.&lt;/span&gt;
git commit &lt;span class="nt"&gt;-m&lt;/span&gt; &lt;span class="s2"&gt;"Rabia added"&lt;/span&gt;

&lt;span class="c"&gt;# Switch back to main branch&lt;/span&gt;
git checkout main

&lt;span class="c"&gt;# Merge new-names branch into main&lt;/span&gt;
git merge new-names
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;h3&gt;
  
  
  ★ Merge Types
&lt;/h3&gt;

&lt;p&gt;&lt;strong&gt;Fast-Forward Merge:&lt;/strong&gt; If there are no new commits on the target branch (&lt;code&gt;main&lt;/code&gt;), Git simply moves the branch pointer forward. No new merge commit is created:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;main:    A → B → C
                  ↑ (fast-forward)
feature:          C → D → E
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;To prevent a fast-forward merge and always create a merge commit:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;git merge &lt;span class="nt"&gt;--no-ff&lt;/span&gt; new-names
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;&lt;strong&gt;Three-Way Merge:&lt;/strong&gt; When both branches have new commits, Git finds a common ancestor, performs a three-way comparison, and creates a new &lt;strong&gt;merge commit&lt;/strong&gt;.&lt;/p&gt;

&lt;p&gt;💡 To keep your feature branch up to date, you can regularly integrate changes from the main branch. This can be done with either merge or rebase:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;git checkout new-names
git merge main
&lt;span class="c"&gt;# or&lt;/span&gt;
git rebase main
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;h2&gt;
  
  
  Conflicts (Git Conflicts) ⚡
&lt;/h2&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.amazonaws.com%2Fuploads%2Farticles%2Ffgvpyem8ikq5nz1emal1.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.amazonaws.com%2Fuploads%2Farticles%2Ffgvpyem8ikq5nz1emal1.png" alt="Conflicts of Git" width="800" height="339"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;When the same lines of the same file are modified differently in two branches, a &lt;strong&gt;conflict&lt;/strong&gt; occurs.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Example scenario:&lt;/strong&gt;&lt;/p&gt;

&lt;p&gt;Your &lt;code&gt;names.txt&lt;/code&gt; file on the &lt;code&gt;main&lt;/code&gt; branch looks like this:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;Eda
Beyza
Tuvana
Melis
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;&lt;strong&gt;1.&lt;/strong&gt; Create a new branch and change &lt;code&gt;Tuvana&lt;/code&gt; on line 3 to &lt;code&gt;Beril&lt;/code&gt;:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;git checkout &lt;span class="nt"&gt;-b&lt;/span&gt; conflict-example
&lt;span class="c"&gt;# names.txt → Change the line "Tuvana" to "Beril"&lt;/span&gt;
git commit &lt;span class="nt"&gt;-am&lt;/span&gt; &lt;span class="s2"&gt;"Tuvana replaced with Beril"&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;&lt;strong&gt;2.&lt;/strong&gt; Switch back to &lt;code&gt;main&lt;/code&gt; and change the same line to a different name:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;git checkout main
&lt;span class="c"&gt;# names.txt → Change the line "Tuvana" to "Rabia"&lt;/span&gt;
git commit &lt;span class="nt"&gt;-am&lt;/span&gt; &lt;span class="s2"&gt;"Tuvana replaced with Rabia"&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;&lt;strong&gt;3.&lt;/strong&gt; Try to merge:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;git checkout conflict-example
git merge main
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Git shows the following conflict message:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;CONFLICT (content): Merge conflict in names.txt
Automatic merge failed; fix conflicts and then commit the result.
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;When you open the file, Git marks the conflicting sections:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;Eda
Beyza
&amp;lt;&amp;lt;&amp;lt;&amp;lt;&amp;lt;&amp;lt;&amp;lt; HEAD
Beril
=======
Rabia
&amp;gt;&amp;gt;&amp;gt;&amp;gt;&amp;gt;&amp;gt;&amp;gt; main
Melis
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;ul&gt;
&lt;li&gt;Between &lt;code&gt;&amp;lt;&amp;lt;&amp;lt;&amp;lt;&amp;lt;&amp;lt;&amp;lt; HEAD&lt;/code&gt; and &lt;code&gt;=======&lt;/code&gt;: Changes from &lt;strong&gt;your branch&lt;/strong&gt;
&lt;/li&gt;
&lt;li&gt;Between &lt;code&gt;=======&lt;/code&gt; and &lt;code&gt;&amp;gt;&amp;gt;&amp;gt;&amp;gt;&amp;gt;&amp;gt;&amp;gt; main&lt;/code&gt;: Changes from &lt;strong&gt;the branch being merged&lt;/strong&gt;
&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;&lt;strong&gt;To resolve the conflict:&lt;/strong&gt;&lt;/p&gt;

&lt;ol&gt;
&lt;li&gt;Edit the file and keep the content you want&lt;/li&gt;
&lt;li&gt;Remove the &lt;code&gt;&amp;lt;&amp;lt;&amp;lt;&amp;lt;&amp;lt;&amp;lt;&amp;lt;&lt;/code&gt;, &lt;code&gt;=======&lt;/code&gt;, &lt;code&gt;&amp;gt;&amp;gt;&amp;gt;&amp;gt;&amp;gt;&amp;gt;&amp;gt;&lt;/code&gt; markers&lt;/li&gt;
&lt;li&gt;Save and commit:
&lt;/li&gt;
&lt;/ol&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;git add names.txt
git commit &lt;span class="nt"&gt;-m&lt;/span&gt; &lt;span class="s2"&gt;"Conflict resolved, updated as Beril"&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;h3&gt;
  
  
  ★ Quick Fix: Ours or Theirs
&lt;/h3&gt;

&lt;p&gt;If you want to directly choose one side in a conflict:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;&lt;span class="c"&gt;# Accept your branch's changes&lt;/span&gt;
git checkout &lt;span class="nt"&gt;--ours&lt;/span&gt; names.txt

&lt;span class="c"&gt;# Accept the incoming changes&lt;/span&gt;
git checkout &lt;span class="nt"&gt;--theirs&lt;/span&gt; names.txt

git add names.txt
git commit &lt;span class="nt"&gt;-m&lt;/span&gt; &lt;span class="s2"&gt;"Conflict resolved"&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;h3&gt;
  
  
  ★ Aborting the Merge (--abort)
&lt;/h3&gt;

&lt;p&gt;To completely cancel the merge before resolving any conflicts:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;git merge &lt;span class="nt"&gt;--abort&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;This command cancels the merge and restores your files to their pre-merge state.&lt;/p&gt;

&lt;h3&gt;
  
  
  ★ Continuing the Merge (--continue)
&lt;/h3&gt;

&lt;p&gt;After resolving the conflicts in the file and adding them to the staging area with &lt;code&gt;git add&lt;/code&gt;:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;git merge &lt;span class="nt"&gt;--continue&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;This is similar to running &lt;code&gt;git commit&lt;/code&gt;, but it explicitly resumes the in-progress merge.&lt;/p&gt;

&lt;p&gt;💡 Editors like VS Code automatically detect conflict markers and simplify resolution with buttons like "Accept Current", "Accept Incoming", and "Accept Both". Alternatively, you can use external tools configured with the &lt;code&gt;git mergetool&lt;/code&gt; command. Many IDEs (WebStorm, PhpStorm, PyCharm, etc.) also provide their own merge editors to make conflict resolution easier.&lt;/p&gt;

&lt;h2&gt;
  
  
  Rebasing Commits onto Another Branch (git rebase) 🔀
&lt;/h2&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.amazonaws.com%2Fuploads%2Farticles%2Fqrynym7pz02dxgiztnr9.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.amazonaws.com%2Fuploads%2Farticles%2Fqrynym7pz02dxgiztnr9.png" alt="Rebasing Commits onto Another Branch" width="800" height="446"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;Rebase creates a linear history by &lt;strong&gt;re-applying&lt;/strong&gt; a branch's commits onto the tip of another branch.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;git checkout new-feature
git rebase main
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;This command does the following:&lt;/p&gt;

&lt;ol&gt;
&lt;li&gt;Temporarily rewinds the &lt;code&gt;new-feature&lt;/code&gt; branch&lt;/li&gt;
&lt;li&gt;Takes the latest commits from the &lt;code&gt;main&lt;/code&gt; branch&lt;/li&gt;
&lt;li&gt;Re-applies &lt;code&gt;new-feature&lt;/code&gt;'s commits one by one on top of &lt;code&gt;main&lt;/code&gt;'s latest commit&lt;/li&gt;
&lt;/ol&gt;

&lt;h3&gt;
  
  
  ★ Interactive Rebase
&lt;/h3&gt;

&lt;p&gt;To edit, combine, reorder, or delete recent commits:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;git rebase &lt;span class="nt"&gt;-i&lt;/span&gt; HEAD~3
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;In the editor that opens, you can change the command at the beginning of each commit:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;pick a1b2c3d Names added
pick d4e5f6g New names edited
pick h7i8j9k Beyza added
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Available commands:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;strong&gt;pick&lt;/strong&gt; — Keep the commit as is&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;reword&lt;/strong&gt; — Change the commit message&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;squash&lt;/strong&gt; — Combine with the previous commit (merges messages)&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;fixup&lt;/strong&gt; — Combine with the previous commit (discards this commit's message)&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;drop&lt;/strong&gt; — Completely remove the commit&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;edit&lt;/strong&gt; — Stop to edit the commit&lt;/li&gt;
&lt;/ul&gt;

&lt;h3&gt;
  
  
  ★ Rebase --onto
&lt;/h3&gt;

&lt;p&gt;To detach a branch from its source branch and move it onto another branch:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;git rebase &lt;span class="nt"&gt;--onto&lt;/span&gt; main feature bugfix
&lt;span class="c"&gt;# Detach bugfix branch from feature and place it onto main&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;h3&gt;
  
  
  ★ Rebase vs Merge
&lt;/h3&gt;

&lt;p&gt;&lt;strong&gt;Merge&lt;/strong&gt;&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Merges branches and creates a merge commit&lt;/li&gt;
&lt;li&gt;Does not rewrite commit history (safe)&lt;/li&gt;
&lt;li&gt;If there is a conflict, it is resolved all at once&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;&lt;strong&gt;Rebase&lt;/strong&gt;&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Re-applies commits onto another branch's tip&lt;/li&gt;
&lt;li&gt;Creates a cleaner history&lt;/li&gt;
&lt;li&gt;Rewrites commit hashes&lt;/li&gt;
&lt;li&gt;If conflicts occur, they are resolved for each commit separately&lt;/li&gt;
&lt;li&gt;Typically used on personal branches&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;⚠️ This can cause problems on shared branches. Avoid rebasing branches that other people are already using.&lt;/p&gt;

&lt;p&gt;If a conflict occurs during rebase:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;&lt;span class="c"&gt;# Resolve the conflict in the file, then:&lt;/span&gt;
git add &lt;span class="nb"&gt;.&lt;/span&gt;
git rebase &lt;span class="nt"&gt;--continue&lt;/span&gt;

&lt;span class="c"&gt;# or abort the rebase entirely:&lt;/span&gt;
git rebase &lt;span class="nt"&gt;--abort&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;h2&gt;
  
  
  The HEAD Concept 🎯
&lt;/h2&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.amazonaws.com%2Fuploads%2Farticles%2F52044v48tglz3hfsiclr.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.amazonaws.com%2Fuploads%2Farticles%2F52044v48tglz3hfsiclr.png" alt="Git HEAD" width="800" height="446"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;HEAD&lt;/strong&gt; is the answer to the question "where are you right now?" in Git. It points to the commit you are currently working on.&lt;/p&gt;

&lt;p&gt;Normally, HEAD points to a branch and corresponds to that branch's latest commit:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;&lt;span class="nb"&gt;cat&lt;/span&gt; .git/HEAD
&lt;span class="c"&gt;# Output: ref: refs/heads/main&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;This means "HEAD → main → latest commit." When you make a new commit, HEAD moves forward to the new commit automatically.&lt;/p&gt;

&lt;h3&gt;
  
  
  ★ Detached HEAD
&lt;/h3&gt;

&lt;p&gt;When you switch directly to a commit with &lt;code&gt;git checkout &amp;lt;commit-hash&amp;gt;&lt;/code&gt;, HEAD no longer points to a branch, but directly to that commit:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;git checkout a1b2c3d
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;In this state, since any commits you make are not attached to a branch, they can become difficult to recover later when you switch to another branch. If you want to preserve your changes:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;git checkout &lt;span class="nt"&gt;-b&lt;/span&gt; new-branch-name
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;💡 Commits made in detached HEAD do not disappear immediately. You can find their hashes with &lt;code&gt;git reflog&lt;/code&gt; and recover them. However, after the reflog retention period expires (90 days by default), they may be cleaned up by garbage collection.&lt;/p&gt;

&lt;h2&gt;
  
  
  Tagging (git tag) 🏷️
&lt;/h2&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.amazonaws.com%2Fuploads%2Farticles%2Fbmz1veb133ll5gqkh6oh.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.amazonaws.com%2Fuploads%2Farticles%2Fbmz1veb133ll5gqkh6oh.png" alt="git tag" width="800" height="339"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;Tags are used to add permanent labels (bookmarks) to specific commits. They are typically used to mark version numbers. Unlike branches, tags are fixed and do not move.&lt;/p&gt;

&lt;h3&gt;
  
  
  ★ Lightweight Tag
&lt;/h3&gt;

&lt;p&gt;A simple pointer that stores no additional information:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;git tag v1.0
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;h3&gt;
  
  
  ★ Annotated Tag
&lt;/h3&gt;

&lt;p&gt;A tag that includes author, date, and message information. Recommended for version tags:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;git tag &lt;span class="nt"&gt;-a&lt;/span&gt; v1.0 &lt;span class="nt"&gt;-m&lt;/span&gt; &lt;span class="s2"&gt;"First stable release"&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;h3&gt;
  
  
  ★ Adding a Tag to a Specific Commit
&lt;/h3&gt;



&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;git tag &lt;span class="nt"&gt;-a&lt;/span&gt; v0.9 a1b2c3d &lt;span class="nt"&gt;-m&lt;/span&gt; &lt;span class="s2"&gt;"Beta release"&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;h3&gt;
  
  
  ★ Tag Operations
&lt;/h3&gt;



&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;git tag                    &lt;span class="c"&gt;# List all tags&lt;/span&gt;
git show v1.0              &lt;span class="c"&gt;# Show tag details&lt;/span&gt;
git tag &lt;span class="nt"&gt;-d&lt;/span&gt; v1.0            &lt;span class="c"&gt;# Delete local tag&lt;/span&gt;
git push origin v1.0       &lt;span class="c"&gt;# Push tag to remote repository&lt;/span&gt;
git push origin &lt;span class="nt"&gt;--tags&lt;/span&gt;     &lt;span class="c"&gt;# Push all tags&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;h2&gt;
  
  
  Undoing Changes ↩️
&lt;/h2&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.amazonaws.com%2Fuploads%2Farticles%2F6l4igk7xexvxrgicvxe5.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.amazonaws.com%2Fuploads%2Farticles%2F6l4igk7xexvxrgicvxe5.png" alt="Undoing Changes of Git" width="800" height="446"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;Use &lt;code&gt;git restore&lt;/code&gt; to discard changes in the working directory or unstage files from the index:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;&lt;span class="c"&gt;# Restore the file to its last committed state (working directory changes are lost)&lt;/span&gt;
git restore names.txt

&lt;span class="c"&gt;# Remove the file from the staging area, but keep the file unchanged&lt;/span&gt;
git restore &lt;span class="nt"&gt;--staged&lt;/span&gt; names.txt
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;h3&gt;
  
  
  ★ git reset
&lt;/h3&gt;

&lt;p&gt;Used to undo commit history. &lt;code&gt;git reset&lt;/code&gt; moves the current branch reference backward to an earlier commit; depending on the mode used, the staging area and working directory are adjusted accordingly.&lt;/p&gt;

&lt;p&gt;It has three modes:&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;&lt;code&gt;--soft&lt;/code&gt;:&lt;/strong&gt; The commit is undone, but the changes remain in the &lt;strong&gt;staging area&lt;/strong&gt;. Useful when you want to correct the commit message or adjust the contents of the commit:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;git reset &lt;span class="nt"&gt;--soft&lt;/span&gt; HEAD~1
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;&lt;strong&gt;&lt;code&gt;--mixed&lt;/code&gt; (default):&lt;/strong&gt; The commit is undone, the changes remain in the &lt;strong&gt;working directory&lt;/strong&gt;, but they are removed from the staging area:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;git reset HEAD~1
&lt;span class="c"&gt;# or&lt;/span&gt;
git reset &lt;span class="nt"&gt;--mixed&lt;/span&gt; HEAD~1
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;&lt;strong&gt;&lt;code&gt;--hard&lt;/code&gt;:&lt;/strong&gt; The commit &lt;strong&gt;and&lt;/strong&gt; all changes are &lt;strong&gt;completely deleted&lt;/strong&gt;:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;git reset &lt;span class="nt"&gt;--hard&lt;/span&gt; HEAD~1
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;⚠️ The &lt;code&gt;--hard&lt;/code&gt; parameter permanently deletes changes. Be careful.&lt;/p&gt;

&lt;p&gt;Commits removed by &lt;code&gt;git reset --hard&lt;/code&gt; can often still be recovered with &lt;code&gt;git reflog&lt;/code&gt;, as long as they have not been pruned by garbage collection. By default, unreachable commits are typically recoverable for some time (often around 90 days, depending on reflog and GC settings). Good commit messages also make lost commits much easier to identify in the reflog. If your commit messages are all the same, finding the right one becomes much harder 🥲&lt;/p&gt;

&lt;p&gt;&lt;code&gt;HEAD~1&lt;/code&gt; means the previous commit. &lt;code&gt;HEAD~3&lt;/code&gt; means three commits back. You can also use a specific commit hash:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;git reset &lt;span class="nt"&gt;--soft&lt;/span&gt; a1b2c3d
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;h3&gt;
  
  
  ★ git revert
&lt;/h3&gt;

&lt;p&gt;Creates a &lt;strong&gt;new commit&lt;/strong&gt; that undoes the changes introduced by a specific commit. It does not erase history, so it can be used safely on shared branches:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;git revert a1b2c3d
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;&lt;strong&gt;Reverting a merge commit:&lt;/strong&gt;&lt;/p&gt;

&lt;p&gt;When reverting merge commits, you need to specify which parent to use as the base with the &lt;code&gt;-m&lt;/code&gt; parameter:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;git revert &lt;span class="nt"&gt;-m&lt;/span&gt; 1 &amp;lt;merge-commit-hash&amp;gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;h3&gt;
  
  
  ★ Which one should you use?
&lt;/h3&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;strong&gt;File changes you have not committed yet&lt;/strong&gt; → &lt;code&gt;git restore&lt;/code&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Commits you have not pushed yet&lt;/strong&gt; → &lt;code&gt;git reset&lt;/code&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Safely undo pushed commits&lt;/strong&gt; → &lt;code&gt;git revert&lt;/code&gt;
&lt;/li&gt;
&lt;/ul&gt;

&lt;h2&gt;
  
  
  Reference History (git reflog) 🕵️
&lt;/h2&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.amazonaws.com%2Fuploads%2Farticles%2Fmkvyg3kg98af2ah8xq9b.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.amazonaws.com%2Fuploads%2Farticles%2Fmkvyg3kg98af2ah8xq9b.png" alt="Reference History of Git" width="800" height="436"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;&lt;code&gt;git reflog&lt;/code&gt; is a safety net that records updates to HEAD and other references locally. Even after running a dangerous command like &lt;code&gt;git reset --hard&lt;/code&gt;, you can often find lost commits here:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;git reflog
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Example output:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;a1b2c3d HEAD@{0}: reset: moving to HEAD~1
f4e5d6c HEAD@{1}: commit: Beril added
b7a8c9d HEAD@{2}: commit: Names file created
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;You can find the hash of the lost commit and go back to it:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;git reset &lt;span class="nt"&gt;--hard&lt;/span&gt; f4e5d6c
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;💡 Reflog entries are kept for &lt;strong&gt;90 days&lt;/strong&gt; by default.&lt;/p&gt;

&lt;h2&gt;
  
  
  Stashing Changes (git stash) 📦
&lt;/h2&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.amazonaws.com%2Fuploads%2Farticles%2F22te1ytf5tnbwj96f1qp.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.amazonaws.com%2Fuploads%2Farticles%2F22te1ytf5tnbwj96f1qp.png" alt="Shelving Changes of Git" width="800" height="339"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;Used to temporarily save changes you are working on without committing them. This is very useful when an urgent task comes up and you need to switch branches.&lt;/p&gt;

&lt;h3&gt;
  
  
  ★ Basic Commands
&lt;/h3&gt;



&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;git stash                              &lt;span class="c"&gt;# Stash changes&lt;/span&gt;
git stash push &lt;span class="nt"&gt;-m&lt;/span&gt; &lt;span class="s2"&gt;"Description"&lt;/span&gt;        &lt;span class="c"&gt;# Stash with a message&lt;/span&gt;
git stash &lt;span class="nt"&gt;-u&lt;/span&gt;                           &lt;span class="c"&gt;# Include untracked files&lt;/span&gt;
git stash &lt;span class="nt"&gt;--all&lt;/span&gt;                        &lt;span class="c"&gt;# Stash everything, including ignored files&lt;/span&gt;
git stash list                         &lt;span class="c"&gt;# List stashes&lt;/span&gt;
git stash show                         &lt;span class="c"&gt;# Show a summary of the latest stash&lt;/span&gt;
git stash show &lt;span class="nt"&gt;-p&lt;/span&gt;                      &lt;span class="c"&gt;# Show the detailed diff of the latest stash&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;💡 In older resources, you may see &lt;code&gt;git stash save "Description"&lt;/code&gt;. In modern Git, &lt;code&gt;git stash push -m "Description"&lt;/code&gt; is recommended instead.&lt;/p&gt;

&lt;p&gt;⚠️ The default &lt;code&gt;git stash&lt;/code&gt; command does &lt;strong&gt;not&lt;/strong&gt; include untracked files. To save those as well, use the &lt;code&gt;-u&lt;/code&gt; parameter.&lt;/p&gt;

&lt;h3&gt;
  
  
  ★ Restoring
&lt;/h3&gt;



&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;git stash pop                    &lt;span class="c"&gt;# Apply the latest stash and remove it from the stash list&lt;/span&gt;
git stash apply                  &lt;span class="c"&gt;# Apply the latest stash and keep it in the stash list&lt;/span&gt;
git stash apply stash@&lt;span class="o"&gt;{&lt;/span&gt;2&lt;span class="o"&gt;}&lt;/span&gt;        &lt;span class="c"&gt;# Apply a specific stash&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;h3&gt;
  
  
  ★ Cleanup
&lt;/h3&gt;



&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;git stash drop                   &lt;span class="c"&gt;# Drop the latest stash&lt;/span&gt;
git stash drop stash@&lt;span class="o"&gt;{&lt;/span&gt;1&lt;span class="o"&gt;}&lt;/span&gt;         &lt;span class="c"&gt;# Drop a specific stash&lt;/span&gt;
git stash clear                  &lt;span class="c"&gt;# Clear all stashes&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;h3&gt;
  
  
  ★ Example Scenario
&lt;/h3&gt;

&lt;p&gt;You are adding new names to &lt;code&gt;names.txt&lt;/code&gt;. Suddenly, an urgent fix is needed:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;&lt;span class="c"&gt;# Stash the work in progress&lt;/span&gt;
git stash push &lt;span class="nt"&gt;-m&lt;/span&gt; &lt;span class="s2"&gt;"I was updating Tuvana's information"&lt;/span&gt;

&lt;span class="c"&gt;# Switch to main and make the fix&lt;/span&gt;
git checkout main
git commit &lt;span class="nt"&gt;-am&lt;/span&gt; &lt;span class="s2"&gt;"Urgent fix applied"&lt;/span&gt;

&lt;span class="c"&gt;# Switch back to your feature branch and pick up where you left off&lt;/span&gt;
git checkout new-feature
git stash pop
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;h2&gt;
  
  
  Ignoring Files (.gitignore) 🙈
&lt;/h2&gt;

&lt;p&gt;Create a &lt;code&gt;.gitignore&lt;/code&gt; file in the project root directory to prevent Git from tracking certain files and folders:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;# Dependency folders
node_modules/
vendor/

# Build outputs
dist/
build/
*.class

# Environment variables (passwords, API keys, etc.)
.env
.env.local

# IDE files
.idea/
.vscode/
*.swp

# Operating system files
.DS_Store
Thumbs.db

# Log files
*.log

# Compiled files
*.o
*.exe
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;h3&gt;
  
  
  ★ Important Notes
&lt;/h3&gt;

&lt;ul&gt;
&lt;li&gt;Files that were already being tracked by Git &lt;strong&gt;before&lt;/strong&gt; the &lt;code&gt;.gitignore&lt;/code&gt; file was created will not automatically stop being tracked when added to &lt;code&gt;.gitignore&lt;/code&gt;. To remove these files from tracking:
&lt;/li&gt;
&lt;/ul&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;git &lt;span class="nb"&gt;rm&lt;/span&gt; &lt;span class="nt"&gt;--cached&lt;/span&gt; filename.txt
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;ul&gt;
&lt;li&gt;Empty folders are not tracked by Git. If you want to keep an otherwise empty directory in the repository, you can place an empty file named &lt;code&gt;.gitkeep&lt;/code&gt; inside it. &lt;code&gt;.gitkeep&lt;/code&gt; is not a Git-specific feature; it is a community convention. The file name can be anything, but &lt;code&gt;.gitkeep&lt;/code&gt; is commonly used.&lt;/li&gt;
&lt;/ul&gt;

&lt;h3&gt;
  
  
  ★ Global .gitignore
&lt;/h3&gt;

&lt;p&gt;You can define a global &lt;code&gt;.gitignore&lt;/code&gt; file that applies to all your projects. This is useful for system-specific files like &lt;code&gt;.DS_Store&lt;/code&gt;, &lt;code&gt;Thumbs.db&lt;/code&gt;, and temporary editor files:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;git config &lt;span class="nt"&gt;--global&lt;/span&gt; core.excludesfile ~/.gitignore_global
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Then add your global rules to the &lt;code&gt;~/.gitignore_global&lt;/code&gt; file.&lt;/p&gt;

&lt;p&gt;📌 Ready-made &lt;code&gt;.gitignore&lt;/code&gt; templates for different project types: &lt;a href="https://github.com/github/gitignore" rel="noopener noreferrer"&gt;github.com/github/gitignore&lt;/a&gt;&lt;/p&gt;

&lt;h2&gt;
  
  
  Remote Repository (Remote) 🌐
&lt;/h2&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.amazonaws.com%2Fuploads%2Farticles%2F1om1ddzh67vc08b8kb51.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.amazonaws.com%2Fuploads%2Farticles%2F1om1ddzh67vc08b8kb51.png" alt="Remote Repository of Git" width="800" height="446"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;So far, all operations have been local. To host the project on platforms such as GitHub, GitLab, or Bitbucket and share it with others, you use a &lt;strong&gt;remote repository&lt;/strong&gt;.&lt;/p&gt;

&lt;h3&gt;
  
  
  ★ HTTPS vs SSH
&lt;/h3&gt;

&lt;p&gt;There are two common ways to connect to a remote repository:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;&lt;span class="c"&gt;# HTTPS — Authentication with username/password or token&lt;/span&gt;
git remote add origin https://github.com/user/project.git

&lt;span class="c"&gt;# SSH — Authentication with SSH key (more practical)&lt;/span&gt;
git remote add origin git@github.com:user/project.git
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;💡 To use SSH, you first need to create an SSH key and add it to your platform (GitHub, GitLab, etc.). For detailed steps: &lt;a href="https://docs.github.com/en/authentication/connecting-to-github-with-ssh" rel="noopener noreferrer"&gt;docs.github.com/en/authentication/connecting-to-github-with-ssh&lt;/a&gt;&lt;/p&gt;

&lt;h3&gt;
  
  
  ★ Adding a Remote Repository
&lt;/h3&gt;



&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;git remote add origin https://github.com/user/project.git
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Here, &lt;code&gt;origin&lt;/code&gt; is the local alias for the remote repository. By convention, &lt;code&gt;origin&lt;/code&gt; is commonly used, but you can choose any name you like.&lt;/p&gt;

&lt;h3&gt;
  
  
  ★ Remote-Tracking Branch Concept
&lt;/h3&gt;

&lt;p&gt;References like &lt;code&gt;origin/main&lt;/code&gt; are local references that reflect the last fetched state of remote branches. This is not the live state of the remote server itself; it is a local reference updated after the last fetch or pull. This lets you inspect the last known state of the remote branch even while offline.&lt;/p&gt;

&lt;h3&gt;
  
  
  ★ Listing Remote Repositories
&lt;/h3&gt;



&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;git remote &lt;span class="nt"&gt;-v&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Example output:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;origin  https://github.com/user/project.git (fetch)
origin  https://github.com/user/project.git (push)
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;h3&gt;
  
  
  ★ Changing a Remote Repository URL
&lt;/h3&gt;



&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;git remote set-url origin https://github.com/user/new-project.git
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;h3&gt;
  
  
  ★ Removing a Remote Repository
&lt;/h3&gt;



&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;git remote remove origin
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;h2&gt;
  
  
  Cloning (git clone) 📥
&lt;/h2&gt;

&lt;p&gt;To copy a remote repository to your local machine:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;git clone https://github.com/user/project.git
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;This command:&lt;/p&gt;

&lt;ol&gt;
&lt;li&gt;Creates a folder with the project name&lt;/li&gt;
&lt;li&gt;Creates the &lt;code&gt;.git&lt;/code&gt; folder&lt;/li&gt;
&lt;li&gt;Downloads the repository history and working tree&lt;/li&gt;
&lt;li&gt;Automatically sets up the &lt;code&gt;origin&lt;/code&gt; remote&lt;/li&gt;
&lt;/ol&gt;

&lt;h3&gt;
  
  
  ★ Additional Parameters
&lt;/h3&gt;



&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;&lt;span class="c"&gt;# Clone a specific branch&lt;/span&gt;
git clone &lt;span class="nt"&gt;-b&lt;/span&gt; branch-name https://github.com/user/project.git

&lt;span class="c"&gt;# Clone with a different folder name&lt;/span&gt;
git clone https://github.com/user/project.git my-project

&lt;span class="c"&gt;# Clone only the last commit (for speed in large projects)&lt;/span&gt;
git clone &lt;span class="nt"&gt;--depth&lt;/span&gt; 1 https://github.com/user/project.git
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;h2&gt;
  
  
  Pulling Changes (git fetch &amp;amp; git pull) ⬇️
&lt;/h2&gt;

&lt;h3&gt;
  
  
  ★ git fetch
&lt;/h3&gt;

&lt;p&gt;Downloads changes from the remote repository &lt;strong&gt;but&lt;/strong&gt; does not merge them into your local branch. This is useful when you want to review changes first:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;git fetch origin
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;To review changes in the remote branch after fetching:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;git diff main origin/main
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;If the changes look correct, merge them:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;git merge origin/main
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;h3&gt;
  
  
  ★ git pull
&lt;/h3&gt;

&lt;p&gt;Performs &lt;code&gt;fetch&lt;/code&gt; + &lt;code&gt;merge&lt;/code&gt; with a single command. It downloads changes from the remote repository and merges them into your local branch:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;git pull origin main
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;For a cleaner history, pull with rebase:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;git pull &lt;span class="nt"&gt;--rebase&lt;/span&gt; origin main
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;💡 To make &lt;code&gt;git pull --rebase&lt;/code&gt; the default behavior:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;git config &lt;span class="nt"&gt;--global&lt;/span&gt; pull.rebase &lt;span class="nb"&gt;true&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;h3&gt;
  
  
  ★ Pull vs Fetch
&lt;/h3&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;strong&gt;git fetch:&lt;/strong&gt; Downloads changes but does not merge them. Safer because it gives you a chance to review changes first. Use it when you want to inspect changes before integrating them.&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;git pull:&lt;/strong&gt; Downloads changes and automatically merges them. Conflicts may occur. Use it when you want to update quickly.&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;💡 &lt;code&gt;git pull&lt;/code&gt; = &lt;code&gt;git fetch&lt;/code&gt; + &lt;code&gt;git merge&lt;/code&gt;&lt;/p&gt;

&lt;h2&gt;
  
  
  Pushing Changes (git push) ⬆️
&lt;/h2&gt;

&lt;p&gt;To send your local commits to the remote repository:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;git push origin main
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;h3&gt;
  
  
  ★ Setting Upstream for First Push
&lt;/h3&gt;

&lt;p&gt;The &lt;code&gt;-u&lt;/code&gt; (upstream) parameter is used when pushing a new branch for the first time. This sets the upstream tracking relationship between the local branch and the remote branch. After that, simply running &lt;code&gt;git push&lt;/code&gt; is enough for future pushes:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;git push &lt;span class="nt"&gt;-u&lt;/span&gt; origin new-feature
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;To change or set the upstream of an existing branch:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;git branch &lt;span class="nt"&gt;--set-upstream-to&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;origin/main main
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;h3&gt;
  
  
  ★ Other Parameters
&lt;/h3&gt;



&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;git push origin &lt;span class="nt"&gt;--delete&lt;/span&gt; branch-name    &lt;span class="c"&gt;# Delete remote branch&lt;/span&gt;
git push &lt;span class="nt"&gt;--force&lt;/span&gt;                       &lt;span class="c"&gt;# or -f  ⚠️ be extra careful when using&lt;/span&gt;
git push &lt;span class="nt"&gt;--force-with-lease&lt;/span&gt;            &lt;span class="c"&gt;# Safer force push&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;⚠️ The &lt;code&gt;--force&lt;/code&gt; parameter rewrites history on the remote repository. It can cause teammates to lose their work. If you use &lt;code&gt;--force-with-lease&lt;/code&gt; instead, Git rejects the push if the remote branch contains commits you do not know about.&lt;/p&gt;

&lt;h2&gt;
  
  
  Fork and Pull Request 🍴
&lt;/h2&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.amazonaws.com%2Fuploads%2Farticles%2Fzibk83t3e3mgezd1ndc8.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.amazonaws.com%2Fuploads%2Farticles%2Fzibk83t3e3mgezd1ndc8.png" alt="Contributing to open source projects" width="800" height="446"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;h3&gt;
  
  
  ★ Fork
&lt;/h3&gt;

&lt;p&gt;Copying someone else's repository into your own GitHub/GitLab account. This is done through the &lt;strong&gt;Fork&lt;/strong&gt; button in the platform interface. A fork remains associated with the original repository on the hosting platform.&lt;/p&gt;

&lt;h3&gt;
  
  
  ★ Pull Request (PR) / Merge Request (MR)
&lt;/h3&gt;

&lt;p&gt;A request to have changes from your fork or branch accepted into the main repository. It is called a &lt;strong&gt;Pull Request&lt;/strong&gt; on GitHub and a &lt;strong&gt;Merge Request&lt;/strong&gt; on GitLab.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Typical workflow:&lt;/strong&gt;&lt;/p&gt;

&lt;ol&gt;
&lt;li&gt;Fork the repository&lt;/li&gt;
&lt;li&gt;Clone it to your local machine&lt;/li&gt;
&lt;li&gt;Create a new branch&lt;/li&gt;
&lt;li&gt;Make your changes and commit them&lt;/li&gt;
&lt;li&gt;Push to your fork&lt;/li&gt;
&lt;li&gt;Open a Pull Request on the platform&lt;/li&gt;
&lt;li&gt;Code review is performed&lt;/li&gt;
&lt;li&gt;If approved, it is merged into the main branch&lt;/li&gt;
&lt;/ol&gt;

&lt;h2&gt;
  
  
  Branching Strategies 🗺️
&lt;/h2&gt;

&lt;p&gt;Common strategies for how teams use Git:&lt;/p&gt;

&lt;h3&gt;
  
  
  ★ Git Flow
&lt;/h3&gt;

&lt;p&gt;A comprehensive branching strategy, often used in long-lived projects:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;strong&gt;main&lt;/strong&gt; — Published stable version&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;develop&lt;/strong&gt; — Development branch&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;feature/*&lt;/strong&gt; — For new features&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;release/*&lt;/strong&gt; — For release preparation&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;hotfix/*&lt;/strong&gt; — For urgent fixes&lt;/li&gt;
&lt;/ul&gt;

&lt;h3&gt;
  
  
  ★ GitHub Flow
&lt;/h3&gt;

&lt;p&gt;Well suited to teams that deploy frequently:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;strong&gt;main&lt;/strong&gt; — Always in a deployable state&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;feature branch&lt;/strong&gt; — New feature or fix&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Pull Request&lt;/strong&gt; — Code review and merging&lt;/li&gt;
&lt;/ul&gt;

&lt;h3&gt;
  
  
  ★ Trunk-Based Development
&lt;/h3&gt;

&lt;p&gt;Short-lived branches are used and continuously merged into the main branch (trunk). It is commonly used with continuous integration (CI) in large teams.&lt;/p&gt;

&lt;p&gt;💡 The best strategy depends on team size, project type, and deployment frequency. For small teams, GitHub Flow is generally enough.&lt;/p&gt;

&lt;h2&gt;
  
  
  Cherry Picking (git cherry-pick) 🍒
&lt;/h2&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.amazonaws.com%2Fuploads%2Farticles%2F0m91ptz8x8hj6o3apba6.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.amazonaws.com%2Fuploads%2Farticles%2F0m91ptz8x8hj6o3apba6.png" alt="Cherry Pick of Git" width="800" height="339"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;To take only a specific commit from another branch instead of merging the entire branch:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;git cherry-pick a1b2c3d
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;&lt;strong&gt;Example scenario:&lt;/strong&gt;&lt;/p&gt;

&lt;p&gt;The &lt;code&gt;new-feature&lt;/code&gt; branch has 5 commits, but you only want to bring the bug fix from one of them into &lt;code&gt;main&lt;/code&gt;:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;git checkout main
git cherry-pick f4e5d6c
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;To take multiple commits:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;git cherry-pick a1b2c3d f4e5d6c
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;If a conflict occurs during cherry-pick, resolve it like a normal merge conflict and continue:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;git add &lt;span class="nb"&gt;.&lt;/span&gt;
git cherry-pick &lt;span class="nt"&gt;--continue&lt;/span&gt;

&lt;span class="c"&gt;# or cancel:&lt;/span&gt;
git cherry-pick &lt;span class="nt"&gt;--abort&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;h2&gt;
  
  
  Line-by-Line History (git blame) 🔬
&lt;/h2&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.amazonaws.com%2Fuploads%2Farticles%2Fuczeknhh58irfxvcof5o.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.amazonaws.com%2Fuploads%2Farticles%2Fuczeknhh58irfxvcof5o.png" alt="Line-by-Line History of Git" width="800" height="339"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;To see who last changed each line of a file and when:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;git blame names.txt
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Example output:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;a1b2c3d4 (Beril Dumanlı     2025-01-10) Eda
f4e5d6c7 (Sitare Demir      2025-02-15) Beyza
b7a8c9d0 (Arya Çelik        2025-03-22) Tuvana
a1b2c3d4 (Beril Dumanlı     2025-01-10) Melis
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;💡 In the example above, the first and last lines were changed by the same person at different positions in the file. Lines 2 and 3 in between were changed by different people.&lt;/p&gt;

&lt;h3&gt;
  
  
  ★ Additional Parameters
&lt;/h3&gt;



&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;git blame &lt;span class="nt"&gt;-L&lt;/span&gt; 5,10 names.txt     &lt;span class="c"&gt;# Only lines 5-10&lt;/span&gt;
git blame &lt;span class="nt"&gt;-e&lt;/span&gt; names.txt           &lt;span class="c"&gt;# Show email addresses&lt;/span&gt;
git blame &lt;span class="nt"&gt;-w&lt;/span&gt; names.txt           &lt;span class="c"&gt;# Ignore whitespace changes&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Useful for tracing when and by whom a line was last modified.&lt;/p&gt;

&lt;h2&gt;
  
  
  Searching (git grep) 🔎
&lt;/h2&gt;

&lt;p&gt;To search for text within the &lt;strong&gt;contents&lt;/strong&gt; of files in the repository:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;git &lt;span class="nb"&gt;grep&lt;/span&gt; &lt;span class="s2"&gt;"Beril"&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Example output:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;names.txt:Beril
notes.txt:Beril's note added
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;h3&gt;
  
  
  ★ Additional Parameters
&lt;/h3&gt;



&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;git &lt;span class="nb"&gt;grep&lt;/span&gt; &lt;span class="nt"&gt;-n&lt;/span&gt; &lt;span class="s2"&gt;"Beril"&lt;/span&gt;                  &lt;span class="c"&gt;# Show line numbers&lt;/span&gt;
git &lt;span class="nb"&gt;grep&lt;/span&gt; &lt;span class="nt"&gt;-c&lt;/span&gt; &lt;span class="s2"&gt;"Beril"&lt;/span&gt;                  &lt;span class="c"&gt;# Number of matches in each file&lt;/span&gt;
git &lt;span class="nb"&gt;grep&lt;/span&gt; &lt;span class="nt"&gt;-i&lt;/span&gt; &lt;span class="s2"&gt;"beril"&lt;/span&gt;                  &lt;span class="c"&gt;# Case-insensitive search&lt;/span&gt;
git &lt;span class="nb"&gt;grep&lt;/span&gt; &lt;span class="s2"&gt;"Beril"&lt;/span&gt; &lt;span class="nt"&gt;--&lt;/span&gt; &lt;span class="s2"&gt;"*.txt"&lt;/span&gt;          &lt;span class="c"&gt;# Search only in .txt files&lt;/span&gt;
git &lt;span class="nb"&gt;grep&lt;/span&gt; &lt;span class="s2"&gt;"Beril"&lt;/span&gt; a1b2c3d             &lt;span class="c"&gt;# Search in files at a specific commit&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;💡 Unlike regular &lt;code&gt;grep&lt;/code&gt;, &lt;code&gt;git grep&lt;/code&gt; searches only files tracked by Git. It skips files listed in &lt;code&gt;.gitignore&lt;/code&gt;, so it does not waste time scanning directories like &lt;code&gt;node_modules&lt;/code&gt;. This makes it much faster in large projects.&lt;/p&gt;

&lt;h2&gt;
  
  
  Finding Bugs with Binary Search (git bisect) 🐛
&lt;/h2&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.amazonaws.com%2Fuploads%2Farticles%2Fo2a17uu44c6r0ui8rcaz.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.amazonaws.com%2Fuploads%2Farticles%2Fo2a17uu44c6r0ui8rcaz.png" alt="Finding Bugs with Binary Search of Git" width="800" height="339"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;There is a bug in your project, but you do not know which commit introduced it. &lt;code&gt;git bisect&lt;/code&gt; uses a binary search algorithm to quickly find the problematic commit among hundreds of commits.&lt;/p&gt;

&lt;h3&gt;
  
  
  ★ Usage
&lt;/h3&gt;



&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;&lt;span class="c"&gt;# Start bisect&lt;/span&gt;
git bisect start

&lt;span class="c"&gt;# Mark the current commit as buggy&lt;/span&gt;
git bisect bad

&lt;span class="c"&gt;# Mark an old commit that you know was working&lt;/span&gt;
git bisect good a1b2c3d
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Git automatically checks out a commit in the middle. Test the project:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;&lt;span class="c"&gt;# If the bug exists in this commit too:&lt;/span&gt;
git bisect bad

&lt;span class="c"&gt;# If the bug does not exist in this commit:&lt;/span&gt;
git bisect good
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;At each step, Git cuts the search space in half. It finds the buggy commit in just a few steps:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;f4e5d6c is the first bad commit
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;When you are done:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;git bisect reset
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;💡 If there are 128 commits, &lt;code&gt;git bisect&lt;/code&gt; finds the buggy commit in at most &lt;strong&gt;7 steps&lt;/strong&gt;. (log₂128 = 7)&lt;/p&gt;

&lt;h2&gt;
  
  
  Viewing Commit Details (git show) 🔍
&lt;/h2&gt;

&lt;p&gt;To see the details of a single commit (author, date, message, and changes made):&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;git show               &lt;span class="c"&gt;# Details of the last commit&lt;/span&gt;
git show a1b2c3d       &lt;span class="c"&gt;# Details of a specific commit&lt;/span&gt;
git show v1.0          &lt;span class="c"&gt;# Details of the commit the tag points to&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;While &lt;code&gt;git log&lt;/code&gt; shows commit history, &lt;code&gt;git show&lt;/code&gt; displays the full details of a single commit, including the diff.&lt;/p&gt;

&lt;h2&gt;
  
  
  Cleaning Untracked Files (git clean) 🧹
&lt;/h2&gt;

&lt;p&gt;To delete untracked files from the working directory:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;git clean &lt;span class="nt"&gt;-n&lt;/span&gt;           &lt;span class="c"&gt;# Show what would be deleted first (dry run)&lt;/span&gt;
git clean &lt;span class="nt"&gt;-f&lt;/span&gt;           &lt;span class="c"&gt;# Delete untracked files&lt;/span&gt;
git clean &lt;span class="nt"&gt;-fd&lt;/span&gt;          &lt;span class="c"&gt;# Delete files and directories&lt;/span&gt;
git clean &lt;span class="nt"&gt;-fdx&lt;/span&gt;         &lt;span class="c"&gt;# Delete everything including files in .gitignore&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;⚠️ &lt;code&gt;git clean&lt;/code&gt; is irreversible. Always check with &lt;code&gt;-n&lt;/code&gt; (dry run) before deleting.&lt;/p&gt;

&lt;h2&gt;
  
  
  Git Hooks 🪝
&lt;/h2&gt;

&lt;p&gt;Hooks are scripts that run automatically on specific Git events. They are located in the &lt;code&gt;.git/hooks/&lt;/code&gt; folder.&lt;/p&gt;

&lt;h3&gt;
  
  
  ★ Commonly Used Hooks
&lt;/h3&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;strong&gt;pre-commit&lt;/strong&gt; — Runs before a commit (lint, format check)&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;commit-msg&lt;/strong&gt; — Runs after the commit message is entered, before the commit is finalized (message format check)&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;pre-push&lt;/strong&gt; — Runs before a push (for example, running tests)&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;post-merge&lt;/strong&gt; — Runs after a merge (for example, updating dependencies)&lt;/li&gt;
&lt;/ul&gt;

&lt;h3&gt;
  
  
  ★ Example: Lint Check Before Commit
&lt;/h3&gt;

&lt;p&gt;Create a &lt;code&gt;.git/hooks/pre-commit&lt;/code&gt; file and make it executable:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;&lt;span class="c"&gt;#!/bin/sh&lt;/span&gt;
npm run lint
&lt;span class="k"&gt;if&lt;/span&gt; &lt;span class="o"&gt;[&lt;/span&gt; &lt;span class="nv"&gt;$?&lt;/span&gt; &lt;span class="nt"&gt;-ne&lt;/span&gt; 0 &lt;span class="o"&gt;]&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt; &lt;span class="k"&gt;then
  &lt;/span&gt;&lt;span class="nb"&gt;echo&lt;/span&gt; &lt;span class="s2"&gt;"Lint errors found. Commit cancelled."&lt;/span&gt;
  &lt;span class="nb"&gt;exit &lt;/span&gt;1
&lt;span class="k"&gt;fi&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;





&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;&lt;span class="nb"&gt;chmod&lt;/span&gt; +x .git/hooks/pre-commit
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;💡 Hooks in the &lt;code&gt;.git/hooks/&lt;/code&gt; folder are not shared with the repository. For team-wide hook sharing, tools like &lt;a href="https://typicode.github.io/husky/" rel="noopener noreferrer"&gt;Husky&lt;/a&gt; can be used.&lt;/p&gt;

&lt;h2&gt;
  
  
  Managing External Repositories (Submodule &amp;amp; Subtree) 📦
&lt;/h2&gt;

&lt;p&gt;In large projects, you may need to include other repositories in your own project.&lt;/p&gt;

&lt;h3&gt;
  
  
  ★ git submodule
&lt;/h3&gt;

&lt;p&gt;Embeds another repository inside your repository as a reference to a specific commit. The subproject remains independent; only a specific commit is referenced:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;git submodule add https://github.com/user/library.git libs/library
git commit &lt;span class="nt"&gt;-m&lt;/span&gt; &lt;span class="s2"&gt;"Library added as submodule"&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;When a repository with submodules is cloned, submodule contents are not checked out automatically:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;git clone &lt;span class="nt"&gt;--recurse-submodules&lt;/span&gt; &amp;lt;url&amp;gt;
&lt;span class="c"&gt;# or after cloning:&lt;/span&gt;
git submodule update &lt;span class="nt"&gt;--init&lt;/span&gt; &lt;span class="nt"&gt;--recursive&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;h3&gt;
  
  
  ★ git subtree
&lt;/h3&gt;

&lt;p&gt;&lt;strong&gt;Copies&lt;/strong&gt; another repository's code directly into your project. It is simpler than submodule, but it increases repository size:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;git subtree add &lt;span class="nt"&gt;--prefix&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;libs/library https://github.com/user/library.git main &lt;span class="nt"&gt;--squash&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;💡 Submodule is more widely used, but managing it is more complex. Subtree is a simpler alternative. Choose based on your needs.&lt;/p&gt;

&lt;h2&gt;
  
  
  Git Garbage Collection (git gc) 🗑️
&lt;/h2&gt;

&lt;p&gt;Over time, Git accumulates unreachable and unnecessary objects (commits, blobs, trees) in its internal structure. &lt;code&gt;git gc&lt;/code&gt; cleans up these objects and optimizes the repository:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;git gc
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;h3&gt;
  
  
  ★ When Does It Run?
&lt;/h3&gt;

&lt;ul&gt;
&lt;li&gt;Git automatically triggers gc during some commands (&lt;code&gt;git merge&lt;/code&gt;, &lt;code&gt;git rebase&lt;/code&gt;, etc.)&lt;/li&gt;
&lt;li&gt;You can also run it manually&lt;/li&gt;
&lt;/ul&gt;

&lt;h3&gt;
  
  
  ★ What Gets Cleaned?
&lt;/h3&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;strong&gt;Orphan commits&lt;/strong&gt; not referenced by any branch, tag, or HEAD&lt;/li&gt;
&lt;li&gt;Reflog entries past their retention period (default 90 days)&lt;/li&gt;
&lt;li&gt;Unused Git objects
&lt;/li&gt;
&lt;/ul&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;git gc &lt;span class="nt"&gt;--aggressive&lt;/span&gt;       &lt;span class="c"&gt;# Deeper optimization (slow but effective)&lt;/span&gt;
git gc &lt;span class="nt"&gt;--prune&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;now        &lt;span class="c"&gt;# Delete all unreachable objects immediately&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;⚠️ Under normal circumstances, you do not need to run &lt;code&gt;git gc&lt;/code&gt; manually. Git handles this automatically in the background.&lt;/p&gt;

&lt;p&gt;📌 Detailed information: &lt;a href="https://git-scm.com/docs/git-gc" rel="noopener noreferrer"&gt;git-scm.com/docs/git-gc&lt;/a&gt;&lt;/p&gt;

&lt;h2&gt;
  
  
  Git Internals: A Brief Look 🧬
&lt;/h2&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.amazonaws.com%2Fuploads%2Farticles%2Fzdomiquqhi7e3rqa85oe.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.amazonaws.com%2Fuploads%2Farticles%2Fzdomiquqhi7e3rqa85oe.png" alt="Git Internals" width="800" height="339"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;Let's take a brief look at what is inside Git's &lt;code&gt;.git&lt;/code&gt; folder:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;.git/
├── HEAD              # Reference to current branch
├── config            # Repository configuration
├── objects/          # All Git objects (commit, tree, blob)
├── refs/             # Branch and tag references
│   ├── heads/        # Local branches
│   └── tags/         # Tags
├── hooks/            # Automatically triggered scripts
└── index             # Staging area data
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;h3&gt;
  
  
  ★ Git's Three Fundamental Objects
&lt;/h3&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;strong&gt;Blob&lt;/strong&gt; — Stores file content (does not store the file name)&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Tree&lt;/strong&gt; — Stores the structure of a directory (which blob corresponds to which file name)&lt;/li&gt;
&lt;li&gt;
&lt;strong&gt;Commit&lt;/strong&gt; — Represents a snapshot; contains tree, author, date, and message information&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;Git traditionally identifies each object with a SHA-1 hash. This hash is generated from the object's content. Newer versions also support SHA-256.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;&lt;span class="c"&gt;# To view an object's content:&lt;/span&gt;
git cat-file &lt;span class="nt"&gt;-p&lt;/span&gt; a1b2c3d

&lt;span class="c"&gt;# To view an object's type:&lt;/span&gt;
git cat-file &lt;span class="nt"&gt;-t&lt;/span&gt; a1b2c3d
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;💡 Git internals is a large topic on its own. It will be covered in more detail in a separate article.&lt;/p&gt;

&lt;h2&gt;
  
  
  Git Commands Summary 📋
&lt;/h2&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.amazonaws.com%2Fuploads%2Farticles%2F1arx41w86yqmdehm5zaa.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.amazonaws.com%2Fuploads%2Farticles%2F1arx41w86yqmdehm5zaa.png" alt="Git Commands Summary Table" width="800" height="446"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;h3&gt;
  
  
  ★ Basic Commands
&lt;/h3&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;code&gt;git init&lt;/code&gt; — Creates a new repository&lt;/li&gt;
&lt;li&gt;
&lt;code&gt;git clone &amp;lt;url&amp;gt;&lt;/code&gt; — Clones a remote repository&lt;/li&gt;
&lt;li&gt;
&lt;code&gt;git status&lt;/code&gt; — Shows repository status&lt;/li&gt;
&lt;li&gt;
&lt;code&gt;git add &amp;lt;file&amp;gt;&lt;/code&gt; — Adds a file to the staging area&lt;/li&gt;
&lt;li&gt;
&lt;code&gt;git add .&lt;/code&gt; — Adds all changes&lt;/li&gt;
&lt;li&gt;
&lt;code&gt;git commit -m "message"&lt;/code&gt; — Creates a commit&lt;/li&gt;
&lt;li&gt;
&lt;code&gt;git commit -am "message"&lt;/code&gt; — Commits modified tracked files&lt;/li&gt;
&lt;li&gt;
&lt;code&gt;git show &amp;lt;hash&amp;gt;&lt;/code&gt; — Shows commit details&lt;/li&gt;
&lt;/ul&gt;

&lt;h3&gt;
  
  
  ★ File Operations
&lt;/h3&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;code&gt;git rm &amp;lt;file&amp;gt;&lt;/code&gt; — Deletes a file and stages the removal&lt;/li&gt;
&lt;li&gt;
&lt;code&gt;git rm --cached &amp;lt;file&amp;gt;&lt;/code&gt; — Removes a file from version control (does not delete it from disk)&lt;/li&gt;
&lt;li&gt;
&lt;code&gt;git mv &amp;lt;old&amp;gt; &amp;lt;new&amp;gt;&lt;/code&gt; — Moves/renames a file&lt;/li&gt;
&lt;li&gt;
&lt;code&gt;git clean -fd&lt;/code&gt; — Deletes untracked files and directories&lt;/li&gt;
&lt;/ul&gt;

&lt;h3&gt;
  
  
  ★ History and Diffs
&lt;/h3&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;code&gt;git log&lt;/code&gt; — Shows commit history&lt;/li&gt;
&lt;li&gt;
&lt;code&gt;git log --oneline --graph --decorate --all&lt;/code&gt; — Visual commit history&lt;/li&gt;
&lt;li&gt;
&lt;code&gt;git diff&lt;/code&gt; — Shows file differences&lt;/li&gt;
&lt;li&gt;
&lt;code&gt;git blame &amp;lt;file&amp;gt;&lt;/code&gt; — Shows who changed each line&lt;/li&gt;
&lt;li&gt;
&lt;code&gt;git reflog&lt;/code&gt; — Shows HEAD/reference update history&lt;/li&gt;
&lt;li&gt;
&lt;code&gt;git shortlog -sn&lt;/code&gt; — Commit counts by contributor&lt;/li&gt;
&lt;/ul&gt;

&lt;h3&gt;
  
  
  ★ Branching and Merging
&lt;/h3&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;code&gt;git branch &amp;lt;name&amp;gt;&lt;/code&gt; — Creates a new branch&lt;/li&gt;
&lt;li&gt;
&lt;code&gt;git branch -d &amp;lt;name&amp;gt;&lt;/code&gt; — Deletes a branch&lt;/li&gt;
&lt;li&gt;
&lt;code&gt;git checkout &amp;lt;branch&amp;gt;&lt;/code&gt; — Switches to a branch&lt;/li&gt;
&lt;li&gt;
&lt;code&gt;git checkout -b &amp;lt;name&amp;gt;&lt;/code&gt; — Creates a branch and switches to it&lt;/li&gt;
&lt;li&gt;
&lt;code&gt;git switch &amp;lt;branch&amp;gt;&lt;/code&gt; — Switches to a branch (modern)&lt;/li&gt;
&lt;li&gt;
&lt;code&gt;git merge &amp;lt;branch&amp;gt;&lt;/code&gt; — Merges branches&lt;/li&gt;
&lt;li&gt;
&lt;code&gt;git merge --no-ff &amp;lt;branch&amp;gt;&lt;/code&gt; — Always creates a merge commit&lt;/li&gt;
&lt;li&gt;
&lt;code&gt;git merge --abort&lt;/code&gt; — Cancels the merge&lt;/li&gt;
&lt;li&gt;
&lt;code&gt;git rebase &amp;lt;branch&amp;gt;&lt;/code&gt; — Rebases commits&lt;/li&gt;
&lt;li&gt;
&lt;code&gt;git rebase --onto &amp;lt;new-base&amp;gt; &amp;lt;old-base&amp;gt; &amp;lt;branch&amp;gt;&lt;/code&gt; — Moves a branch to a different base&lt;/li&gt;
&lt;li&gt;
&lt;code&gt;git cherry-pick &amp;lt;hash&amp;gt;&lt;/code&gt; — Applies a specific commit&lt;/li&gt;
&lt;/ul&gt;

&lt;h3&gt;
  
  
  ★ Undoing
&lt;/h3&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;code&gt;git restore &amp;lt;file&amp;gt;&lt;/code&gt; — Discards file changes&lt;/li&gt;
&lt;li&gt;
&lt;code&gt;git restore --staged &amp;lt;file&amp;gt;&lt;/code&gt; — Removes a file from staging&lt;/li&gt;
&lt;li&gt;
&lt;code&gt;git reset --soft HEAD~1&lt;/code&gt; — Undoes a commit, keeps changes staged&lt;/li&gt;
&lt;li&gt;
&lt;code&gt;git reset --hard HEAD~1&lt;/code&gt; — Completely deletes a commit and its changes&lt;/li&gt;
&lt;li&gt;
&lt;code&gt;git revert &amp;lt;hash&amp;gt;&lt;/code&gt; — Creates a new commit that undoes another commit&lt;/li&gt;
&lt;/ul&gt;

&lt;h3&gt;
  
  
  ★ Temporary Storage
&lt;/h3&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;code&gt;git stash&lt;/code&gt; — Temporarily saves changes&lt;/li&gt;
&lt;li&gt;
&lt;code&gt;git stash push -m "message"&lt;/code&gt; — Saves changes with a message&lt;/li&gt;
&lt;li&gt;
&lt;code&gt;git stash -u&lt;/code&gt; — Saves changes including untracked files&lt;/li&gt;
&lt;li&gt;
&lt;code&gt;git stash pop&lt;/code&gt; — Restores the latest stash&lt;/li&gt;
&lt;li&gt;
&lt;code&gt;git stash list&lt;/code&gt; — Lists stashes&lt;/li&gt;
&lt;/ul&gt;

&lt;h3&gt;
  
  
  ★ Remote Repository
&lt;/h3&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;code&gt;git remote add &amp;lt;name&amp;gt; &amp;lt;url&amp;gt;&lt;/code&gt; — Adds a remote repository&lt;/li&gt;
&lt;li&gt;
&lt;code&gt;git remote -v&lt;/code&gt; — Lists remote repositories&lt;/li&gt;
&lt;li&gt;
&lt;code&gt;git fetch&lt;/code&gt; — Downloads remote changes&lt;/li&gt;
&lt;li&gt;
&lt;code&gt;git pull&lt;/code&gt; — Downloads and merges changes&lt;/li&gt;
&lt;li&gt;
&lt;code&gt;git pull --rebase&lt;/code&gt; — Downloads and rebases changes&lt;/li&gt;
&lt;li&gt;
&lt;code&gt;git push&lt;/code&gt; — Pushes commits to a remote repository&lt;/li&gt;
&lt;li&gt;
&lt;code&gt;git push -u origin &amp;lt;branch&amp;gt;&lt;/code&gt; — Pushes a branch for the first time&lt;/li&gt;
&lt;li&gt;
&lt;code&gt;git push --force-with-lease&lt;/code&gt; — Safer force push&lt;/li&gt;
&lt;/ul&gt;

&lt;h3&gt;
  
  
  ★ Tagging and Searching
&lt;/h3&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;code&gt;git tag &amp;lt;name&amp;gt;&lt;/code&gt; — Adds a tag&lt;/li&gt;
&lt;li&gt;
&lt;code&gt;git tag -a &amp;lt;name&amp;gt; -m "message"&lt;/code&gt; — Adds an annotated tag&lt;/li&gt;
&lt;li&gt;
&lt;code&gt;git grep "text"&lt;/code&gt; — Searches file contents&lt;/li&gt;
&lt;li&gt;
&lt;code&gt;git bisect start&lt;/code&gt; — Starts bug hunting with binary search&lt;/li&gt;
&lt;/ul&gt;

&lt;h3&gt;
  
  
  ★ Configuration Shortcuts
&lt;/h3&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;code&gt;git config --global alias.st status&lt;/code&gt; — &lt;code&gt;git st&lt;/code&gt; shortcut&lt;/li&gt;
&lt;li&gt;
&lt;code&gt;git config --global alias.co checkout&lt;/code&gt; — &lt;code&gt;git co&lt;/code&gt; shortcut&lt;/li&gt;
&lt;li&gt;
&lt;code&gt;git config --global alias.br branch&lt;/code&gt; — &lt;code&gt;git br&lt;/code&gt; shortcut&lt;/li&gt;
&lt;li&gt;
&lt;code&gt;git config --global alias.lg "log --oneline --graph --decorate --all"&lt;/code&gt; — &lt;code&gt;git lg&lt;/code&gt; shortcut&lt;/li&gt;
&lt;/ul&gt;




&lt;p&gt;📬 &lt;strong&gt;Feedback&lt;/strong&gt;&lt;/p&gt;

&lt;p&gt;While writing this article, I relied on my own notes for source selection and research, and used the &lt;strong&gt;"Claude Opus 4"&lt;/strong&gt; model for proofreading and additional research. Images were generated using the &lt;strong&gt;"Gemini 3 Pro Preview 2k (Nano Banana Pro)"&lt;/strong&gt; model.&lt;/p&gt;

&lt;p&gt;I welcome feedback, suggestions, and constructive criticism on this article. If you'd like to get in touch, you can reach me through the social links on my &lt;a href="https://yasinates.com" rel="noopener noreferrer"&gt;website&lt;/a&gt; or via &lt;a href="https://www.linkedin.com/in/yasinatesim" rel="noopener noreferrer"&gt;LinkedIn&lt;/a&gt;.&lt;/p&gt;

&lt;p&gt;Best, Yasin 🤗&lt;/p&gt;

&lt;p&gt;📚 &lt;strong&gt;Sources Used While Writing This Article&lt;/strong&gt;&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;&lt;a href="https://git-scm.com/doc" rel="noopener noreferrer"&gt;Git Documentation — git-scm.com/doc&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://git-scm.com/book/en/v2" rel="noopener noreferrer"&gt;Pro Git Book — git-scm.com/book&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://docs.github.com" rel="noopener noreferrer"&gt;GitHub Docs — docs.github.com&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://www.atlassian.com/git/tutorials" rel="noopener noreferrer"&gt;Atlassian Git Tutorials — atlassian.com/git/tutorials&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://www.git-tower.com/learn/git/commands/git-commit" rel="noopener noreferrer"&gt;Git Commit — Tower&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://fatihacet.com/git-bisect/" rel="noopener noreferrer"&gt;Git Bisect — Fatih AÇET&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://medium.com/turkce/yeni-ba%C5%9Flayanlar-i%C3%A7in-git-101-ff7ea5b3eff9" rel="noopener noreferrer"&gt;Yeni Başlayanlar İçin Git 101 — Medium&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://medium.com/turkce/ba%C5%9Far%C4%B1l%C4%B1-bir-git-branch-modeli-nas%C4%B1l-olu%C5%9Fturulur-e026e5cc24c2" rel="noopener noreferrer"&gt;Başarılı Bir Git Branch Modeli Nasıl Oluşturulur — Medium&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://medium.com/@onejohi/git-understanding-the-basics-ba004a20dacc" rel="noopener noreferrer"&gt;Git: Understanding the Basics — Medium&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://medium.com/@mustafazahidefe/git-notlar%C4%B1-5-branch-kavram%C4%B1-d176626711a4" rel="noopener noreferrer"&gt;Git Notları 5: Branch Kavramı — Medium&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://www.atlassian.com/git/tutorials/using-branches/git-checkout" rel="noopener noreferrer"&gt;Git Checkout — Atlassian&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://medium.com/kodgemisi/yeni-baslayanlar-icin-git-ee548b2abb36" rel="noopener noreferrer"&gt;Yeni Başlayanlar İçin Git — Medium&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://medium.com/bambam-t%C3%BCrkiye/git-nedir-70325a66d45b" rel="noopener noreferrer"&gt;Git Nedir? — Medium&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://medium.com/bambam-t%C3%BCrkiye/git-sunucu-servisleri-alternatifler-556269acbc3c" rel="noopener noreferrer"&gt;Git Sunucu Servisleri Alternatifler — Medium&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://www.conventionalcommits.org/" rel="noopener noreferrer"&gt;Conventional Commits&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://commitizen-tools.github.io/commitizen/" rel="noopener noreferrer"&gt;Commitizen&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://commitlint.js.org/" rel="noopener noreferrer"&gt;Commitlint&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;

</description>
      <category>git</category>
      <category>github</category>
      <category>gitlab</category>
      <category>bitbucket</category>
    </item>
    <item>
      <title>Keep Your GitHub Profile README Alive: Auto-Update with GitHub Actions ⚡</title>
      <dc:creator>Yasin ATEŞ</dc:creator>
      <pubDate>Tue, 10 Mar 2026 03:00:00 +0000</pubDate>
      <link>https://dev.to/yasinatesim/keep-your-github-profile-readme-alive-auto-update-with-github-actions-952</link>
      <guid>https://dev.to/yasinatesim/keep-your-github-profile-readme-alive-auto-update-with-github-actions-952</guid>
      <description>&lt;p&gt;Someone visiting your GitHub profile wants to get to know you. They want to see who you are, what you build, what you write. But most profile READMEs are written once and then left untouched for years. A "latest posts" list from 2021, expired projects, a tech stack still waiting to be updated.&lt;/p&gt;

&lt;p&gt;What if your README updated itself every morning?&lt;/p&gt;

&lt;p&gt;In this article we will build a system that automatically pulls your Medium and dev.to articles, runs daily via GitHub Actions, and keeps your README alive. We will walk through every step: the Python script, the workflow file, placeholder markers, and manual triggering.&lt;/p&gt;




&lt;h2&gt;
  
  
  1. How Does It Work? 🔄
&lt;/h2&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.amazonaws.com%2Fuploads%2Farticles%2Farcmy7vmtapz61hfoses.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.amazonaws.com%2Fuploads%2Farticles%2Farcmy7vmtapz61hfoses.png" alt="How It works github actions via auto update profile readme" width="800" height="446"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;The system we are building has four parts:&lt;/p&gt;

&lt;p&gt;We place special HTML comment lines inside &lt;strong&gt;README.md&lt;/strong&gt; (like &lt;code&gt;&amp;lt;!-- MEDIUM-ARTICLES:START --&amp;gt;&lt;/code&gt;). The script finds the content between these markers and replaces it; it does not touch anything outside the markers.&lt;/p&gt;

&lt;p&gt;The &lt;strong&gt;Python script&lt;/strong&gt; calls Medium's RSS feed and dev.to's REST API, collects article titles and URLs, then updates the README.&lt;/p&gt;

&lt;p&gt;The &lt;strong&gt;GitHub Actions workflow&lt;/strong&gt; runs this script on a schedule. It triggers every day at 06:00 UTC; if the script makes any changes, it automatically commits and pushes.&lt;/p&gt;

&lt;p&gt;The &lt;strong&gt;manual trigger&lt;/strong&gt; option means you do not have to wait. The moment you publish a new article, you can run it with a single click from the Actions tab.&lt;/p&gt;

&lt;blockquote&gt;
&lt;p&gt;💡 The entire system runs on GitHub's own infrastructure. No external server, no paid service, and your machine does not need to be on. GitHub Actions is free for public repos.&lt;/p&gt;
&lt;/blockquote&gt;




&lt;h2&gt;
  
  
  2. What Is a GitHub Profile README? 👤
&lt;/h2&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.amazonaws.com%2Fuploads%2Farticles%2F4in48i2fbh8y73gedj97.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.amazonaws.com%2Fuploads%2Farticles%2F4in48i2fbh8y73gedj97.png" alt="What Is the github profile readme" width="800" height="446"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;When you create a repository with the same name as your username, GitHub automatically displays the &lt;code&gt;README.md&lt;/code&gt; inside it on your profile page. This is a special GitHub feature.&lt;/p&gt;

&lt;h3&gt;
  
  
  How to Create the Profile README Repo
&lt;/h3&gt;

&lt;ol&gt;
&lt;li&gt;Click the &lt;strong&gt;New repository&lt;/strong&gt; button on GitHub&lt;/li&gt;
&lt;li&gt;Enter &lt;strong&gt;your own username&lt;/strong&gt; as the repository name (e.g. &lt;code&gt;yasinatesim&lt;/code&gt;)&lt;/li&gt;
&lt;li&gt;Make sure &lt;strong&gt;Public&lt;/strong&gt; is selected&lt;/li&gt;
&lt;li&gt;Check the &lt;strong&gt;Add a README file&lt;/strong&gt; checkbox&lt;/li&gt;
&lt;li&gt;Click &lt;strong&gt;Create repository&lt;/strong&gt;
&lt;/li&gt;
&lt;/ol&gt;

&lt;p&gt;When the repo is created, GitHub greets you with "✨ yasinatesim/yasinatesim is a special repository." Everything you write in &lt;code&gt;README.md&lt;/code&gt; starts appearing on your profile.&lt;/p&gt;

&lt;blockquote&gt;
&lt;p&gt;⚠️ The repository name must be &lt;strong&gt;exactly&lt;/strong&gt; the same as your username, including case. &lt;code&gt;Yasinatesim&lt;/code&gt; and &lt;code&gt;yasinatesim&lt;/code&gt; are different repos and the profile feature will not work.&lt;/p&gt;
&lt;/blockquote&gt;




&lt;h2&gt;
  
  
  3. Adding Placeholder Markers to the README 📍
&lt;/h2&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.amazonaws.com%2Fuploads%2Farticles%2F9qgv5aj1u0hdgwpxa7rp.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.amazonaws.com%2Fuploads%2Farticles%2F9qgv5aj1u0hdgwpxa7rp.png" alt="Adding Placeholder Markers to the GitHub README" width="800" height="446"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;How does the script know what to update in the README? Through special markers we place as HTML comment lines. These markers are invisible in the browser and on GitHub, but they act as coordinates for the script.&lt;/p&gt;

&lt;p&gt;Add the following block wherever you want articles to appear in your README:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight markdown"&gt;&lt;code&gt;&lt;span class="gu"&gt;## ✍️ Latest Medium Articles&lt;/span&gt;

&lt;span class="c"&gt;&amp;lt;!-- MEDIUM-ARTICLES:START --&amp;gt;&lt;/span&gt;
&lt;span class="c"&gt;&amp;lt;!-- MEDIUM-ARTICLES:END --&amp;gt;&lt;/span&gt;

&lt;span class="gu"&gt;## 📝 Latest dev.to Articles&lt;/span&gt;

&lt;span class="c"&gt;&amp;lt;!-- DEVTO-ARTICLES:START --&amp;gt;&lt;/span&gt;
&lt;span class="c"&gt;&amp;lt;!-- DEVTO-ARTICLES:END --&amp;gt;&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;When the script runs, it deletes everything between the two markers and writes the current article list in its place. It does not touch any line outside the markers. After the first run the output will look like this:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight markdown"&gt;&lt;code&gt;&lt;span class="gu"&gt;## ✍️ Latest Medium Articles&lt;/span&gt;

&lt;span class="c"&gt;&amp;lt;!-- MEDIUM-ARTICLES:START --&amp;gt;&lt;/span&gt;
&lt;span class="p"&gt;-&lt;/span&gt; &lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="nv"&gt;Micro Frontend Architecture (with React Examples)&lt;/span&gt;&lt;span class="p"&gt;](&lt;/span&gt;&lt;span class="sx"&gt;https://medium.com/...&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
&lt;span class="p"&gt;-&lt;/span&gt; &lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="nv"&gt;How We Integrated Google Lighthouse into Our Dev Process&lt;/span&gt;&lt;span class="p"&gt;](&lt;/span&gt;&lt;span class="sx"&gt;https://medium.com/...&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="ge"&gt;*(Hepsiburadatech)*&lt;/span&gt;
&lt;span class="p"&gt;-&lt;/span&gt; &lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="nv"&gt;TypeScript from A to Z&lt;/span&gt;&lt;span class="p"&gt;](&lt;/span&gt;&lt;span class="sx"&gt;https://medium.com/...&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
&lt;span class="c"&gt;&amp;lt;!-- MEDIUM-ARTICLES:END --&amp;gt;&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;blockquote&gt;
&lt;p&gt;💡 The example above is from my own GitHub Profile README. Publication info (the channel name in parentheses) is extracted automatically from the article URL by the script. When it sees a URL like &lt;code&gt;medium.com/publication/...&lt;/code&gt;, it grabs the slug and adds it in parentheses next to the article title (shown on the second line above). For personal profile articles (&lt;code&gt;medium.com/@yasinatesim/...&lt;/code&gt;) it shows no parentheses.&lt;/p&gt;
&lt;/blockquote&gt;




&lt;h2&gt;
  
  
  4. Python Script: Fetching Article Data 🐍
&lt;/h2&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.amazonaws.com%2Fuploads%2Farticles%2Fqsurmmtxguvmy9jnh8xa.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.amazonaws.com%2Fuploads%2Farticles%2Fqsurmmtxguvmy9jnh8xa.png" alt="Fetching Article Data on medium and dev.to" width="800" height="446"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;The entire script uses two external libraries: &lt;code&gt;feedparser&lt;/code&gt; (for the Medium RSS feed) and &lt;code&gt;requests&lt;/code&gt; (for the dev.to API). No other dependencies.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;scripts/
└── fetch_articles.py
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;h3&gt;
  
  
  4.1 Basic Structure
&lt;/h3&gt;



&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight python"&gt;&lt;code&gt;&lt;span class="sh"&gt;"""&lt;/span&gt;&lt;span class="s"&gt;
fetch_articles.py
-----------------
Fetches all articles from Medium RSS and the dev.to API,
then automatically updates the placeholders in README.md.
&lt;/span&gt;&lt;span class="sh"&gt;"""&lt;/span&gt;

&lt;span class="kn"&gt;import&lt;/span&gt; &lt;span class="n"&gt;re&lt;/span&gt;
&lt;span class="kn"&gt;import&lt;/span&gt; &lt;span class="n"&gt;feedparser&lt;/span&gt;
&lt;span class="kn"&gt;import&lt;/span&gt; &lt;span class="n"&gt;requests&lt;/span&gt;

&lt;span class="n"&gt;MEDIUM_USERNAME&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="s"&gt;your-username&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;   &lt;span class="c1"&gt;# without the @ sign
&lt;/span&gt;&lt;span class="n"&gt;DEVTO_USERNAME&lt;/span&gt;  &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="s"&gt;your-username&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;
&lt;span class="n"&gt;README_PATH&lt;/span&gt;     &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="s"&gt;README.md&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;

&lt;span class="n"&gt;MEDIUM_START&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="s"&gt;&amp;lt;!-- MEDIUM-ARTICLES:START --&amp;gt;&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;
&lt;span class="n"&gt;MEDIUM_END&lt;/span&gt;   &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="s"&gt;&amp;lt;!-- MEDIUM-ARTICLES:END --&amp;gt;&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;
&lt;span class="n"&gt;DEVTO_START&lt;/span&gt;  &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="s"&gt;&amp;lt;!-- DEVTO-ARTICLES:START --&amp;gt;&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;
&lt;span class="n"&gt;DEVTO_END&lt;/span&gt;    &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="s"&gt;&amp;lt;!-- DEVTO-ARTICLES:END --&amp;gt;&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;h3&gt;
  
  
  4.2 Fetching Medium Articles
&lt;/h3&gt;

&lt;p&gt;Medium provides a public RSS feed for every user. &lt;code&gt;feedparser&lt;/code&gt; converts this XML feed into Python objects. We do not set a limit; we process the entire &lt;code&gt;feed.entries&lt;/code&gt; list.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight python"&gt;&lt;code&gt;&lt;span class="k"&gt;def&lt;/span&gt; &lt;span class="nf"&gt;fetch_medium_articles&lt;/span&gt;&lt;span class="p"&gt;():&lt;/span&gt;
    &lt;span class="n"&gt;url&lt;/span&gt;  &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="sa"&gt;f&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="s"&gt;https://medium.com/feed/@&lt;/span&gt;&lt;span class="si"&gt;{&lt;/span&gt;&lt;span class="n"&gt;MEDIUM_USERNAME&lt;/span&gt;&lt;span class="si"&gt;}&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;
    &lt;span class="n"&gt;feed&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;feedparser&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;parse&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;url&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
    &lt;span class="n"&gt;articles&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="p"&gt;[]&lt;/span&gt;

    &lt;span class="k"&gt;for&lt;/span&gt; &lt;span class="n"&gt;entry&lt;/span&gt; &lt;span class="ow"&gt;in&lt;/span&gt; &lt;span class="n"&gt;feed&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;entries&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;
        &lt;span class="n"&gt;publication&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="bp"&gt;None&lt;/span&gt;
        &lt;span class="n"&gt;link&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;entry&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;link&lt;/span&gt;

        &lt;span class="c1"&gt;# Extract publication info from the URL
&lt;/span&gt;        &lt;span class="c1"&gt;# medium.com/publication-slug/... → publication exists
&lt;/span&gt;        &lt;span class="c1"&gt;# medium.com/@username/...        → personal profile, no publication
&lt;/span&gt;        &lt;span class="n"&gt;subdomain_match&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;re&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;match&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="sa"&gt;r&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="s"&gt;https://([^.]+)\.medium\.com/&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;link&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
        &lt;span class="n"&gt;path_match&lt;/span&gt;      &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;re&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;match&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="sa"&gt;r&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="s"&gt;https://medium\.com/([^@/][^/]*)/&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;link&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;

        &lt;span class="k"&gt;if&lt;/span&gt; &lt;span class="n"&gt;subdomain_match&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;
            &lt;span class="n"&gt;slug&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;subdomain_match&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;group&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
            &lt;span class="n"&gt;publication&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;slug&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;replace&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="s"&gt;-&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="s"&gt; &lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="p"&gt;).&lt;/span&gt;&lt;span class="nf"&gt;title&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;
        &lt;span class="k"&gt;elif&lt;/span&gt; &lt;span class="n"&gt;path_match&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;
            &lt;span class="n"&gt;slug&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;path_match&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;group&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
            &lt;span class="c1"&gt;# Filter out system paths (tag, search, topic, etc.)
&lt;/span&gt;            &lt;span class="n"&gt;system_paths&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="s"&gt;tag&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="s"&gt;tags&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="s"&gt;search&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="s"&gt;topic&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="s"&gt;topics&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
                            &lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="s"&gt;m&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="s"&gt;about&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="s"&gt;membership&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;
            &lt;span class="k"&gt;if&lt;/span&gt; &lt;span class="n"&gt;slug&lt;/span&gt; &lt;span class="ow"&gt;not&lt;/span&gt; &lt;span class="ow"&gt;in&lt;/span&gt; &lt;span class="n"&gt;system_paths&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;
                &lt;span class="n"&gt;publication&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;slug&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;replace&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="s"&gt;-&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="s"&gt; &lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="p"&gt;).&lt;/span&gt;&lt;span class="nf"&gt;title&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;

        &lt;span class="n"&gt;articles&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;append&lt;/span&gt;&lt;span class="p"&gt;({&lt;/span&gt;
            &lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="s"&gt;title&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;       &lt;span class="n"&gt;entry&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;title&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
            &lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="s"&gt;url&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;         &lt;span class="n"&gt;link&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
            &lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="s"&gt;publication&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="n"&gt;publication&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
        &lt;span class="p"&gt;})&lt;/span&gt;

    &lt;span class="k"&gt;return&lt;/span&gt; &lt;span class="n"&gt;articles&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;blockquote&gt;
&lt;p&gt;⚠️ Medium's RSS feed returns only the &lt;strong&gt;last 10 articles&lt;/strong&gt; by default. This is a limit set by Medium; no matter what your script does, it cannot pull more than 10 via RSS. If you want to show all your articles, you will need to look into scraping approaches.&lt;/p&gt;

&lt;p&gt;I do not yet have 10 published articles on Medium, so I have not integrated this into my own GitHub Profile README yet. 😁 I will update the repo once I cross 10 articles. The repo link is in the Demo section at the end.&lt;/p&gt;
&lt;/blockquote&gt;

&lt;h3&gt;
  
  
  4.3 Fetching dev.to Articles
&lt;/h3&gt;

&lt;p&gt;dev.to has an open REST API that requires no API key. Since it supports pagination, we can pull all articles with a &lt;code&gt;while&lt;/code&gt; loop:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight python"&gt;&lt;code&gt;&lt;span class="k"&gt;def&lt;/span&gt; &lt;span class="nf"&gt;fetch_devto_articles&lt;/span&gt;&lt;span class="p"&gt;():&lt;/span&gt;
    &lt;span class="n"&gt;page&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;articles&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="p"&gt;[]&lt;/span&gt;

    &lt;span class="k"&gt;while&lt;/span&gt; &lt;span class="bp"&gt;True&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;
        &lt;span class="n"&gt;url&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;
            &lt;span class="sa"&gt;f&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="s"&gt;https://dev.to/api/articles&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;
            &lt;span class="sa"&gt;f&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="s"&gt;?username=&lt;/span&gt;&lt;span class="si"&gt;{&lt;/span&gt;&lt;span class="n"&gt;DEVTO_USERNAME&lt;/span&gt;&lt;span class="si"&gt;}&lt;/span&gt;&lt;span class="s"&gt;&amp;amp;per_page=100&amp;amp;page=&lt;/span&gt;&lt;span class="si"&gt;{&lt;/span&gt;&lt;span class="n"&gt;page&lt;/span&gt;&lt;span class="si"&gt;}&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;
        &lt;span class="p"&gt;)&lt;/span&gt;
        &lt;span class="n"&gt;response&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;requests&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;get&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;url&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;timeout&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="mi"&gt;10&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;

        &lt;span class="k"&gt;if&lt;/span&gt; &lt;span class="n"&gt;response&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;status_code&lt;/span&gt; &lt;span class="o"&gt;!=&lt;/span&gt; &lt;span class="mi"&gt;200&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;
            &lt;span class="k"&gt;break&lt;/span&gt;

        &lt;span class="n"&gt;batch&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;response&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;json&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;
        &lt;span class="k"&gt;if&lt;/span&gt; &lt;span class="ow"&gt;not&lt;/span&gt; &lt;span class="n"&gt;batch&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;          &lt;span class="c1"&gt;# Empty page → no more data
&lt;/span&gt;            &lt;span class="k"&gt;break&lt;/span&gt;

        &lt;span class="k"&gt;for&lt;/span&gt; &lt;span class="n"&gt;item&lt;/span&gt; &lt;span class="ow"&gt;in&lt;/span&gt; &lt;span class="n"&gt;batch&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;
            &lt;span class="n"&gt;articles&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;append&lt;/span&gt;&lt;span class="p"&gt;({&lt;/span&gt;
                &lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="s"&gt;title&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="n"&gt;item&lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="s"&gt;title&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="p"&gt;],&lt;/span&gt;
                &lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="s"&gt;url&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;   &lt;span class="n"&gt;item&lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="s"&gt;url&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="p"&gt;],&lt;/span&gt;
            &lt;span class="p"&gt;})&lt;/span&gt;

        &lt;span class="n"&gt;page&lt;/span&gt; &lt;span class="o"&gt;+=&lt;/span&gt; &lt;span class="mi"&gt;1&lt;/span&gt;

    &lt;span class="k"&gt;return&lt;/span&gt; &lt;span class="n"&gt;articles&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;h3&gt;
  
  
  4.4 Building Markdown Rows
&lt;/h3&gt;



&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight python"&gt;&lt;code&gt;&lt;span class="k"&gt;def&lt;/span&gt; &lt;span class="nf"&gt;build_medium_rows&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;articles&lt;/span&gt;&lt;span class="p"&gt;):&lt;/span&gt;
    &lt;span class="k"&gt;if&lt;/span&gt; &lt;span class="ow"&gt;not&lt;/span&gt; &lt;span class="n"&gt;articles&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;
        &lt;span class="k"&gt;return&lt;/span&gt; &lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="s"&gt;_No articles found._&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;

    &lt;span class="n"&gt;rows&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="p"&gt;[]&lt;/span&gt;
    &lt;span class="k"&gt;for&lt;/span&gt; &lt;span class="n"&gt;a&lt;/span&gt; &lt;span class="ow"&gt;in&lt;/span&gt; &lt;span class="n"&gt;articles&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;
        &lt;span class="c1"&gt;# Show publication in italic parentheses if present
&lt;/span&gt;        &lt;span class="n"&gt;pub&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="sa"&gt;f&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="s"&gt; *(&lt;/span&gt;&lt;span class="si"&gt;{&lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="sh"&gt;'&lt;/span&gt;&lt;span class="s"&gt;publication&lt;/span&gt;&lt;span class="sh"&gt;'&lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt;&lt;span class="si"&gt;}&lt;/span&gt;&lt;span class="s"&gt;)*&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt; &lt;span class="k"&gt;if&lt;/span&gt; &lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;get&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="s"&gt;publication&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="k"&gt;else&lt;/span&gt; &lt;span class="sh"&gt;""&lt;/span&gt;
        &lt;span class="n"&gt;rows&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;append&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="sa"&gt;f&lt;/span&gt;&lt;span class="sh"&gt;'&lt;/span&gt;&lt;span class="s"&gt;- [&lt;/span&gt;&lt;span class="si"&gt;{&lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="s"&gt;title&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt;&lt;span class="si"&gt;}&lt;/span&gt;&lt;span class="s"&gt;](&lt;/span&gt;&lt;span class="si"&gt;{&lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="s"&gt;url&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt;&lt;span class="si"&gt;}&lt;/span&gt;&lt;span class="s"&gt;)&lt;/span&gt;&lt;span class="si"&gt;{&lt;/span&gt;&lt;span class="n"&gt;pub&lt;/span&gt;&lt;span class="si"&gt;}&lt;/span&gt;&lt;span class="sh"&gt;'&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;

    &lt;span class="k"&gt;return&lt;/span&gt; &lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="se"&gt;\n&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;join&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;rows&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;


&lt;span class="k"&gt;def&lt;/span&gt; &lt;span class="nf"&gt;build_devto_rows&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;articles&lt;/span&gt;&lt;span class="p"&gt;):&lt;/span&gt;
    &lt;span class="k"&gt;if&lt;/span&gt; &lt;span class="ow"&gt;not&lt;/span&gt; &lt;span class="n"&gt;articles&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;
        &lt;span class="k"&gt;return&lt;/span&gt; &lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="s"&gt;_No articles found._&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;

    &lt;span class="k"&gt;return&lt;/span&gt; &lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="se"&gt;\n&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;join&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;
        &lt;span class="sa"&gt;f&lt;/span&gt;&lt;span class="sh"&gt;'&lt;/span&gt;&lt;span class="s"&gt;- [&lt;/span&gt;&lt;span class="si"&gt;{&lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="s"&gt;title&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt;&lt;span class="si"&gt;}&lt;/span&gt;&lt;span class="s"&gt;](&lt;/span&gt;&lt;span class="si"&gt;{&lt;/span&gt;&lt;span class="n"&gt;a&lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="s"&gt;url&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt;&lt;span class="si"&gt;}&lt;/span&gt;&lt;span class="s"&gt;)&lt;/span&gt;&lt;span class="sh"&gt;'&lt;/span&gt; &lt;span class="k"&gt;for&lt;/span&gt; &lt;span class="n"&gt;a&lt;/span&gt; &lt;span class="ow"&gt;in&lt;/span&gt; &lt;span class="n"&gt;articles&lt;/span&gt;
    &lt;span class="p"&gt;)&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;h3&gt;
  
  
  4.5 Updating the README
&lt;/h3&gt;

&lt;p&gt;We use regex to find the block between the markers and replace it with the new content. The &lt;code&gt;re.DOTALL&lt;/code&gt; flag makes &lt;code&gt;.&lt;/code&gt; match newlines as well; without it, multi-line blocks are not captured.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight python"&gt;&lt;code&gt;&lt;span class="k"&gt;def&lt;/span&gt; &lt;span class="nf"&gt;replace_section&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;content&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;start_marker&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;end_marker&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;new_body&lt;/span&gt;&lt;span class="p"&gt;):&lt;/span&gt;
    &lt;span class="n"&gt;pattern&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;re&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;compile&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;
        &lt;span class="sa"&gt;rf&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="si"&gt;{&lt;/span&gt;&lt;span class="n"&gt;re&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;escape&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;start_marker&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="si"&gt;}&lt;/span&gt;&lt;span class="s"&gt;.*?&lt;/span&gt;&lt;span class="si"&gt;{&lt;/span&gt;&lt;span class="n"&gt;re&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;escape&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;end_marker&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="si"&gt;}&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
        &lt;span class="n"&gt;re&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;DOTALL&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
    &lt;span class="p"&gt;)&lt;/span&gt;
    &lt;span class="n"&gt;replacement&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="sa"&gt;f&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="si"&gt;{&lt;/span&gt;&lt;span class="n"&gt;start_marker&lt;/span&gt;&lt;span class="si"&gt;}&lt;/span&gt;&lt;span class="se"&gt;\n&lt;/span&gt;&lt;span class="si"&gt;{&lt;/span&gt;&lt;span class="n"&gt;new_body&lt;/span&gt;&lt;span class="si"&gt;}&lt;/span&gt;&lt;span class="se"&gt;\n&lt;/span&gt;&lt;span class="si"&gt;{&lt;/span&gt;&lt;span class="n"&gt;end_marker&lt;/span&gt;&lt;span class="si"&gt;}&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;
    &lt;span class="k"&gt;return&lt;/span&gt; &lt;span class="n"&gt;pattern&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;sub&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;replacement&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;content&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;


&lt;span class="k"&gt;def&lt;/span&gt; &lt;span class="nf"&gt;main&lt;/span&gt;&lt;span class="p"&gt;():&lt;/span&gt;
    &lt;span class="nf"&gt;print&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="s"&gt;📡 Fetching Medium articles...&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
    &lt;span class="n"&gt;medium_articles&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nf"&gt;fetch_medium_articles&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;
    &lt;span class="nf"&gt;print&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="sa"&gt;f&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="s"&gt;   ✅ &lt;/span&gt;&lt;span class="si"&gt;{&lt;/span&gt;&lt;span class="nf"&gt;len&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;medium_articles&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="si"&gt;}&lt;/span&gt;&lt;span class="s"&gt; articles fetched.&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;

    &lt;span class="nf"&gt;print&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="s"&gt;📡 Fetching dev.to articles...&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
    &lt;span class="n"&gt;devto_articles&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nf"&gt;fetch_devto_articles&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;
    &lt;span class="nf"&gt;print&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="sa"&gt;f&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="s"&gt;   ✅ &lt;/span&gt;&lt;span class="si"&gt;{&lt;/span&gt;&lt;span class="nf"&gt;len&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;devto_articles&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;&lt;span class="si"&gt;}&lt;/span&gt;&lt;span class="s"&gt; articles fetched.&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;

    &lt;span class="k"&gt;with&lt;/span&gt; &lt;span class="nf"&gt;open&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;README_PATH&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="s"&gt;r&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;encoding&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="s"&gt;utf-8&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="k"&gt;as&lt;/span&gt; &lt;span class="n"&gt;f&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;
        &lt;span class="n"&gt;content&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;f&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;read&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;

    &lt;span class="n"&gt;content&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nf"&gt;replace_section&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;
        &lt;span class="n"&gt;content&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;MEDIUM_START&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;MEDIUM_END&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="nf"&gt;build_medium_rows&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;medium_articles&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
    &lt;span class="p"&gt;)&lt;/span&gt;
    &lt;span class="n"&gt;content&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nf"&gt;replace_section&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;
        &lt;span class="n"&gt;content&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;DEVTO_START&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;DEVTO_END&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="nf"&gt;build_devto_rows&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;devto_articles&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
    &lt;span class="p"&gt;)&lt;/span&gt;

    &lt;span class="k"&gt;with&lt;/span&gt; &lt;span class="nf"&gt;open&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;README_PATH&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="s"&gt;w&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;encoding&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="s"&gt;utf-8&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="k"&gt;as&lt;/span&gt; &lt;span class="n"&gt;f&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;
        &lt;span class="n"&gt;f&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;write&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;content&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;

    &lt;span class="nf"&gt;print&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="s"&gt;✅ README.md updated successfully!&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;


&lt;span class="k"&gt;if&lt;/span&gt; &lt;span class="n"&gt;__name__&lt;/span&gt; &lt;span class="o"&gt;==&lt;/span&gt; &lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="s"&gt;__main__&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;
    &lt;span class="nf"&gt;main&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;






&lt;h2&gt;
  
  
  5. GitHub Actions Workflow File ⚙️
&lt;/h2&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.amazonaws.com%2Fuploads%2Farticles%2F776s4cr6nvjelxewzcm9.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.amazonaws.com%2Fuploads%2Farticles%2F776s4cr6nvjelxewzcm9.png" alt="GitHub Actions Workflow File Usage" width="800" height="446"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;The workflow file goes inside the &lt;code&gt;.github/workflows/&lt;/code&gt; folder. GitHub automatically scans this folder and treats YAML files as workflows.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;.github/
└── workflows/
    └── update-articles.yml
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;File contents:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight yaml"&gt;&lt;code&gt;&lt;span class="na"&gt;name&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;📝 Update Blog Articles&lt;/span&gt;

&lt;span class="na"&gt;on&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt;
  &lt;span class="na"&gt;schedule&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt;
    &lt;span class="pi"&gt;-&lt;/span&gt; &lt;span class="na"&gt;cron&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"&lt;/span&gt;&lt;span class="s"&gt;0&lt;/span&gt;&lt;span class="nv"&gt; &lt;/span&gt;&lt;span class="s"&gt;6&lt;/span&gt;&lt;span class="nv"&gt; &lt;/span&gt;&lt;span class="s"&gt;*&lt;/span&gt;&lt;span class="nv"&gt; &lt;/span&gt;&lt;span class="s"&gt;*&lt;/span&gt;&lt;span class="nv"&gt; &lt;/span&gt;&lt;span class="s"&gt;*"&lt;/span&gt;   &lt;span class="c1"&gt;# Every day at 06:00 UTC&lt;/span&gt;
  &lt;span class="na"&gt;workflow_dispatch&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt;        &lt;span class="c1"&gt;# For manual triggering from the Actions tab&lt;/span&gt;

&lt;span class="na"&gt;jobs&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt;
  &lt;span class="na"&gt;update-readme&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt;
    &lt;span class="na"&gt;name&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;Fetch &amp;amp; Update Articles&lt;/span&gt;
    &lt;span class="na"&gt;runs-on&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;ubuntu-latest&lt;/span&gt;

    &lt;span class="na"&gt;steps&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt;
      &lt;span class="pi"&gt;-&lt;/span&gt; &lt;span class="na"&gt;name&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;🔄 Checkout Repository&lt;/span&gt;
        &lt;span class="na"&gt;uses&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;actions/checkout@v4&lt;/span&gt;

      &lt;span class="pi"&gt;-&lt;/span&gt; &lt;span class="na"&gt;name&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;🐍 Set up Python&lt;/span&gt;
        &lt;span class="na"&gt;uses&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;actions/setup-python@v5&lt;/span&gt;
        &lt;span class="na"&gt;with&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt;
          &lt;span class="na"&gt;python-version&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s2"&gt;"&lt;/span&gt;&lt;span class="s"&gt;3.11"&lt;/span&gt;

      &lt;span class="pi"&gt;-&lt;/span&gt; &lt;span class="na"&gt;name&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;📦 Install Dependencies&lt;/span&gt;
        &lt;span class="na"&gt;run&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;pip install requests feedparser&lt;/span&gt;

      &lt;span class="pi"&gt;-&lt;/span&gt; &lt;span class="na"&gt;name&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;🚀 Run Article Fetcher&lt;/span&gt;
        &lt;span class="na"&gt;run&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;python scripts/fetch_articles.py&lt;/span&gt;

      &lt;span class="pi"&gt;-&lt;/span&gt; &lt;span class="na"&gt;name&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="s"&gt;💾 Commit &amp;amp; Push Changes&lt;/span&gt;
        &lt;span class="na"&gt;run&lt;/span&gt;&lt;span class="pi"&gt;:&lt;/span&gt; &lt;span class="pi"&gt;|&lt;/span&gt;
          &lt;span class="s"&gt;git config --local user.email "github-actions[bot]@users.noreply.github.com"&lt;/span&gt;
          &lt;span class="s"&gt;git config --local user.name "github-actions[bot]"&lt;/span&gt;
          &lt;span class="s"&gt;git add README.md&lt;/span&gt;
          &lt;span class="s"&gt;git diff --staged --quiet || git commit -m "📝 Auto-update: Latest blog articles [$(date +'%Y-%m-%d')]"&lt;/span&gt;
          &lt;span class="s"&gt;git push&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;&lt;code&gt;actions/checkout@v4&lt;/code&gt; -- Copies your repo to the virtual machine (ubuntu-latest) where the workflow runs. Without it the script cannot find README.md.&lt;/p&gt;

&lt;p&gt;&lt;code&gt;actions/setup-python@v5&lt;/code&gt; -- Sets up the Python 3.11 environment. Even though GitHub Actions machines come with Python pre-installed, pinning the version is safer.&lt;/p&gt;

&lt;p&gt;&lt;code&gt;pip install requests feedparser&lt;/code&gt; -- Installs the two dependencies.&lt;/p&gt;

&lt;p&gt;&lt;code&gt;python scripts/fetch_articles.py&lt;/code&gt; -- Runs the script. This step updates README.md but does not commit yet.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Commit &amp;amp; Push step&lt;/strong&gt; -- The critical line is:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight shell"&gt;&lt;code&gt;git diff &lt;span class="nt"&gt;--staged&lt;/span&gt; &lt;span class="nt"&gt;--quiet&lt;/span&gt; &lt;span class="o"&gt;||&lt;/span&gt; git commit &lt;span class="nt"&gt;-m&lt;/span&gt; &lt;span class="s2"&gt;"..."&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;&lt;code&gt;git diff --staged --quiet&lt;/code&gt; returns a non-zero exit code when there are changes in the README; thanks to the &lt;code&gt;||&lt;/code&gt; operator, a commit is made only if there are changes, and nothing happens otherwise. Without this, an empty commit would be created on every run.&lt;/p&gt;

&lt;blockquote&gt;
&lt;p&gt;💡 &lt;strong&gt;Cron syntax:&lt;/strong&gt; &lt;code&gt;0 6 * * *&lt;/code&gt; means minute=0, hour=6, every day, every month, every day of the week. Keep in mind it uses UTC. For a different time, use &lt;a href="https://crontab.guru" rel="noopener noreferrer"&gt;crontab.guru&lt;/a&gt;.&lt;/p&gt;
&lt;/blockquote&gt;




&lt;h2&gt;
  
  
  6. Manual Triggering 🖱️
&lt;/h2&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.amazonaws.com%2Fuploads%2Farticles%2F3hvb3do7jngyhtequ67w.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.amazonaws.com%2Fuploads%2Farticles%2F3hvb3do7jngyhtequ67w.png" alt="Github Action Manuel trigger" width="800" height="446"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;The cron job runs every morning, but you might not want to wait after publishing a new article. The &lt;code&gt;workflow_dispatch&lt;/code&gt; trigger lets you run it whenever you want:&lt;/p&gt;

&lt;ol&gt;
&lt;li&gt;Go to your repository on GitHub&lt;/li&gt;
&lt;li&gt;Click the &lt;strong&gt;Actions&lt;/strong&gt; tab at the top&lt;/li&gt;
&lt;li&gt;Click &lt;strong&gt;📝 Update Blog Articles&lt;/strong&gt; in the left menu&lt;/li&gt;
&lt;li&gt;Click the &lt;strong&gt;Run workflow&lt;/strong&gt; button that appears on the right&lt;/li&gt;
&lt;li&gt;Click &lt;strong&gt;Run workflow&lt;/strong&gt; again in the dropdown that opens&lt;/li&gt;
&lt;/ol&gt;

&lt;p&gt;The workflow starts within a few seconds. A yellow spinning icon appears in the left menu; once it finishes it turns green ✅. When you look at your README, you will see the updated article list.&lt;/p&gt;




&lt;h2&gt;
  
  
  7. Demo 👀
&lt;/h2&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.amazonaws.com%2Fuploads%2Farticles%2Fldmcq11dzts6akf5bmqu.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.amazonaws.com%2Fuploads%2Farticles%2Fldmcq11dzts6akf5bmqu.png" alt="GitHub Profile README Demo" width="800" height="446"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;You can see a working example of the system described in this article on my own GitHub profile. Medium and dev.to articles update automatically every morning.&lt;/p&gt;

&lt;p&gt;👉 &lt;a href="https://github.com/yasinatesim" rel="noopener noreferrer"&gt;github.com/yasinatesim&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;The full source code, including &lt;code&gt;fetch_articles.py&lt;/code&gt; and &lt;code&gt;update-articles.yml&lt;/code&gt;, is available in the repo below:&lt;/p&gt;

&lt;p&gt;👉 &lt;a href="https://github.com/yasinatesim/yasinatesim" rel="noopener noreferrer"&gt;github.com/yasinatesim/yasinatesim&lt;/a&gt;&lt;/p&gt;




&lt;h2&gt;
  
  
  Feedback 📬
&lt;/h2&gt;

&lt;p&gt;While writing this article, I used &lt;strong&gt;Claude Opus 4.6 Thinking&lt;/strong&gt; for proofreading and research, and &lt;strong&gt;Gemini 3.1 Flash Image Preview (Nano Banana 2)&lt;/strong&gt; for generating the diagrams.&lt;/p&gt;

&lt;p&gt;Feedback, suggestions, and corrections are always welcome. You can reach me through the social media links on &lt;a href="https://yasinates.com" rel="noopener noreferrer"&gt;my website&lt;/a&gt; or on &lt;a href="https://linkedin.com/in/yasinatesim" rel="noopener noreferrer"&gt;LinkedIn&lt;/a&gt;.&lt;/p&gt;

&lt;p&gt;Best, Yasin 🤗&lt;/p&gt;




&lt;h2&gt;
  
  
  Resources 📚
&lt;/h2&gt;

&lt;h3&gt;
  
  
  Docs
&lt;/h3&gt;

&lt;ul&gt;
&lt;li&gt;&lt;a href="https://docs.github.com/en/actions/using-workflows/workflow-syntax-for-github-actions" rel="noopener noreferrer"&gt;GitHub Actions -- Workflow syntax&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://docs.github.com/en/actions/using-workflows/events-that-trigger-workflows" rel="noopener noreferrer"&gt;GitHub Actions -- Events (schedule, workflow_dispatch)&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://developers.forem.com/api" rel="noopener noreferrer"&gt;dev.to API Docs&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://feedparser.readthedocs.io/" rel="noopener noreferrer"&gt;feedparser Docs&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;

&lt;h3&gt;
  
  
  Tools
&lt;/h3&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;a href="https://crontab.guru" rel="noopener noreferrer"&gt;crontab.guru&lt;/a&gt; -- Visually test cron expressions&lt;/li&gt;
&lt;li&gt;
&lt;a href="https://docs.github.com/en/actions/security-guides/encrypted-secrets" rel="noopener noreferrer"&gt;GitHub Secrets Docs&lt;/a&gt; -- Store API keys securely&lt;/li&gt;
&lt;/ul&gt;

&lt;h3&gt;
  
  
  Inspiring README Examples
&lt;/h3&gt;

&lt;ul&gt;
&lt;li&gt;&lt;a href="https://github.com/abhisheknaiidu/awesome-github-profile-readme" rel="noopener noreferrer"&gt;awesome-github-profile-readme&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://github.com/anuraghazra/github-readme-stats" rel="noopener noreferrer"&gt;github-readme-stats&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://github.com/DenverCoder1/readme-typing-svg" rel="noopener noreferrer"&gt;readme-typing-svg&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;

</description>
      <category>github</category>
      <category>githubactions</category>
      <category>readme</category>
      <category>productivity</category>
    </item>
    <item>
      <title>Micro Frontend Architecture (with React Examples) 🧩</title>
      <dc:creator>Yasin ATEŞ</dc:creator>
      <pubDate>Sun, 08 Mar 2026 15:16:08 +0000</pubDate>
      <link>https://dev.to/yasinatesim/micro-frontend-architecture-with-react-examples-2b5h</link>
      <guid>https://dev.to/yasinatesim/micro-frontend-architecture-with-react-examples-2b5h</guid>
      <description>&lt;p&gt;As a product grows, so does the organization building it. Different business domains emerge, teams split up, and each team develops its own pace and priorities. But if the codebase stays in one piece, every small change requires coordination and every deployment affects the entire organization.&lt;/p&gt;

&lt;p&gt;That is where &lt;strong&gt;Micro Frontend&lt;/strong&gt; comes in.&lt;/p&gt;

&lt;p&gt;In this article I will explain micro frontend architecture from the ground up. Instead of handing you a ready-made library list, I wanted to explain &lt;strong&gt;the underlying logic&lt;/strong&gt;. The examples are written in React, but the architectural principles I cover (isolation, event bus, integration approaches) can be applied with any framework. I chose React to show the full picture in one consistent language.&lt;/p&gt;

&lt;p&gt;I have a personal connection to this topic. At one of the companies I worked at, I had the chance to be a maintainer on an open-source micro frontend framework called &lt;a href="https://github.com/hepsiburada/VoltranJS" rel="noopener noreferrer"&gt;VoltranJS&lt;/a&gt;. That experience let me understand this architecture deeply, both in theory and in practice.&lt;/p&gt;




&lt;h2&gt;
  
  
  1. What Is Micro Frontend? 🤔
&lt;/h2&gt;

&lt;p&gt;&lt;strong&gt;Micro Frontend&lt;/strong&gt; is an architecture that breaks a large and complex frontend application into small pieces that can be developed independently, deployed independently, and updated without blocking each other. Each of these independent pieces is called a &lt;strong&gt;micro app&lt;/strong&gt;.&lt;/p&gt;

&lt;blockquote&gt;
&lt;p&gt;🎯 In short: what microservices do for the backend, Micro Frontend does for the frontend.&lt;/p&gt;
&lt;/blockquote&gt;

&lt;p&gt;Unlike backend microservices, however, micro apps share the same browser environment (same DOM, same &lt;code&gt;window&lt;/code&gt;, same &lt;code&gt;localStorage&lt;/code&gt;). Isolation does not come for free here; it must be provided deliberately.&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.amazonaws.com%2Fuploads%2Farticles%2F40qurr85d4e55gbi685y.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.amazonaws.com%2Fuploads%2Farticles%2F40qurr85d4e55gbi685y.png" alt="Image description 1" width="800" height="446"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;Consider an e-commerce site. Home page, product listing, product detail, cart, checkout -- these are all areas with different business logic, different requirements, and different rates of change. Micro frontend makes it possible for each of these areas to:&lt;/p&gt;

&lt;p&gt;★ Live in its own repository&lt;/p&gt;

&lt;p&gt;★ Have its own CI/CD pipeline&lt;/p&gt;

&lt;p&gt;★ Be deployed independently&lt;/p&gt;

&lt;p&gt;★ Use different technology stacks if desired&lt;/p&gt;

&lt;blockquote&gt;
&lt;p&gt;⚠️ &lt;strong&gt;The freedom to use different technology stacks is theoretical.&lt;/strong&gt; In practice, most successful micro frontend implementations standardize around a single main framework. I cover this in detail in Section 3 -- Disadvantages.&lt;/p&gt;
&lt;/blockquote&gt;




&lt;h2&gt;
  
  
  2. Monolith vs Micro Frontend 🆚
&lt;/h2&gt;



&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;┌─────────────────────────────────────────────┐
│           Single Large Frontend App         │
│  ┌────────┐  ┌──────────┐  ┌─────────────┐  │
│  │ Header │  │ Products │  │  Checkout   │  │
│  └────────┘  └──────────┘  └─────────────┘  │
│    One Repo -- One Deploy -- All Teams      │
└─────────────────────────────────────────────┘
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Problems that arise as a monolith grows:&lt;/p&gt;

&lt;p&gt;★ Every small change requires deploying the entire application&lt;/p&gt;

&lt;p&gt;★ Multiple teams working on the same codebase leads to constant merge conflicts&lt;/p&gt;

&lt;p&gt;★ Different teams' different speed requirements get squeezed into a single pipeline&lt;/p&gt;

&lt;p&gt;★ Modernizing legacy code forces an all-or-nothing decision&lt;/p&gt;

&lt;p&gt;★ One team's bug can bring down the entire application&lt;/p&gt;

&lt;p&gt;Micro frontend addresses these problems like this:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;┌──────────────┐  ┌───────────────┐  ┌────────────┐
│    Header    │  │   Products    │  │    Cart    │
│    Team A    │  │    Team B     │  │   Team C   │
│ Independent  │  │ Independent   │  │Independent │
│   Deploy     │  │   Deploy      │  │  Deploy    │
└──────────────┘  └───────────────┘  └────────────┘
        │                │                  │
        └────────────────┴──────────────────┘
                         │
               ┌──────────────────┐
               │     Main App     │
               └──────────────────┘
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;






&lt;h2&gt;
  
  
  3. Advantages and Disadvantages ⚖️
&lt;/h2&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.amazonaws.com%2Fuploads%2Farticles%2Fgojpwxxu454ynpocyiba.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.amazonaws.com%2Fuploads%2Farticles%2Fgojpwxxu454ynpocyiba.png" alt="Image description 2" width="800" height="446"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;h3&gt;
  
  
  3.1 Advantages
&lt;/h3&gt;

&lt;p&gt;★ &lt;strong&gt;Independent Deployment&lt;/strong&gt;&lt;br&gt;
Each team can ship their own micro app without waiting for other teams. A payment team's deployment does not affect the cart team's release schedule.&lt;/p&gt;

&lt;p&gt;★ &lt;strong&gt;Team Autonomy&lt;/strong&gt;&lt;br&gt;
Each team can make its own technology decisions. Onboarding gets easier; a new developer only needs to learn their own micro app, not the entire application.&lt;/p&gt;

&lt;p&gt;★ &lt;strong&gt;Fault Isolation&lt;/strong&gt;&lt;br&gt;
If a micro app crashes, error boundaries keep the others running. In a monolith, a single bug can bring down the whole page.&lt;/p&gt;

&lt;p&gt;★ &lt;strong&gt;Incremental Modernization&lt;/strong&gt;&lt;br&gt;
Instead of rewriting a legacy application all at once, you can migrate piece by piece to modern technology. Old pages keep working while new micro apps are added one by one.&lt;/p&gt;

&lt;p&gt;★ &lt;strong&gt;Parallel Development&lt;/strong&gt;&lt;br&gt;
Multiple teams can work on different micro apps at the same time, completing their sprints without blocking each other.&lt;/p&gt;

&lt;p&gt;★ &lt;strong&gt;Easy A/B Testing&lt;/strong&gt;&lt;br&gt;
You can run region-based or user-based tests simply by deploying a different version of the relevant micro app.&lt;/p&gt;
&lt;h3&gt;
  
  
  3.2 Disadvantages
&lt;/h3&gt;

&lt;p&gt;★ &lt;strong&gt;Increased Operational Complexity&lt;/strong&gt;&lt;br&gt;
Each micro app means a separate service: separate repo, separate CI/CD, separate monitoring. This overhead can be heavy for small teams.&lt;/p&gt;

&lt;p&gt;★ &lt;strong&gt;Initial Load Performance&lt;/strong&gt;&lt;br&gt;
Each micro app means a separate JavaScript bundle. HTTP/2 multiplexing reduces the multi-request problem, but total JavaScript parse and execution time still increases. A poorly configured dependency strategy can bloat the page.&lt;/p&gt;

&lt;p&gt;★ &lt;strong&gt;Design Inconsistency&lt;/strong&gt;&lt;br&gt;
If each team manages its own CSS, visual inconsistencies build up over time. A shared design system becomes mandatory.&lt;/p&gt;

&lt;p&gt;★ &lt;strong&gt;Test Complexity&lt;/strong&gt;&lt;br&gt;
Integration and end-to-end tests require keeping multiple services running at the same time.&lt;/p&gt;

&lt;p&gt;★ &lt;strong&gt;Dependency Conflicts&lt;/strong&gt;&lt;br&gt;
If different micro apps use incompatible library versions, two instances of the same library end up running in the browser simultaneously.&lt;/p&gt;

&lt;p&gt;★ &lt;strong&gt;Multiple Framework Cost&lt;/strong&gt;&lt;br&gt;
The freedom for each team to use its own framework is theoretical. In practice, each additional technology stack loads its own runtime (framework core ~40-50 kb + router ~15-20 kb + state library ~10-30 kb gzipped), developers cannot move between teams, the UI kit has to be written separately for each framework, and the test matrix multiplies. Most successful implementations standardize around a single main framework.&lt;/p&gt;

&lt;p&gt;★ &lt;strong&gt;Drawing Wrong Boundaries&lt;/strong&gt;&lt;br&gt;
If domain boundaries are drawn based on technology preferences rather than business requirements, unnecessary network requests and data duplication become inevitable. This is the most common structural mistake.&lt;/p&gt;


&lt;h2&gt;
  
  
  4. Core Concepts 🧱
&lt;/h2&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.amazonaws.com%2Fuploads%2Farticles%2Fkkilnd33bfzws4aebqr8.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.amazonaws.com%2Fuploads%2Farticles%2Fkkilnd33bfzws4aebqr8.png" alt="Image description 3" width="800" height="446"&gt;&lt;/a&gt;&lt;/p&gt;
&lt;h3&gt;
  
  
  4.1 Main App
&lt;/h3&gt;

&lt;p&gt;This is the shell of the micro frontend architecture -- the central structure that brings all other micro apps together. Routing, navigation, and shared layout live in this layer. Authentication and global state are typically managed here as well. The main app also takes on the &lt;strong&gt;orchestration&lt;/strong&gt; role, deciding how and where micro apps are composed. That composition can happen client-side, server-side, or at the edge.&lt;/p&gt;

&lt;p&gt;Some micro frontend resources also call this the "shell" or "container." I used "Main App" throughout this article to avoid confusion with other uses of those words in software. You will see "shell" in the code examples because that is the common directory naming convention.&lt;/p&gt;
&lt;h3&gt;
  
  
  4.2 Micro App
&lt;/h3&gt;

&lt;p&gt;A small frontend application responsible for a specific business domain, deployed independently. In Module Federation terminology it is also called a &lt;strong&gt;remote&lt;/strong&gt;.&lt;/p&gt;

&lt;blockquote&gt;
&lt;p&gt;💡 The word "remote" is heavily overloaded in software, so outside the Module Federation section I use "Micro App" throughout the article.&lt;/p&gt;
&lt;/blockquote&gt;
&lt;h3&gt;
  
  
  4.3 Routing
&lt;/h3&gt;

&lt;p&gt;The main app is responsible for unmounting the current micro app and mounting the new one when the route changes. There are two common patterns:&lt;/p&gt;

&lt;p&gt;★ &lt;strong&gt;Main-app-side routing:&lt;/strong&gt; All URL navigation is defined in the main app. The micro app only knows its mount point; it has no idea which URL it will be shown on. This provides centralized control and keeps micro apps fully isolated.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="c1"&gt;// shell/src/App.js -- main app&lt;/span&gt;
&lt;span class="k"&gt;import&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt; &lt;span class="nx"&gt;BrowserRouter&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="nx"&gt;Routes&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="nx"&gt;Route&lt;/span&gt; &lt;span class="p"&gt;}&lt;/span&gt; &lt;span class="k"&gt;from&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;react-router-dom&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
&lt;span class="k"&gt;import&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt; &lt;span class="nx"&gt;Suspense&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="nx"&gt;lazy&lt;/span&gt; &lt;span class="p"&gt;}&lt;/span&gt; &lt;span class="k"&gt;from&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;react&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;

&lt;span class="c1"&gt;// Micro apps are lazy-loaded (integration details in Section 7)&lt;/span&gt;
&lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;Home&lt;/span&gt;    &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nf"&gt;lazy&lt;/span&gt;&lt;span class="p"&gt;(()&lt;/span&gt; &lt;span class="o"&gt;=&amp;gt;&lt;/span&gt; &lt;span class="k"&gt;import&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;homeApp/Home&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;));&lt;/span&gt;
&lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;Catalog&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nf"&gt;lazy&lt;/span&gt;&lt;span class="p"&gt;(()&lt;/span&gt; &lt;span class="o"&gt;=&amp;gt;&lt;/span&gt; &lt;span class="k"&gt;import&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;catalogApp/Catalog&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;));&lt;/span&gt;
&lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;Cart&lt;/span&gt;    &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nf"&gt;lazy&lt;/span&gt;&lt;span class="p"&gt;(()&lt;/span&gt; &lt;span class="o"&gt;=&amp;gt;&lt;/span&gt; &lt;span class="k"&gt;import&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;cartApp/Cart&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;));&lt;/span&gt;

&lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;Fallback&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="p"&gt;({&lt;/span&gt; &lt;span class="nx"&gt;name&lt;/span&gt; &lt;span class="p"&gt;})&lt;/span&gt; &lt;span class="o"&gt;=&amp;gt;&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;
  &lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="nx"&gt;div&lt;/span&gt; &lt;span class="nx"&gt;className&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;mfe-skeleton&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="o"&gt;&amp;gt;&lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="nx"&gt;name&lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt; &lt;span class="nx"&gt;loading&lt;/span&gt;&lt;span class="p"&gt;...&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="sr"&gt;/div&lt;/span&gt;&lt;span class="err"&gt;&amp;gt;
&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;

&lt;span class="k"&gt;export&lt;/span&gt; &lt;span class="k"&gt;default&lt;/span&gt; &lt;span class="kd"&gt;function&lt;/span&gt; &lt;span class="nf"&gt;App&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
  &lt;span class="k"&gt;return &lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;
    &lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="nx"&gt;BrowserRouter&lt;/span&gt;&lt;span class="o"&gt;&amp;gt;&lt;/span&gt;
      &lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="nx"&gt;Routes&lt;/span&gt;&lt;span class="o"&gt;&amp;gt;&lt;/span&gt;
        &lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="nx"&gt;Route&lt;/span&gt; &lt;span class="nx"&gt;path&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;/&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt; &lt;span class="nx"&gt;element&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;
          &lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="nx"&gt;Suspense&lt;/span&gt; &lt;span class="nx"&gt;fallback&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="nx"&gt;Fallback&lt;/span&gt; &lt;span class="nx"&gt;name&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;Home&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt; &lt;span class="o"&gt;/&amp;gt;&lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="o"&gt;&amp;gt;&lt;/span&gt;
            &lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="nx"&gt;Home&lt;/span&gt; &lt;span class="o"&gt;/&amp;gt;&lt;/span&gt;
          &lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="sr"&gt;/Suspense&lt;/span&gt;&lt;span class="err"&gt;&amp;gt;
&lt;/span&gt;        &lt;span class="p"&gt;}&lt;/span&gt; &lt;span class="sr"&gt;/&lt;/span&gt;&lt;span class="err"&gt;&amp;gt;
&lt;/span&gt;        &lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="nx"&gt;Route&lt;/span&gt; &lt;span class="nx"&gt;path&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;/products/*&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt; &lt;span class="nx"&gt;element&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;
          &lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="nx"&gt;Suspense&lt;/span&gt; &lt;span class="nx"&gt;fallback&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="nx"&gt;Fallback&lt;/span&gt; &lt;span class="nx"&gt;name&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;Products&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt; &lt;span class="o"&gt;/&amp;gt;&lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="o"&gt;&amp;gt;&lt;/span&gt;
            &lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="nx"&gt;Catalog&lt;/span&gt; &lt;span class="o"&gt;/&amp;gt;&lt;/span&gt;
          &lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="sr"&gt;/Suspense&lt;/span&gt;&lt;span class="err"&gt;&amp;gt;
&lt;/span&gt;        &lt;span class="p"&gt;}&lt;/span&gt; &lt;span class="sr"&gt;/&lt;/span&gt;&lt;span class="err"&gt;&amp;gt;
&lt;/span&gt;        &lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="nx"&gt;Route&lt;/span&gt; &lt;span class="nx"&gt;path&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;/cart&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt; &lt;span class="nx"&gt;element&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;
          &lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="nx"&gt;Suspense&lt;/span&gt; &lt;span class="nx"&gt;fallback&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="nx"&gt;Fallback&lt;/span&gt; &lt;span class="nx"&gt;name&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;Cart&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt; &lt;span class="o"&gt;/&amp;gt;&lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="o"&gt;&amp;gt;&lt;/span&gt;
            &lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="nx"&gt;Cart&lt;/span&gt; &lt;span class="o"&gt;/&amp;gt;&lt;/span&gt;
          &lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="sr"&gt;/Suspense&lt;/span&gt;&lt;span class="err"&gt;&amp;gt;
&lt;/span&gt;        &lt;span class="p"&gt;}&lt;/span&gt; &lt;span class="sr"&gt;/&lt;/span&gt;&lt;span class="err"&gt;&amp;gt;
&lt;/span&gt;      &lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="sr"&gt;/Routes&lt;/span&gt;&lt;span class="err"&gt;&amp;gt;
&lt;/span&gt;    &lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="sr"&gt;/BrowserRouter&lt;/span&gt;&lt;span class="err"&gt;&amp;gt;
&lt;/span&gt;  &lt;span class="p"&gt;);&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;★ &lt;strong&gt;Micro-app-side routing:&lt;/strong&gt; The micro app manages its own internal navigation (for example, moving from a product list to a product detail page). The main app only knows which root URL to mount the micro app at; everything inside is the micro app's responsibility.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="c1"&gt;// catalog-micro-app/src/CatalogApp.js&lt;/span&gt;
&lt;span class="k"&gt;import&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt; &lt;span class="nx"&gt;Routes&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="nx"&gt;Route&lt;/span&gt; &lt;span class="p"&gt;}&lt;/span&gt; &lt;span class="k"&gt;from&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;react-router-dom&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
&lt;span class="k"&gt;import&lt;/span&gt; &lt;span class="nx"&gt;ProductList&lt;/span&gt; &lt;span class="k"&gt;from&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;./ProductList&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
&lt;span class="k"&gt;import&lt;/span&gt; &lt;span class="nx"&gt;ProductDetail&lt;/span&gt; &lt;span class="k"&gt;from&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;./ProductDetail&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;

&lt;span class="c1"&gt;// The main app mounts this micro app under "/products/*".&lt;/span&gt;
&lt;span class="c1"&gt;// The micro app manages its own nested routes.&lt;/span&gt;
&lt;span class="k"&gt;export&lt;/span&gt; &lt;span class="k"&gt;default&lt;/span&gt; &lt;span class="kd"&gt;function&lt;/span&gt; &lt;span class="nf"&gt;CatalogApp&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
  &lt;span class="k"&gt;return &lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;
    &lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="nx"&gt;Routes&lt;/span&gt;&lt;span class="o"&gt;&amp;gt;&lt;/span&gt;
      &lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="nx"&gt;Route&lt;/span&gt; &lt;span class="nx"&gt;index&lt;/span&gt; &lt;span class="nx"&gt;element&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="nx"&gt;ProductList&lt;/span&gt; &lt;span class="o"&gt;/&amp;gt;&lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt; &lt;span class="sr"&gt;/&lt;/span&gt;&lt;span class="err"&gt;&amp;gt;
&lt;/span&gt;      &lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="nx"&gt;Route&lt;/span&gt; &lt;span class="nx"&gt;path&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;:id&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt; &lt;span class="nx"&gt;element&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="nx"&gt;ProductDetail&lt;/span&gt; &lt;span class="o"&gt;/&amp;gt;&lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt; &lt;span class="sr"&gt;/&lt;/span&gt;&lt;span class="err"&gt;&amp;gt;
&lt;/span&gt;    &lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="sr"&gt;/Routes&lt;/span&gt;&lt;span class="err"&gt;&amp;gt;
&lt;/span&gt;  &lt;span class="p"&gt;);&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;blockquote&gt;
&lt;p&gt;💡 The two patterns are not mutually exclusive. The main app handles top-level routing (which micro app to show) while the micro app handles its own nested routes. Together, the flow looks like this:&lt;br&gt;
&lt;/p&gt;
&lt;/blockquote&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;URL: /products/abc-123

Main app routing (App.js):
  "/products/*" → mount &amp;lt;Catalog /&amp;gt; micro app

Micro app routing (CatalogApp.js):
  "/products/"       → &amp;lt;ProductList /&amp;gt;     (index route)
  "/products/:id"    → &amp;lt;ProductDetail /&amp;gt;   ← abc-123 matches here
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;The &lt;code&gt;"/products/*"&lt;/code&gt; wildcard in the main app lets the micro app recognize its own nested paths. The main app answers "which micro app," the micro app answers "which sub-page."&lt;/p&gt;




&lt;h2&gt;
  
  
  5. How Is Isolation Achieved? 🔒
&lt;/h2&gt;

&lt;p&gt;One of the most critical challenges in micro frontend is isolation: how do you prevent one micro app's CSS or JavaScript from overriding another's?&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.amazonaws.com%2Fuploads%2Farticles%2F4kc1eziwa6hw2cno15v3.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.amazonaws.com%2Fuploads%2Farticles%2F4kc1eziwa6hw2cno15v3.png" alt="Image description 4" width="800" height="446"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;h3&gt;
  
  
  5.1 CSS Isolation
&lt;/h3&gt;

&lt;p&gt;The browser's global CSS scope is shared by all micro apps. If the same class name is used in two different micro apps, one will override the other.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight css"&gt;&lt;code&gt;&lt;span class="nc"&gt;.container&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt; &lt;span class="nl"&gt;background&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="no"&gt;blue&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt; &lt;span class="p"&gt;}&lt;/span&gt;  &lt;span class="c"&gt;/* Micro App A */&lt;/span&gt;
&lt;span class="nc"&gt;.container&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt; &lt;span class="nl"&gt;background&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="no"&gt;red&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt; &lt;span class="p"&gt;}&lt;/span&gt;   &lt;span class="c"&gt;/* Micro App B -- overrides the rule above! */&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;The most practical and widespread solution is &lt;strong&gt;CSS Modules&lt;/strong&gt;. With CSS Modules you give the file a &lt;code&gt;.module.css&lt;/code&gt; extension, and at build time an automatic hash is added to every class name. So instead of &lt;code&gt;.container&lt;/code&gt; you get something like &lt;code&gt;.ProductList_container__3xMq2&lt;/code&gt;, making collisions impossible. &lt;strong&gt;SCSS Modules&lt;/strong&gt; use the same isolation mechanism (&lt;code&gt;.module.scss&lt;/code&gt; extension) and add SCSS features like variables, nesting, and mixins on top. I used SCSS Modules in the examples throughout this article.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight scss"&gt;&lt;code&gt;&lt;span class="cm"&gt;/* ProductList.module.scss */&lt;/span&gt;
&lt;span class="nc"&gt;.container&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
  &lt;span class="nl"&gt;padding&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="m"&gt;1rem&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
  &lt;span class="nl"&gt;border-radius&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="m"&gt;8px&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;

  &lt;span class="nc"&gt;.title&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="nl"&gt;font-size&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="m"&gt;1&lt;/span&gt;&lt;span class="mi"&gt;.5rem&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
    &lt;span class="nl"&gt;color&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="mh"&gt;#111827&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
  &lt;span class="p"&gt;}&lt;/span&gt;

  &lt;span class="k"&gt;&amp;amp;&lt;/span&gt;&lt;span class="nd"&gt;:hover&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt; &lt;span class="nl"&gt;background&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="mh"&gt;#f9fafb&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt; &lt;span class="p"&gt;}&lt;/span&gt;

  &lt;span class="nv"&gt;$primary&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="mh"&gt;#4f46e5&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;

  &lt;span class="nc"&gt;.badge&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="nl"&gt;background&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="nv"&gt;$primary&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
    &lt;span class="nl"&gt;color&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="no"&gt;white&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
    &lt;span class="nl"&gt;padding&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="m"&gt;2px&lt;/span&gt; &lt;span class="m"&gt;8px&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
    &lt;span class="nl"&gt;border-radius&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="m"&gt;999px&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
  &lt;span class="p"&gt;}&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;





&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="c1"&gt;// ProductList.js&lt;/span&gt;
&lt;span class="k"&gt;import&lt;/span&gt; &lt;span class="nx"&gt;styles&lt;/span&gt; &lt;span class="k"&gt;from&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;./ProductList.module.scss&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;

&lt;span class="kd"&gt;function&lt;/span&gt; &lt;span class="nf"&gt;ProductList&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
  &lt;span class="k"&gt;return &lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;
    &lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="nx"&gt;div&lt;/span&gt; &lt;span class="nx"&gt;className&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="nx"&gt;styles&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;container&lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="o"&gt;&amp;gt;&lt;/span&gt;
      &lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="nx"&gt;h2&lt;/span&gt; &lt;span class="nx"&gt;className&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="nx"&gt;styles&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;title&lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="o"&gt;&amp;gt;&lt;/span&gt;&lt;span class="nx"&gt;Products&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="sr"&gt;/h2&lt;/span&gt;&lt;span class="err"&gt;&amp;gt;
&lt;/span&gt;      &lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="nx"&gt;span&lt;/span&gt; &lt;span class="nx"&gt;className&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="nx"&gt;styles&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;badge&lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="o"&gt;&amp;gt;&lt;/span&gt;&lt;span class="nx"&gt;New&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="sr"&gt;/span&lt;/span&gt;&lt;span class="err"&gt;&amp;gt;
&lt;/span&gt;    &lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="sr"&gt;/div&lt;/span&gt;&lt;span class="err"&gt;&amp;gt;
&lt;/span&gt;  &lt;span class="p"&gt;);&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;span class="c1"&gt;// Rendered to DOM as: &amp;lt;div class="ProductList_container__3xMq2"&amp;gt;&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;blockquote&gt;
&lt;p&gt;💡 &lt;strong&gt;Alternative approaches:&lt;/strong&gt; CSS-in-JS libraries (styled-components, Emotion) or Shadow DOM also provide isolation. In a micro frontend context, though, SCSS Modules offer the lowest runtime cost and the broadest tooling compatibility.&lt;/p&gt;
&lt;/blockquote&gt;

&lt;h3&gt;
  
  
  5.2 JavaScript Isolation
&lt;/h3&gt;

&lt;p&gt;Global variables, properties on &lt;code&gt;window&lt;/code&gt;, and &lt;code&gt;localStorage&lt;/code&gt; are the most common sources of collisions.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="c1"&gt;// Micro App A&lt;/span&gt;
&lt;span class="nb"&gt;window&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;currentUser&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt; &lt;span class="na"&gt;id&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="na"&gt;name&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;Alice&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt; &lt;span class="p"&gt;};&lt;/span&gt;

&lt;span class="c1"&gt;// Micro App B overwrites Micro App A's data&lt;/span&gt;
&lt;span class="nb"&gt;window&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;currentUser&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt; &lt;span class="na"&gt;id&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="mi"&gt;2&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="na"&gt;name&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;Bob&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt; &lt;span class="p"&gt;};&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;The correct approach:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="nb"&gt;window&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;__MFE__&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nb"&gt;window&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;__MFE__&lt;/span&gt; &lt;span class="o"&gt;||&lt;/span&gt; &lt;span class="p"&gt;{};&lt;/span&gt;

&lt;span class="nb"&gt;window&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;__MFE__&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;header&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt; &lt;span class="na"&gt;currentUser&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt; &lt;span class="na"&gt;id&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="na"&gt;name&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;Alice&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt; &lt;span class="p"&gt;},&lt;/span&gt; &lt;span class="na"&gt;version&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;1.2.3&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt; &lt;span class="p"&gt;};&lt;/span&gt;
&lt;span class="nb"&gt;window&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;__MFE__&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;cart&lt;/span&gt;   &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt; &lt;span class="na"&gt;items&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;[],&lt;/span&gt; &lt;span class="na"&gt;total&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="mi"&gt;0&lt;/span&gt; &lt;span class="p"&gt;};&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;★ For &lt;code&gt;localStorage&lt;/code&gt;, use a prefix:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;PREFIX&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;mfe_header_&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
&lt;span class="nx"&gt;localStorage&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;setItem&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s2"&gt;`&lt;/span&gt;&lt;span class="p"&gt;${&lt;/span&gt;&lt;span class="nx"&gt;PREFIX&lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="s2"&gt;user`&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="nx"&gt;JSON&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;stringify&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;user&lt;/span&gt;&lt;span class="p"&gt;));&lt;/span&gt;
&lt;span class="nx"&gt;localStorage&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;getItem&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="s2"&gt;`&lt;/span&gt;&lt;span class="p"&gt;${&lt;/span&gt;&lt;span class="nx"&gt;PREFIX&lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="s2"&gt;user`&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;blockquote&gt;
&lt;p&gt;⚠️ A namespace is only a &lt;strong&gt;naming convention&lt;/strong&gt;; it is not enforced at runtime. Any micro app can still read or overwrite &lt;code&gt;window.__MFE__.cart&lt;/code&gt;. This approach works only when every team respects the convention.&lt;/p&gt;
&lt;/blockquote&gt;




&lt;h2&gt;
  
  
  6. Communication with Event Bus 📡
&lt;/h2&gt;

&lt;p&gt;Micro apps should not import each other directly; that creates coupling and breaks independent deployment. Communication should be &lt;strong&gt;event-based&lt;/strong&gt;. The &lt;code&gt;CustomEvent&lt;/code&gt; API on &lt;code&gt;window&lt;/code&gt; is all you need for this:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;bus&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
  &lt;span class="nf"&gt;emit&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;event&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="nx"&gt;data&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="nb"&gt;window&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;dispatchEvent&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="k"&gt;new&lt;/span&gt; &lt;span class="nc"&gt;CustomEvent&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;event&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt; &lt;span class="na"&gt;detail&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="nx"&gt;data&lt;/span&gt; &lt;span class="p"&gt;}));&lt;/span&gt;
  &lt;span class="p"&gt;},&lt;/span&gt;

  &lt;span class="nf"&gt;on&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;event&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="nx"&gt;handler&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="cm"&gt;/*
      wrapper:
        (1) extracts e.detail
        (2) stores the reference for cleanup
    */&lt;/span&gt;
    &lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;wrapper&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;e&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="o"&gt;=&amp;gt;&lt;/span&gt; &lt;span class="nf"&gt;handler&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;e&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;detail&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;

    &lt;span class="nb"&gt;window&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;addEventListener&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;event&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="nx"&gt;wrapper&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;
    &lt;span class="k"&gt;return &lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt; &lt;span class="o"&gt;=&amp;gt;&lt;/span&gt; &lt;span class="nb"&gt;window&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;removeEventListener&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;event&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="nx"&gt;wrapper&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt; &lt;span class="c1"&gt;// cleanup&lt;/span&gt;
  &lt;span class="p"&gt;},&lt;/span&gt;
&lt;span class="p"&gt;};&lt;/span&gt;

&lt;span class="k"&gt;export&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt; &lt;span class="nx"&gt;bus&lt;/span&gt; &lt;span class="p"&gt;};&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;You publish this package as &lt;code&gt;@org/event-bus&lt;/code&gt; in your private npm registry (GitHub Packages, npm org scope, Verdaccio, etc.). How the package is distributed to micro apps (Module Federation shared config, vendor CDN, etc.) depends on the integration approach you choose; I will cover those in Section 7.&lt;/p&gt;

&lt;p&gt;★ &lt;strong&gt;Why &lt;code&gt;CustomEvent&lt;/code&gt;?&lt;/strong&gt; &lt;/p&gt;

&lt;p&gt;Because it lives on &lt;code&gt;window&lt;/code&gt;, events emitted from different bundles naturally see each other on the same page. No extra instance-sharing is needed. When any micro app calls &lt;code&gt;bus.emit()&lt;/code&gt; from its own bundle, the &lt;code&gt;bus.on()&lt;/code&gt; listeners in other micro apps will catch it. Zero dependencies, native browser API.&lt;/p&gt;

&lt;h3&gt;
  
  
  6.1 Usage
&lt;/h3&gt;

&lt;blockquote&gt;
&lt;p&gt;💡 &lt;strong&gt;Naming convention:&lt;/strong&gt; The format &lt;code&gt;mfe:{microapp}:{action}&lt;/code&gt; is recommended. The &lt;code&gt;mfe:&lt;/code&gt; prefix prevents collisions (and typically matches the name of the micro frontend framework in use), the middle segment identifies the source, and the trailing segment describes the action.&lt;br&gt;
&lt;/p&gt;
&lt;/blockquote&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="c1"&gt;// ProductsApp.jsx&lt;/span&gt;
&lt;span class="k"&gt;import&lt;/span&gt; &lt;span class="nx"&gt;React&lt;/span&gt; &lt;span class="k"&gt;from&lt;/span&gt; &lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;react&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
&lt;span class="k"&gt;import&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt; &lt;span class="nx"&gt;bus&lt;/span&gt; &lt;span class="p"&gt;}&lt;/span&gt; &lt;span class="k"&gt;from&lt;/span&gt; &lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;@org/event-bus&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;

&lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;products&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="p"&gt;[&lt;/span&gt;
  &lt;span class="p"&gt;{&lt;/span&gt; &lt;span class="na"&gt;id&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="na"&gt;name&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;Keyboard&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="na"&gt;price&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="mi"&gt;500&lt;/span&gt; &lt;span class="p"&gt;},&lt;/span&gt;
  &lt;span class="p"&gt;{&lt;/span&gt; &lt;span class="na"&gt;id&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="mi"&gt;2&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="na"&gt;name&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;Mouse&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="na"&gt;price&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="mi"&gt;300&lt;/span&gt; &lt;span class="p"&gt;},&lt;/span&gt;
&lt;span class="p"&gt;];&lt;/span&gt;

&lt;span class="k"&gt;export&lt;/span&gt; &lt;span class="k"&gt;default&lt;/span&gt; &lt;span class="kd"&gt;function&lt;/span&gt; &lt;span class="nf"&gt;ProductsApp&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
  &lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;addToCart&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;product&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="o"&gt;=&amp;gt;&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;

    &lt;span class="c1"&gt;// ★ We are sending the product info&lt;/span&gt;
    &lt;span class="nx"&gt;bus&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;emit&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;mfe:cart:add&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
      &lt;span class="na"&gt;productId&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="nx"&gt;product&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;id&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
      &lt;span class="na"&gt;price&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="nx"&gt;product&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;price&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
      &lt;span class="na"&gt;quantity&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="mi"&gt;1&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
    &lt;span class="p"&gt;});&lt;/span&gt;
  &lt;span class="p"&gt;};&lt;/span&gt;

  &lt;span class="k"&gt;return &lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;
    &lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="nx"&gt;div&lt;/span&gt;&lt;span class="o"&gt;&amp;gt;&lt;/span&gt;
      &lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="nx"&gt;h2&lt;/span&gt;&lt;span class="o"&gt;&amp;gt;&lt;/span&gt;&lt;span class="nx"&gt;Products&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="sr"&gt;/h2&lt;/span&gt;&lt;span class="err"&gt;&amp;gt;
&lt;/span&gt;      &lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="nx"&gt;products&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;map&lt;/span&gt;&lt;span class="p"&gt;((&lt;/span&gt;&lt;span class="nx"&gt;product&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="o"&gt;=&amp;gt;&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;
        &lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="nx"&gt;div&lt;/span&gt; &lt;span class="nx"&gt;key&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="nx"&gt;product&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;id&lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="o"&gt;&amp;gt;&lt;/span&gt;
          &lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="nx"&gt;span&lt;/span&gt;&lt;span class="o"&gt;&amp;gt;&lt;/span&gt;
            &lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="nx"&gt;product&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;name&lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt; &lt;span class="o"&gt;-&lt;/span&gt; &lt;span class="nx"&gt;$&lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="nx"&gt;product&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;price&lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;
          &lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="sr"&gt;/span&lt;/span&gt;&lt;span class="err"&gt;&amp;gt;
&lt;/span&gt;          &lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="nx"&gt;button&lt;/span&gt; &lt;span class="nx"&gt;onClick&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="p"&gt;{()&lt;/span&gt; &lt;span class="o"&gt;=&amp;gt;&lt;/span&gt; &lt;span class="nf"&gt;addToCart&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;product&lt;/span&gt;&lt;span class="p"&gt;)}&lt;/span&gt;&lt;span class="o"&gt;&amp;gt;&lt;/span&gt;
            &lt;span class="nx"&gt;Add&lt;/span&gt; &lt;span class="nx"&gt;to&lt;/span&gt; &lt;span class="nx"&gt;Cart&lt;/span&gt;
          &lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="sr"&gt;/button&lt;/span&gt;&lt;span class="err"&gt;&amp;gt;
&lt;/span&gt;        &lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="sr"&gt;/div&lt;/span&gt;&lt;span class="err"&gt;&amp;gt;
&lt;/span&gt;      &lt;span class="p"&gt;))}&lt;/span&gt;
    &lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="sr"&gt;/div&lt;/span&gt;&lt;span class="err"&gt;&amp;gt;
&lt;/span&gt;  &lt;span class="p"&gt;);&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;





&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="c1"&gt;// CartApp.jsx&lt;/span&gt;
&lt;span class="k"&gt;import&lt;/span&gt; &lt;span class="nx"&gt;React&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt; &lt;span class="nx"&gt;useEffect&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="nx"&gt;useState&lt;/span&gt; &lt;span class="p"&gt;}&lt;/span&gt; &lt;span class="k"&gt;from&lt;/span&gt; &lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;react&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
&lt;span class="k"&gt;import&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt; &lt;span class="nx"&gt;bus&lt;/span&gt; &lt;span class="p"&gt;}&lt;/span&gt; &lt;span class="k"&gt;from&lt;/span&gt; &lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;@org/event-bus&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;

&lt;span class="k"&gt;export&lt;/span&gt; &lt;span class="k"&gt;default&lt;/span&gt; &lt;span class="kd"&gt;function&lt;/span&gt; &lt;span class="nf"&gt;CartApp&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
  &lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="nx"&gt;cartItems&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="nx"&gt;setCartItems&lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nf"&gt;useState&lt;/span&gt;&lt;span class="p"&gt;([]);&lt;/span&gt;

  &lt;span class="nf"&gt;useEffect&lt;/span&gt;&lt;span class="p"&gt;(()&lt;/span&gt; &lt;span class="o"&gt;=&amp;gt;&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;handleAddToCart&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;item&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="o"&gt;=&amp;gt;&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
      &lt;span class="nf"&gt;setCartItems&lt;/span&gt;&lt;span class="p"&gt;((&lt;/span&gt;&lt;span class="nx"&gt;prev&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="o"&gt;=&amp;gt;&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
        &lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;existing&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nx"&gt;prev&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;find&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;p&lt;/span&gt; &lt;span class="o"&gt;=&amp;gt;&lt;/span&gt; &lt;span class="nx"&gt;p&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;productId&lt;/span&gt; &lt;span class="o"&gt;===&lt;/span&gt; &lt;span class="nx"&gt;item&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;productId&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;

        &lt;span class="k"&gt;if &lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;existing&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
          &lt;span class="k"&gt;return&lt;/span&gt; &lt;span class="nx"&gt;prev&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;map&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;p&lt;/span&gt; &lt;span class="o"&gt;=&amp;gt;&lt;/span&gt;
            &lt;span class="nx"&gt;p&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;productId&lt;/span&gt; &lt;span class="o"&gt;===&lt;/span&gt; &lt;span class="nx"&gt;item&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;productId&lt;/span&gt;
              &lt;span class="p"&gt;?&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt; &lt;span class="p"&gt;...&lt;/span&gt;&lt;span class="nx"&gt;p&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="na"&gt;quantity&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="nx"&gt;p&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;quantity&lt;/span&gt; &lt;span class="o"&gt;+&lt;/span&gt; &lt;span class="mi"&gt;1&lt;/span&gt; &lt;span class="p"&gt;}&lt;/span&gt;
              &lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="nx"&gt;p&lt;/span&gt;
          &lt;span class="p"&gt;);&lt;/span&gt;
        &lt;span class="p"&gt;}&lt;/span&gt;

        &lt;span class="k"&gt;return&lt;/span&gt; &lt;span class="p"&gt;[...&lt;/span&gt;&lt;span class="nx"&gt;prev&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="nx"&gt;item&lt;/span&gt;&lt;span class="p"&gt;];&lt;/span&gt;
      &lt;span class="p"&gt;});&lt;/span&gt;
    &lt;span class="p"&gt;};&lt;/span&gt;

    &lt;span class="c1"&gt;// ★ We are receiving the product info sent from the other component and running cleanup&lt;/span&gt;

    &lt;span class="cm"&gt;/* This way:
      ✔ Listener is removed when the component unmounts
      ✔ No memory leaks
      ✔ Multiple mount/unmount cycles are safe
   */&lt;/span&gt;
    &lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;unsubscribe&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nx"&gt;bus&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;on&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;mfe:cart:add&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="nx"&gt;handleAddToCart&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;
    &lt;span class="k"&gt;return&lt;/span&gt; &lt;span class="nx"&gt;unsubscribe&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
  &lt;span class="p"&gt;},&lt;/span&gt; &lt;span class="p"&gt;[]);&lt;/span&gt;

  &lt;span class="k"&gt;return &lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;
    &lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="nx"&gt;div&lt;/span&gt;&lt;span class="o"&gt;&amp;gt;&lt;/span&gt;
      &lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="nx"&gt;h2&lt;/span&gt;&lt;span class="o"&gt;&amp;gt;&lt;/span&gt;&lt;span class="nx"&gt;Cart&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="sr"&gt;/h2&lt;/span&gt;&lt;span class="err"&gt;&amp;gt;
&lt;/span&gt;      &lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="nx"&gt;cartItems&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;map&lt;/span&gt;&lt;span class="p"&gt;((&lt;/span&gt;&lt;span class="nx"&gt;item&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="o"&gt;=&amp;gt;&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;
        &lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="nx"&gt;div&lt;/span&gt; &lt;span class="nx"&gt;key&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="nx"&gt;item&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;productId&lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="o"&gt;&amp;gt;&lt;/span&gt;
          &lt;span class="nx"&gt;Product&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="nx"&gt;item&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;productId&lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt; &lt;span class="o"&gt;|&lt;/span&gt;
          &lt;span class="nx"&gt;Quantity&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="nx"&gt;item&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;quantity&lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt; &lt;span class="o"&gt;|&lt;/span&gt;
          &lt;span class="nx"&gt;Price&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="nx"&gt;$&lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="nx"&gt;item&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;price&lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;
        &lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="sr"&gt;/div&lt;/span&gt;&lt;span class="err"&gt;&amp;gt;
&lt;/span&gt;      &lt;span class="p"&gt;))}&lt;/span&gt;
    &lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="sr"&gt;/div&lt;/span&gt;&lt;span class="err"&gt;&amp;gt;
&lt;/span&gt;  &lt;span class="p"&gt;);&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;h3&gt;
  
  
  6.2 Communication Scenarios
&lt;/h3&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.amazonaws.com%2Fuploads%2Farticles%2F0c6c9rgzmbwxn0hxr45e.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.amazonaws.com%2Fuploads%2Farticles%2F0c6c9rgzmbwxn0hxr45e.png" alt="Image description 5" width="800" height="446"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;** ★ Client to Client: Two micro apps on the same page communicate**&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="k"&gt;import&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt; &lt;span class="nx"&gt;bus&lt;/span&gt; &lt;span class="p"&gt;}&lt;/span&gt; &lt;span class="k"&gt;from&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;@org/event-bus&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;

&lt;span class="kd"&gt;function&lt;/span&gt; &lt;span class="nf"&gt;ProductCard&lt;/span&gt;&lt;span class="p"&gt;({&lt;/span&gt; &lt;span class="nx"&gt;product&lt;/span&gt; &lt;span class="p"&gt;})&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
  &lt;span class="k"&gt;return &lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;
    &lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="nx"&gt;button&lt;/span&gt; &lt;span class="nx"&gt;onClick&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="p"&gt;{()&lt;/span&gt; &lt;span class="o"&gt;=&amp;gt;&lt;/span&gt;
      &lt;span class="nx"&gt;bus&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;emit&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;mfe:cart:add&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt; &lt;span class="na"&gt;productId&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="nx"&gt;product&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;id&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="na"&gt;price&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="nx"&gt;product&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;price&lt;/span&gt; &lt;span class="p"&gt;})&lt;/span&gt;
    &lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="o"&gt;&amp;gt;&lt;/span&gt;
      &lt;span class="nx"&gt;Add&lt;/span&gt; &lt;span class="nx"&gt;to&lt;/span&gt; &lt;span class="nx"&gt;Cart&lt;/span&gt;
    &lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="sr"&gt;/button&lt;/span&gt;&lt;span class="err"&gt;&amp;gt;
&lt;/span&gt;  &lt;span class="p"&gt;);&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;** ★ Client to Server to Notification: Notifying other micro apps after a backend action**&lt;/p&gt;

&lt;p&gt;Sending a request to the server does not require the event bus; a standard &lt;code&gt;fetch&lt;/code&gt; is enough. But when &lt;strong&gt;the result needs to be broadcast to other micro apps&lt;/strong&gt;, that is where the event bus comes in:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="c1"&gt;// checkout micro app&lt;/span&gt;
&lt;span class="k"&gt;import&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt; &lt;span class="nx"&gt;bus&lt;/span&gt; &lt;span class="p"&gt;}&lt;/span&gt; &lt;span class="k"&gt;from&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;@org/event-bus&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;

&lt;span class="k"&gt;async&lt;/span&gt; &lt;span class="kd"&gt;function&lt;/span&gt; &lt;span class="nf"&gt;initiatePayment&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;cartId&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="nx"&gt;paymentMethod&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
  &lt;span class="c1"&gt;// Standard fetch request to the server&lt;/span&gt;
  &lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;res&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="k"&gt;await&lt;/span&gt; &lt;span class="nf"&gt;fetch&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;/api/checkout/initiate&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="na"&gt;method&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;POST&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
    &lt;span class="na"&gt;headers&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;Content-Type&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;application/json&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt; &lt;span class="p"&gt;},&lt;/span&gt;
    &lt;span class="na"&gt;body&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="nx"&gt;JSON&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;stringify&lt;/span&gt;&lt;span class="p"&gt;({&lt;/span&gt; &lt;span class="nx"&gt;cartId&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="nx"&gt;paymentMethod&lt;/span&gt; &lt;span class="p"&gt;}),&lt;/span&gt;
  &lt;span class="p"&gt;});&lt;/span&gt;
  &lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt; &lt;span class="nx"&gt;orderId&lt;/span&gt; &lt;span class="p"&gt;}&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="k"&gt;await&lt;/span&gt; &lt;span class="nx"&gt;res&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;json&lt;/span&gt;&lt;span class="p"&gt;();&lt;/span&gt;

  &lt;span class="c1"&gt;// Broadcast the result to other micro apps via event bus&lt;/span&gt;
  &lt;span class="nx"&gt;bus&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;emit&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;mfe:order:created&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt; &lt;span class="nx"&gt;orderId&lt;/span&gt; &lt;span class="p"&gt;});&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;






&lt;h2&gt;
  
  
  7. Integration Approaches 🔗
&lt;/h2&gt;

&lt;p&gt;There are multiple ways to compose micro apps together. Each has different strengths and weaknesses; choosing the right one depends on your project's needs.&lt;/p&gt;

&lt;h3&gt;
  
  
  7.1 Build-Time Integration
&lt;/h3&gt;

&lt;p&gt;Micro apps are published as npm packages, and the main app includes them in a single bundle at build time. The package being published here is the micro app itself -- all business logic, state, and API calls are embedded into the main app's build.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;Micro App A → npm publish → @org/header@1.2.3
Main App → npm install @org/header → build → deploy
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;★ Simple to set up&lt;/p&gt;

&lt;p&gt;★ The micro app cannot be updated without rebuilding the main app -- true independent deployment is not possible&lt;/p&gt;

&lt;h3&gt;
  
  
  7.2 Run-Time Client-Side Integration
&lt;/h3&gt;

&lt;p&gt;Micro apps are loaded dynamically at runtime in the browser. This can be done in two ways: &lt;strong&gt;the manual approach&lt;/strong&gt; and &lt;strong&gt;Module Federation&lt;/strong&gt;.&lt;/p&gt;

&lt;h4&gt;
  
  
  7.2.1 Manual Approach
&lt;/h4&gt;

&lt;p&gt;In its simplest form, each micro app's bundle is fetched from a CDN and mounted into the page:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="k"&gt;async&lt;/span&gt; &lt;span class="kd"&gt;function&lt;/span&gt; &lt;span class="nf"&gt;bootstrapApp&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
  &lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="p"&gt;[&lt;/span&gt;&lt;span class="nx"&gt;HeaderModule&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="nx"&gt;ProductsModule&lt;/span&gt;&lt;span class="p"&gt;]&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="k"&gt;await&lt;/span&gt; &lt;span class="nb"&gt;Promise&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;all&lt;/span&gt;&lt;span class="p"&gt;([&lt;/span&gt;
    &lt;span class="k"&gt;import&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;https://header.cdn.example.com/header.esm.js&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;),&lt;/span&gt;
    &lt;span class="k"&gt;import&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;https://products.cdn.example.com/products.esm.js&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;),&lt;/span&gt;
  &lt;span class="p"&gt;]);&lt;/span&gt;

  &lt;span class="nx"&gt;HeaderModule&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="k"&gt;default&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;mount&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nb"&gt;document&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;getElementById&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;header&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;));&lt;/span&gt;
  &lt;span class="nx"&gt;ProductsModule&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="k"&gt;default&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;mount&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nb"&gt;document&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;getElementById&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;products&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;));&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;★ Each micro app can be deployed completely independently&lt;/p&gt;

&lt;p&gt;★ Initial load time increases&lt;/p&gt;

&lt;p&gt;★ Dependency sharing (avoiding duplicate loading of common libraries like React) must be managed manually by the developer&lt;/p&gt;

&lt;p&gt;That manual management problem leads us to the shared dependency problem and Module Federation.&lt;/p&gt;

&lt;h4&gt;
  
  
  7.2.2 The Shared Dependency Problem
&lt;/h4&gt;

&lt;p&gt;If every micro app bundles its own copy of React and similar libraries, the user downloads the same code multiple times. This wastes bandwidth and causes two separate instances of the same library to run on the page at the same time.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;header.bundle.js    → React (~42kb gzipped) + own code (8kb)
products.bundle.js  → React (~42kb gzipped) + own code (15kb)
cart.bundle.js      → React (~42kb gzipped) + own code (6kb)
──────────────────────────────────────────────────────────────
3 copies loading, 2 of them unnecessary → 84kb wasted
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;** ★ Vendor Bundle Approach (Pre-Module Federation)**&lt;/p&gt;

&lt;p&gt;Before Module Federation, the common solution was to serve shared libraries as a single &lt;strong&gt;vendor bundle&lt;/strong&gt; (&lt;code&gt;vendor.js&lt;/code&gt;) from a CDN, and have micro apps use webpack's &lt;code&gt;externals&lt;/code&gt; config to exclude those libraries from their own bundles. The &lt;code&gt;externals&lt;/code&gt; setting tells webpack not to include a library in the bundle and instead read it from the global scope at runtime (for example &lt;code&gt;window.React&lt;/code&gt;):&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="c1"&gt;// Micro app webpack.config.js (pre-Module Federation approach)&lt;/span&gt;
&lt;span class="nx"&gt;module&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;exports&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
  &lt;span class="na"&gt;externals&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="na"&gt;react&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;React&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;           &lt;span class="c1"&gt;// import React → taken from window.React&lt;/span&gt;
    &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;react-dom&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;ReactDOM&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;  &lt;span class="c1"&gt;// import ReactDOM → taken from window.ReactDOM&lt;/span&gt;
  &lt;span class="p"&gt;},&lt;/span&gt;
&lt;span class="p"&gt;};&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;





&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight html"&gt;&lt;code&gt;&lt;span class="c"&gt;&amp;lt;!-- Main app layout -- loads vendor libraries into global scope --&amp;gt;&lt;/span&gt;
&lt;span class="nt"&gt;&amp;lt;script &lt;/span&gt;&lt;span class="na"&gt;src=&lt;/span&gt;&lt;span class="s"&gt;"https://cdn.example.com/vendor/react.18.2.0.min.js"&lt;/span&gt;&lt;span class="nt"&gt;&amp;gt;&amp;lt;/script&amp;gt;&lt;/span&gt;
&lt;span class="nt"&gt;&amp;lt;script &lt;/span&gt;&lt;span class="na"&gt;src=&lt;/span&gt;&lt;span class="s"&gt;"https://cdn.example.com/vendor/react-dom.18.2.0.min.js"&lt;/span&gt;&lt;span class="nt"&gt;&amp;gt;&amp;lt;/script&amp;gt;&lt;/span&gt;

&lt;span class="c"&gt;&amp;lt;!-- Micro app bundles no longer include React; they use window.React --&amp;gt;&lt;/span&gt;
&lt;span class="nt"&gt;&amp;lt;script &lt;/span&gt;&lt;span class="na"&gt;src=&lt;/span&gt;&lt;span class="s"&gt;"https://header.cdn.example.com/header.bundle.js"&lt;/span&gt;&lt;span class="nt"&gt;&amp;gt;&amp;lt;/script&amp;gt;&lt;/span&gt;
&lt;span class="nt"&gt;&amp;lt;script &lt;/span&gt;&lt;span class="na"&gt;src=&lt;/span&gt;&lt;span class="s"&gt;"https://products.cdn.example.com/products.bundle.js"&lt;/span&gt;&lt;span class="nt"&gt;&amp;gt;&amp;lt;/script&amp;gt;&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;This works, but management is manual: you have to centrally coordinate which library is used at which version. Module Federation automates this process.&lt;/p&gt;

&lt;h4&gt;
  
  
  7.2.3 Module Federation
&lt;/h4&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.amazonaws.com%2Fuploads%2Farticles%2Fqzykl2mrk7deki93c79q.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.amazonaws.com%2Fuploads%2Farticles%2Fqzykl2mrk7deki93c79q.png" alt="Image description 6" width="800" height="446"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;Module Federation, introduced with webpack 5, was the most game-changing innovation in the micro frontend world. It solves the dependency-sharing problem &lt;strong&gt;at runtime, at the webpack level&lt;/strong&gt;.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Main App (Host):&lt;/strong&gt; The central application that consumes modules from other applications. Called the &lt;strong&gt;"host"&lt;/strong&gt; in Module Federation terminology.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Remote (Micro App):&lt;/strong&gt; An independent application that exposes its own modules. Each remote produces a &lt;code&gt;remoteEntry.js&lt;/code&gt; file. This file works like a &lt;strong&gt;manifest&lt;/strong&gt;, declaring which modules the remote exposes and where their JavaScript files are located. The main app downloads this manifest first on page load, then requests the actual code for the needed modules on demand.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Shared:&lt;/strong&gt; Common dependencies. When marked with &lt;code&gt;singleton: true&lt;/code&gt;, only &lt;strong&gt;a single instance&lt;/strong&gt; of a library like React is guaranteed to load.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Remote Configuration:&lt;/strong&gt;&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="c1"&gt;// products-app/webpack.config.js (micro app)&lt;/span&gt;
&lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt; &lt;span class="nx"&gt;ModuleFederationPlugin&lt;/span&gt; &lt;span class="p"&gt;}&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nf"&gt;require&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;webpack&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;).&lt;/span&gt;&lt;span class="nx"&gt;container&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;

&lt;span class="nx"&gt;module&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;exports&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
  &lt;span class="na"&gt;output&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
    &lt;span class="na"&gt;publicPath&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;https://products.cdn.example.com/&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
  &lt;span class="p"&gt;},&lt;/span&gt;
  &lt;span class="na"&gt;plugins&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;[&lt;/span&gt;
    &lt;span class="k"&gt;new&lt;/span&gt; &lt;span class="nc"&gt;ModuleFederationPlugin&lt;/span&gt;&lt;span class="p"&gt;({&lt;/span&gt;
      &lt;span class="na"&gt;name&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;productsApp&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
      &lt;span class="na"&gt;filename&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;remoteEntry.js&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
      &lt;span class="na"&gt;exposes&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
        &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;./ProductList&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;   &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;./src/components/ProductList&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
        &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;./ProductDetail&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;./src/components/ProductDetail&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
      &lt;span class="p"&gt;},&lt;/span&gt;
      &lt;span class="na"&gt;shared&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
        &lt;span class="na"&gt;react&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;       &lt;span class="p"&gt;{&lt;/span&gt; &lt;span class="na"&gt;singleton&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="kc"&gt;true&lt;/span&gt; &lt;span class="p"&gt;},&lt;/span&gt;
        &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;react-dom&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt; &lt;span class="na"&gt;singleton&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="kc"&gt;true&lt;/span&gt; &lt;span class="p"&gt;},&lt;/span&gt;
      &lt;span class="p"&gt;},&lt;/span&gt;
    &lt;span class="p"&gt;}),&lt;/span&gt;
  &lt;span class="p"&gt;],&lt;/span&gt;
&lt;span class="p"&gt;};&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;&lt;strong&gt;Main App (Host) Configuration:&lt;/strong&gt;&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="c1"&gt;// shell-app/webpack.config.js (main app)&lt;/span&gt;
&lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt; &lt;span class="nx"&gt;ModuleFederationPlugin&lt;/span&gt; &lt;span class="p"&gt;}&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nf"&gt;require&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;webpack&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;).&lt;/span&gt;&lt;span class="nx"&gt;container&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;

&lt;span class="nx"&gt;module&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;exports&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
  &lt;span class="na"&gt;plugins&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;[&lt;/span&gt;
    &lt;span class="k"&gt;new&lt;/span&gt; &lt;span class="nc"&gt;ModuleFederationPlugin&lt;/span&gt;&lt;span class="p"&gt;({&lt;/span&gt;
      &lt;span class="na"&gt;name&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;shell&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
      &lt;span class="na"&gt;remotes&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
        &lt;span class="na"&gt;productsApp&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;productsApp@https://products.cdn.example.com/remoteEntry.js&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
        &lt;span class="na"&gt;cartApp&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;     &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;cartApp@https://cart.cdn.example.com/remoteEntry.js&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
        &lt;span class="na"&gt;headerApp&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;   &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;headerApp@https://header.cdn.example.com/remoteEntry.js&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
      &lt;span class="p"&gt;},&lt;/span&gt;
      &lt;span class="na"&gt;shared&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
        &lt;span class="na"&gt;react&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;       &lt;span class="p"&gt;{&lt;/span&gt; &lt;span class="na"&gt;singleton&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="kc"&gt;true&lt;/span&gt; &lt;span class="p"&gt;},&lt;/span&gt;
        &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;react-dom&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt; &lt;span class="na"&gt;singleton&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="kc"&gt;true&lt;/span&gt; &lt;span class="p"&gt;},&lt;/span&gt;
      &lt;span class="p"&gt;},&lt;/span&gt;
    &lt;span class="p"&gt;}),&lt;/span&gt;
  &lt;span class="p"&gt;],&lt;/span&gt;
&lt;span class="p"&gt;};&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;&lt;strong&gt;Using a Remote Module in the Main App:&lt;/strong&gt;&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="c1"&gt;// shell-app/src/App.js (main app)&lt;/span&gt;
&lt;span class="k"&gt;import&lt;/span&gt; &lt;span class="nx"&gt;React&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt; &lt;span class="nx"&gt;Suspense&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="nx"&gt;lazy&lt;/span&gt; &lt;span class="p"&gt;}&lt;/span&gt; &lt;span class="k"&gt;from&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;react&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;

&lt;span class="c1"&gt;// Remote modules are loaded with lazy import&lt;/span&gt;
&lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;ProductList&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nf"&gt;lazy&lt;/span&gt;&lt;span class="p"&gt;(()&lt;/span&gt; &lt;span class="o"&gt;=&amp;gt;&lt;/span&gt; &lt;span class="k"&gt;import&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;productsApp/ProductList&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;));&lt;/span&gt;
&lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;CartBadge&lt;/span&gt;   &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nf"&gt;lazy&lt;/span&gt;&lt;span class="p"&gt;(()&lt;/span&gt; &lt;span class="o"&gt;=&amp;gt;&lt;/span&gt; &lt;span class="k"&gt;import&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;cartApp/CartBadge&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;));&lt;/span&gt;
&lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;Header&lt;/span&gt;      &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nf"&gt;lazy&lt;/span&gt;&lt;span class="p"&gt;(()&lt;/span&gt; &lt;span class="o"&gt;=&amp;gt;&lt;/span&gt; &lt;span class="k"&gt;import&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;headerApp/Header&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;));&lt;/span&gt;

&lt;span class="kd"&gt;const&lt;/span&gt; &lt;span class="nx"&gt;Fallback&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="p"&gt;({&lt;/span&gt; &lt;span class="nx"&gt;name&lt;/span&gt; &lt;span class="p"&gt;})&lt;/span&gt; &lt;span class="o"&gt;=&amp;gt;&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;
  &lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="nx"&gt;div&lt;/span&gt; &lt;span class="nx"&gt;className&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;mfe-skeleton&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="o"&gt;&amp;gt;&lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="nx"&gt;name&lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt; &lt;span class="nx"&gt;loading&lt;/span&gt;&lt;span class="p"&gt;...&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="sr"&gt;/div&lt;/span&gt;&lt;span class="err"&gt;&amp;gt;
&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;

&lt;span class="k"&gt;export&lt;/span&gt; &lt;span class="k"&gt;default&lt;/span&gt; &lt;span class="kd"&gt;function&lt;/span&gt; &lt;span class="nf"&gt;App&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
  &lt;span class="k"&gt;return &lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;
    &lt;span class="o"&gt;&amp;lt;&amp;gt;&lt;/span&gt;
      &lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="nx"&gt;Suspense&lt;/span&gt; &lt;span class="nx"&gt;fallback&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="nx"&gt;Fallback&lt;/span&gt; &lt;span class="nx"&gt;name&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;Header&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt; &lt;span class="o"&gt;/&amp;gt;&lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="o"&gt;&amp;gt;&lt;/span&gt;
        &lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="nx"&gt;Header&lt;/span&gt; &lt;span class="o"&gt;/&amp;gt;&lt;/span&gt;
      &lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="sr"&gt;/Suspense&lt;/span&gt;&lt;span class="err"&gt;&amp;gt;
&lt;/span&gt;
      &lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="nx"&gt;main&lt;/span&gt;&lt;span class="o"&gt;&amp;gt;&lt;/span&gt;
        &lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="nx"&gt;Suspense&lt;/span&gt; &lt;span class="nx"&gt;fallback&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="nx"&gt;Fallback&lt;/span&gt; &lt;span class="nx"&gt;name&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;Products&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt; &lt;span class="o"&gt;/&amp;gt;&lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="o"&gt;&amp;gt;&lt;/span&gt;
          &lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="nx"&gt;ProductList&lt;/span&gt; &lt;span class="o"&gt;/&amp;gt;&lt;/span&gt;
        &lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="sr"&gt;/Suspense&lt;/span&gt;&lt;span class="err"&gt;&amp;gt;
&lt;/span&gt;      &lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="sr"&gt;/main&lt;/span&gt;&lt;span class="err"&gt;&amp;gt;
&lt;/span&gt;
      &lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="nx"&gt;Suspense&lt;/span&gt; &lt;span class="nx"&gt;fallback&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="nx"&gt;Fallback&lt;/span&gt; &lt;span class="nx"&gt;name&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;Cart&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt; &lt;span class="o"&gt;/&amp;gt;&lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="o"&gt;&amp;gt;&lt;/span&gt;
        &lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="nx"&gt;CartBadge&lt;/span&gt; &lt;span class="o"&gt;/&amp;gt;&lt;/span&gt;
      &lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="sr"&gt;/Suspense&lt;/span&gt;&lt;span class="err"&gt;&amp;gt;
&lt;/span&gt;    &lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="sr"&gt;/&lt;/span&gt;&lt;span class="err"&gt;&amp;gt;
&lt;/span&gt;  &lt;span class="p"&gt;);&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;When remote modules are wrapped with &lt;code&gt;lazy&lt;/code&gt;, the &lt;code&gt;Suspense&lt;/code&gt; fallback is shown while loading. Once the remote's JavaScript is downloaded, the actual component renders.&lt;/p&gt;

&lt;blockquote&gt;
&lt;p&gt;As of 2024, Module Federation has evolved into an independent project (&lt;a href="https://github.com/module-federation/core" rel="noopener noreferrer"&gt;module-federation/core&lt;/a&gt;) that can be used with bundlers beyond webpack.&lt;/p&gt;
&lt;/blockquote&gt;

&lt;h3&gt;
  
  
  7.3 Which Approach Should You Choose?
&lt;/h3&gt;

&lt;p&gt;★ &lt;strong&gt;Build-time integration&lt;/strong&gt; is the simplest to set up and type safety comes naturally, but it cannot provide independent deployment. The main app has to be rebuilt with every update. It can work for small teams or rarely-changing micro apps, but it becomes a bottleneck as you scale.&lt;/p&gt;

&lt;p&gt;★ &lt;strong&gt;Manual client-side integration&lt;/strong&gt; offers independent deployment; each micro app is served from its own CDN and loaded at runtime. However, dependency sharing is entirely the developer's responsibility -- you have to manually coordinate &lt;code&gt;externals&lt;/code&gt; and CDN settings to prevent duplicate loading of libraries like React. Initial load time also increases.&lt;/p&gt;

&lt;p&gt;★ &lt;strong&gt;Module Federation&lt;/strong&gt; offers the same runtime independence while automating dependency sharing. &lt;code&gt;singleton: true&lt;/code&gt; guarantees that shared libraries load only once. It works with webpack and, increasingly, with other bundlers.&lt;/p&gt;




&lt;h2&gt;
  
  
  8. Design System Management 🎨
&lt;/h2&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.amazonaws.com%2Fuploads%2Farticles%2Flqf2y14xxjn0n65nyqx5.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.amazonaws.com%2Fuploads%2Farticles%2Flqf2y14xxjn0n65nyqx5.png" alt="Image description 7" width="800" height="446"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;When multiple teams work independently, buttons end up different colors, spacing becomes inconsistent, and typography standards drift.&lt;/p&gt;

&lt;p&gt;The solution is straightforward: a shared &lt;strong&gt;design system&lt;/strong&gt;.&lt;/p&gt;

&lt;h3&gt;
  
  
  8.1 CSS Variables (Custom Properties): Single Source of Truth
&lt;/h3&gt;

&lt;p&gt;Defining design decisions (color, spacing, typography, border radius) as CSS custom properties is the simplest way to maintain consistency across all micro apps. Instead of hardcoding values in CSS, micro apps read from these variables:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight css"&gt;&lt;code&gt;&lt;span class="c"&gt;/* @org/design-system/variables.css */&lt;/span&gt;
&lt;span class="nd"&gt;:root&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
  &lt;span class="py"&gt;--color-primary&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;       &lt;span class="m"&gt;#4F46E5&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
  &lt;span class="py"&gt;--color-primary-hover&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="m"&gt;#4338CA&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
  &lt;span class="py"&gt;--color-success&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;       &lt;span class="m"&gt;#10B981&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
  &lt;span class="py"&gt;--color-danger&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;        &lt;span class="m"&gt;#EF4444&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
  &lt;span class="py"&gt;--color-text&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;          &lt;span class="m"&gt;#111827&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
  &lt;span class="py"&gt;--color-text-muted&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;    &lt;span class="m"&gt;#6B7280&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
  &lt;span class="py"&gt;--color-bg&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;            &lt;span class="m"&gt;#FFFFFF&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
  &lt;span class="py"&gt;--color-bg-secondary&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;  &lt;span class="m"&gt;#F9FAFB&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
  &lt;span class="py"&gt;--color-border&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;        &lt;span class="m"&gt;#E5E7EB&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;

  &lt;span class="py"&gt;--space-xs&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="m"&gt;0.25rem&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
  &lt;span class="py"&gt;--space-sm&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="m"&gt;0.5rem&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
  &lt;span class="py"&gt;--space-md&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="m"&gt;1rem&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
  &lt;span class="py"&gt;--space-lg&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="m"&gt;1.5rem&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
  &lt;span class="py"&gt;--space-xl&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="m"&gt;2rem&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;

  &lt;span class="py"&gt;--font-family&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;    &lt;span class="s2"&gt;'Inter'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;system-ui&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="nb"&gt;sans-serif&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
  &lt;span class="py"&gt;--font-size-sm&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;   &lt;span class="m"&gt;0.875rem&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
  &lt;span class="py"&gt;--font-size-base&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="m"&gt;1rem&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
  &lt;span class="py"&gt;--font-size-lg&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;   &lt;span class="m"&gt;1.25rem&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
  &lt;span class="py"&gt;--font-size-xl&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;   &lt;span class="m"&gt;1.5rem&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;

  &lt;span class="py"&gt;--radius-sm&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;   &lt;span class="m"&gt;4px&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
  &lt;span class="py"&gt;--radius-md&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;   &lt;span class="m"&gt;8px&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
  &lt;span class="py"&gt;--radius-lg&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;   &lt;span class="m"&gt;12px&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
  &lt;span class="py"&gt;--radius-full&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="m"&gt;999px&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;

  &lt;span class="py"&gt;--color-skeleton&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;      &lt;span class="m"&gt;#F0F0F0&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
  &lt;span class="py"&gt;--color-skeleton-wave&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="m"&gt;#E0E0E0&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;





&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight scss"&gt;&lt;code&gt;&lt;span class="cm"&gt;/* products-micro-app/ProductCard.module.scss */&lt;/span&gt;
&lt;span class="nc"&gt;.card&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
  &lt;span class="nl"&gt;background&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;    &lt;span class="nf"&gt;var&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="o"&gt;--&lt;/span&gt;&lt;span class="n"&gt;color-bg&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;
  &lt;span class="nl"&gt;border&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;        &lt;span class="m"&gt;1px&lt;/span&gt; &lt;span class="nb"&gt;solid&lt;/span&gt; &lt;span class="nf"&gt;var&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="o"&gt;--&lt;/span&gt;&lt;span class="n"&gt;color-border&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;
  &lt;span class="nl"&gt;border-radius&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="nf"&gt;var&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="o"&gt;--&lt;/span&gt;&lt;span class="n"&gt;radius-md&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;
  &lt;span class="nl"&gt;padding&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;       &lt;span class="nf"&gt;var&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="o"&gt;--&lt;/span&gt;&lt;span class="n"&gt;space-md&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;

  &lt;span class="nc"&gt;.title&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt; &lt;span class="nl"&gt;font-size&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="nf"&gt;var&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="o"&gt;--&lt;/span&gt;&lt;span class="n"&gt;font-size-lg&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;  &lt;span class="nl"&gt;color&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="nf"&gt;var&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="o"&gt;--&lt;/span&gt;&lt;span class="n"&gt;color-text&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt; &lt;span class="p"&gt;}&lt;/span&gt;
  &lt;span class="nc"&gt;.price&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt; &lt;span class="nl"&gt;color&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="nf"&gt;var&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="o"&gt;--&lt;/span&gt;&lt;span class="n"&gt;color-primary&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt;     &lt;span class="nl"&gt;font-size&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="nf"&gt;var&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="o"&gt;--&lt;/span&gt;&lt;span class="n"&gt;font-size-xl&lt;/span&gt;&lt;span class="p"&gt;);&lt;/span&gt; &lt;span class="p"&gt;}&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;The advantage of this approach: when a brand color changes, you update only the variables file, and all micro apps automatically pick up the new values.&lt;/p&gt;

&lt;h3&gt;
  
  
  8.2 Shared UI Kit: npm Package
&lt;/h3&gt;

&lt;p&gt;Beyond variables, shared components (Button, Input, Modal, Card) are published as an npm package. Micro apps add it as a dependency. What is shared here as an npm package is strictly &lt;strong&gt;presentational components&lt;/strong&gt; with no business logic; the micro apps themselves continue to be deployed independently.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight javascript"&gt;&lt;code&gt;&lt;span class="c1"&gt;// products micro app&lt;/span&gt;
&lt;span class="k"&gt;import&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt; &lt;span class="nx"&gt;Button&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="nx"&gt;Card&lt;/span&gt; &lt;span class="p"&gt;}&lt;/span&gt; &lt;span class="k"&gt;from&lt;/span&gt; &lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="s1"&gt;@org/ui-kit&lt;/span&gt;&lt;span class="dl"&gt;'&lt;/span&gt;&lt;span class="p"&gt;;&lt;/span&gt;

&lt;span class="kd"&gt;function&lt;/span&gt; &lt;span class="nf"&gt;ProductCard&lt;/span&gt;&lt;span class="p"&gt;({&lt;/span&gt; &lt;span class="nx"&gt;product&lt;/span&gt; &lt;span class="p"&gt;})&lt;/span&gt; &lt;span class="p"&gt;{&lt;/span&gt;
  &lt;span class="k"&gt;return &lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;
    &lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="nx"&gt;Card&lt;/span&gt; &lt;span class="nx"&gt;padding&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;md&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt; &lt;span class="nx"&gt;bordered&lt;/span&gt;&lt;span class="o"&gt;&amp;gt;&lt;/span&gt;
      &lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="nx"&gt;h3&lt;/span&gt;&lt;span class="o"&gt;&amp;gt;&lt;/span&gt;&lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="nx"&gt;product&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nx"&gt;name&lt;/span&gt;&lt;span class="p"&gt;}&lt;/span&gt;&lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="sr"&gt;/h3&lt;/span&gt;&lt;span class="err"&gt;&amp;gt;
&lt;/span&gt;      &lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="nx"&gt;Button&lt;/span&gt; &lt;span class="nx"&gt;variant&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt;&lt;span class="s2"&gt;primary&lt;/span&gt;&lt;span class="dl"&gt;"&lt;/span&gt; &lt;span class="nx"&gt;onClick&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="p"&gt;{()&lt;/span&gt; &lt;span class="o"&gt;=&amp;gt;&lt;/span&gt; &lt;span class="nf"&gt;addToCart&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nx"&gt;product&lt;/span&gt;&lt;span class="p"&gt;)}&lt;/span&gt;&lt;span class="o"&gt;&amp;gt;&lt;/span&gt;
        &lt;span class="nx"&gt;Add&lt;/span&gt; &lt;span class="nx"&gt;to&lt;/span&gt; &lt;span class="nx"&gt;Cart&lt;/span&gt;
      &lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="sr"&gt;/Button&lt;/span&gt;&lt;span class="err"&gt;&amp;gt;
&lt;/span&gt;    &lt;span class="o"&gt;&amp;lt;&lt;/span&gt;&lt;span class="sr"&gt;/Card&lt;/span&gt;&lt;span class="err"&gt;&amp;gt;
&lt;/span&gt;  &lt;span class="p"&gt;);&lt;/span&gt;
&lt;span class="p"&gt;}&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;The UI kit is managed with semantic versioning. For minor updates (adding a new component), micro apps can upgrade at their own pace. For major updates (breaking changes), all teams should be given a reasonable migration window.&lt;/p&gt;

&lt;blockquote&gt;
&lt;p&gt;💡 The approach that works best in practice: load CSS variables in the layout, distribute the UI kit as an npm package, and give all teams 2-3 sprints for major version migrations.&lt;/p&gt;
&lt;/blockquote&gt;




&lt;h2&gt;
  
  
  9. When to Use It, When Not To 🤓
&lt;/h2&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.amazonaws.com%2Fuploads%2Farticles%2Flaiky9jrrdxnuy8zqm1f.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.amazonaws.com%2Fuploads%2Farticles%2Flaiky9jrrdxnuy8zqm1f.png" alt="Image description 8" width="800" height="446"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;The core question that determines whether to adopt micro frontend is: &lt;strong&gt;Are your teams' business domains sufficiently separated?&lt;/strong&gt;&lt;/p&gt;

&lt;p&gt;Based on my experience and common industry patterns, micro frontend starts delivering value when there are multiple independent teams with clear domain separation. There is no hard number, but for single-team or very small organizations, the operational overhead typically outweighs the benefits.&lt;/p&gt;

&lt;h3&gt;
  
  
  9.1 When Micro Frontend Is a Good Fit
&lt;/h3&gt;

&lt;p&gt;★ There are clear boundaries between different business domains (checkout, catalog, search, account) managed by separate teams&lt;/p&gt;

&lt;p&gt;★ Teams have started blocking each other's deployments&lt;/p&gt;

&lt;p&gt;★ Different areas have significantly different rates of change&lt;/p&gt;

&lt;p&gt;★ A large legacy application needs to be modernized piece by piece&lt;/p&gt;

&lt;p&gt;★ A/B tests need to run frequently and independently in a specific area of the page&lt;/p&gt;

&lt;p&gt;★ Teams want full ownership of their own release schedule&lt;/p&gt;

&lt;h3&gt;
  
  
  9.2 When Micro Frontend Is Not a Good Fit
&lt;/h3&gt;

&lt;p&gt;★ The application is still in a growth phase and domain boundaries are not yet clear; wrongly drawn boundaries will create large refactoring costs later&lt;/p&gt;

&lt;p&gt;★ Teams are still making decisions together on every feature; architecture alone does not solve organizational problems&lt;/p&gt;

&lt;p&gt;★ The goal is shipping a fast MVP; product first, architecture second&lt;/p&gt;

&lt;p&gt;★ Performance and bundle size are the primary constraints; every additional micro app adds overhead&lt;/p&gt;

&lt;p&gt;★ Developer experience and local setup complexity cannot be tolerated&lt;/p&gt;




&lt;h2&gt;
  
  
  What Is Next? 🗺️
&lt;/h2&gt;

&lt;p&gt;This article covered the core concepts of micro frontend architecture, integration approaches, and the key things to watch out for. If you want to keep exploring, here are some topics worth looking into:&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Server-Side Integration and Hydration&lt;/strong&gt;&lt;br&gt;
Rendering micro apps on the server, composing the layout server-side, and making it interactive on the client (hydration). SSR and CSR micro apps coexisting on the same page, graceful degradation strategies, and resolving hydration mismatch issues.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Performance and Monitoring&lt;/strong&gt;&lt;br&gt;
Per-micro-app Core Web Vitals measurement and reporting. Error boundaries to keep a crashing micro app from affecting others. Skeleton placeholders to prevent Cumulative Layout Shift. Above-the-fold/below-the-fold lazy loading. Critical CSS inlining. INP (Interaction to Next Paint) measurement and optimization per micro app.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Local Development Experience&lt;/strong&gt;&lt;br&gt;
Day-to-day development in a micro frontend setup: running a micro app in standalone mode, testing main app integration with mock micro apps, full environment setup with Docker Compose. The answer to: "Do I really have to spin up 10 services just to work on my own micro app?"&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Micro Frontend with Next.js&lt;/strong&gt;&lt;br&gt;
How Next.js's App Router, Server Components, and built-in SSR capabilities combine with micro frontend architecture. Module Federation's Next.js integration (&lt;code&gt;@module-federation/nextjs-mf&lt;/code&gt;), page-based micro app separation, and using Next.js's own middleware layer as the main app.&lt;/p&gt;




&lt;h2&gt;
  
  
  Feedback 📬
&lt;/h2&gt;

&lt;p&gt;While writing this article, I used &lt;strong&gt;Claude Opus 4.6 Thinking&lt;/strong&gt; for proofreading, my own notes from my time as a &lt;a href="https://github.com/hepsiburada/VoltranJS" rel="noopener noreferrer"&gt;VoltranJS&lt;/a&gt; maintainer combined with &lt;strong&gt;ChatGPT 5.2's deep research feature&lt;/strong&gt; for sourcing and research, and &lt;strong&gt;Gemini 3 Pro Image Preview 2k (Nano Banana Pro)&lt;/strong&gt; for generating the diagrams.&lt;/p&gt;

&lt;p&gt;Feedback, suggestions, and corrections are always welcome. You can reach me through the social media links on &lt;a href="https://yasinates.com" rel="noopener noreferrer"&gt;my website&lt;/a&gt; or on &lt;a href="https://linkedin.com/in/yasinates" rel="noopener noreferrer"&gt;LinkedIn&lt;/a&gt;.&lt;/p&gt;

&lt;p&gt;Take care, Yasin 🤗&lt;/p&gt;




&lt;h2&gt;
  
  
  Resources 📚
&lt;/h2&gt;

&lt;h3&gt;
  
  
  Open Source Repos
&lt;/h3&gt;

&lt;ul&gt;
&lt;li&gt;&lt;a href="https://github.com/verdaccio/verdaccio" rel="noopener noreferrer"&gt;https://github.com/verdaccio/verdaccio&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://github.com/hepsiburada/VoltranJS" rel="noopener noreferrer"&gt;https://github.com/hepsiburada/VoltranJS&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://github.com/puzzle-js/puzzle-js" rel="noopener noreferrer"&gt;https://github.com/puzzle-js/puzzle-js&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://github.com/single-spa/single-spa" rel="noopener noreferrer"&gt;https://github.com/single-spa/single-spa&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://github.com/umijs/qiankun" rel="noopener noreferrer"&gt;https://github.com/umijs/qiankun&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://github.com/modern-js-dev/garfish" rel="noopener noreferrer"&gt;https://github.com/modern-js-dev/garfish&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://github.com/namecheap/ilc" rel="noopener noreferrer"&gt;https://github.com/namecheap/ilc&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://github.com/smapiot/piral" rel="noopener noreferrer"&gt;https://github.com/smapiot/piral&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://github.com/SAP/luigi" rel="noopener noreferrer"&gt;https://github.com/SAP/luigi&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://github.com/zalando/tailor" rel="noopener noreferrer"&gt;https://github.com/zalando/tailor&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://github.com/americanexpress/one-app" rel="noopener noreferrer"&gt;https://github.com/americanexpress/one-app&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://github.com/opencomponents/oc" rel="noopener noreferrer"&gt;https://github.com/opencomponents/oc&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://github.com/module-federation/core" rel="noopener noreferrer"&gt;https://github.com/module-federation/core&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://github.com/module-federation/module-federation-examples" rel="noopener noreferrer"&gt;https://github.com/module-federation/module-federation-examples&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://github.com/systemjs/systemjs" rel="noopener noreferrer"&gt;https://github.com/systemjs/systemjs&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://github.com/chrisdavies/eev" rel="noopener noreferrer"&gt;https://github.com/chrisdavies/eev&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://github.com/developit/mitt" rel="noopener noreferrer"&gt;https://github.com/developit/mitt&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://github.com/originjs/vite-plugin-federation" rel="noopener noreferrer"&gt;https://github.com/originjs/vite-plugin-federation&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://github.com/react-microfrontends" rel="noopener noreferrer"&gt;https://github.com/react-microfrontends&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://github.com/vue-microfrontends" rel="noopener noreferrer"&gt;https://github.com/vue-microfrontends&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://github.com/neuland/micro-frontends" rel="noopener noreferrer"&gt;https://github.com/neuland/micro-frontends&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://github.com/rajasegar/awesome-micro-frontends" rel="noopener noreferrer"&gt;https://github.com/rajasegar/awesome-micro-frontends&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;

&lt;h3&gt;
  
  
  Articles and Docs
&lt;/h3&gt;

&lt;ul&gt;
&lt;li&gt;&lt;a href="https://martinfowler.com/articles/micro-frontends.html" rel="noopener noreferrer"&gt;https://martinfowler.com/articles/micro-frontends.html&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://micro-frontends.org/" rel="noopener noreferrer"&gt;https://micro-frontends.org/&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://www.thoughtworks.com/radar/techniques/micro-frontends" rel="noopener noreferrer"&gt;https://www.thoughtworks.com/radar/techniques/micro-frontends&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://medium.com/swlh/webpack-5-module-federation-a-game-changer-to-javascript-architecture-bcdd30e02669" rel="noopener noreferrer"&gt;https://medium.com/swlh/webpack-5-module-federation-a-game-changer-to-javascript-architecture-bcdd30e02669&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://medium.com/hepsiburadatech/hepsiburada-micro-frontend-d%C3%B6n%C3%BC%C5%9F%C3%BCm%C3%BC-4c2f26b8dcae" rel="noopener noreferrer"&gt;https://medium.com/hepsiburadatech/hepsiburada-micro-frontend-d%C3%B6n%C3%BC%C5%9F%C3%BCm%C3%BC-4c2f26b8dcae&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://medium.com/frontend-development-with-js/scalable-frontend-geli%C5%9Ftirmelerinde-micro-frontend-yakla%C5%9F%C4%B1mlar%C4%B1-framework-ve-pluginler-8d0e5773c34f" rel="noopener noreferrer"&gt;https://medium.com/frontend-development-with-js/scalable-frontend-geli%C5%9Ftirmelerinde-micro-frontend-yakla%C5%9F%C4%B1mlar%C4%B1-framework-ve-pluginler-8d0e5773c34f&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://www.slideshare.net/slideshow/hepsiburada-micro-frontends-dnm/229602398" rel="noopener noreferrer"&gt;https://www.slideshare.net/slideshow/hepsiburada-micro-frontends-dnm/229602398&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://single-spa.js.org/docs/getting-started-overview" rel="noopener noreferrer"&gt;https://single-spa.js.org/docs/getting-started-overview&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://webpack.js.org/concepts/module-federation/" rel="noopener noreferrer"&gt;https://webpack.js.org/concepts/module-federation/&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://blog.scottlogic.com/2021/02/17/probably-dont-need-microfrontends.html" rel="noopener noreferrer"&gt;https://blog.scottlogic.com/2021/02/17/probably-dont-need-microfrontends.html&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://newsletter.systemdesign.one/p/micro-frontends" rel="noopener noreferrer"&gt;https://newsletter.systemdesign.one/p/micro-frontends&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://allegro.tech/2016/03/Managing-Frontend-in-the-microservices-architecture.html" rel="noopener noreferrer"&gt;https://allegro.tech/2016/03/Managing-Frontend-in-the-microservices-architecture.html&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://engineering.hellofresh.com/front-end-microservices-at-hellofresh-23978a611b87" rel="noopener noreferrer"&gt;https://engineering.hellofresh.com/front-end-microservices-at-hellofresh-23978a611b87&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://www.infoq.com/news/2018/08/experiences-micro-frontends/" rel="noopener noreferrer"&gt;https://www.infoq.com/news/2018/08/experiences-micro-frontends/&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://www.upwork.com/blog/2017/05/modernizing-upwork-micro-frontends/" rel="noopener noreferrer"&gt;https://www.upwork.com/blog/2017/05/modernizing-upwork-micro-frontends/&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;

&lt;h3&gt;
  
  
  Books
&lt;/h3&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;em&gt;Micro Frontends in Action&lt;/em&gt; -- &lt;a href="https://www.manning.com/books/micro-frontends-in-action" rel="noopener noreferrer"&gt;https://www.manning.com/books/micro-frontends-in-action&lt;/a&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;em&gt;Building Micro-Frontends&lt;/em&gt; -- &lt;a href="https://www.buildingmicrofrontends.com/" rel="noopener noreferrer"&gt;https://www.buildingmicrofrontends.com/&lt;/a&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;em&gt;The Art of Micro Frontends&lt;/em&gt; -- &lt;a href="https://www.packtpub.com/product/the-art-of-micro-frontends/9781800563568" rel="noopener noreferrer"&gt;https://www.packtpub.com/product/the-art-of-micro-frontends/9781800563568&lt;/a&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;em&gt;Practical Module Federation&lt;/em&gt; -- &lt;a href="https://module-federation.myshopify.com/products/practical-module-federation" rel="noopener noreferrer"&gt;https://module-federation.myshopify.com/products/practical-module-federation&lt;/a&gt;
&lt;/li&gt;
&lt;/ul&gt;

&lt;h3&gt;
  
  
  Courses
&lt;/h3&gt;

&lt;ul&gt;
&lt;li&gt;&lt;a href="https://www.udemy.com/course/microfrontend-course/" rel="noopener noreferrer"&gt;https://www.udemy.com/course/microfrontend-course/&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://www.pluralsight.com/courses/micro-frontends-architecture" rel="noopener noreferrer"&gt;https://www.pluralsight.com/courses/micro-frontends-architecture&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://www.freecodecamp.org/news/learn-all-about-micro-frontends/" rel="noopener noreferrer"&gt;https://www.freecodecamp.org/news/learn-all-about-micro-frontends/&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;

&lt;h3&gt;
  
  
  Podcasts
&lt;/h3&gt;

&lt;ul&gt;
&lt;li&gt;&lt;a href="https://softwareengineeringdaily.com/2022/02/14/micro-frontends-with-luca-mezzalira/" rel="noopener noreferrer"&gt;https://softwareengineeringdaily.com/2022/02/14/micro-frontends-with-luca-mezzalira/&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://www.se-radio.net/2020/08/episode-422-michael-geers-on-micro-frontends/" rel="noopener noreferrer"&gt;https://www.se-radio.net/2020/08/episode-422-michael-geers-on-micro-frontends/&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://changelog.com/jsparty/121" rel="noopener noreferrer"&gt;https://changelog.com/jsparty/121&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://www.thoughtworks.com/podcasts/micro-frontends" rel="noopener noreferrer"&gt;https://www.thoughtworks.com/podcasts/micro-frontends&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;

</description>
      <category>react</category>
      <category>microfrontend</category>
      <category>javascript</category>
      <category>architecture</category>
    </item>
    <item>
      <title>yasinates.com is coming soon 😋</title>
      <dc:creator>Yasin ATEŞ</dc:creator>
      <pubDate>Sun, 21 Jun 2020 08:47:06 +0000</pubDate>
      <link>https://dev.to/yasinatesim/yasinates-com-is-coming-soon-50od</link>
      <guid>https://dev.to/yasinatesim/yasinates-com-is-coming-soon-50od</guid>
      <description>&lt;p&gt;Hello everyone 😀, this is my first post. &lt;/p&gt;

&lt;p&gt;I will share the English of my articles on &lt;a href="https://medium.com/@yasinatesim/"&gt;medium.com&lt;/a&gt; here.&lt;/p&gt;

&lt;p&gt;I create the data on my website using the DEV API, medium.com API, and Github API services 😎&lt;/p&gt;

&lt;p&gt;I will write my next article is about the publishing process of my website.&lt;/p&gt;

&lt;p&gt;Hope to see you in new articles. 👋 👋&lt;/p&gt;

&lt;p&gt;My medium profile: &lt;a href="https://medium.com/@yasinatesim/"&gt;medium.com/@yasinatesim/&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;My personal website: &lt;a href="http://yasinates.com/"&gt;yasinates.com&lt;/a&gt;&lt;/p&gt;

</description>
    </item>
  </channel>
</rss>
