<?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: Nathan Chung</title>
    <description>The latest articles on DEV Community by Nathan Chung (@nchung_than).</description>
    <link>https://dev.to/nchung_than</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%2F3076848%2Fc56c7287-1782-473d-8eea-6217ad287e41.jpg</url>
      <title>DEV Community: Nathan Chung</title>
      <link>https://dev.to/nchung_than</link>
    </image>
    <atom:link rel="self" type="application/rss+xml" href="https://dev.to/feed/nchung_than"/>
    <language>en</language>
    <item>
      <title>How to Structure a React Project in 2025: Clean, Scalable, and Practical</title>
      <dc:creator>Nathan Chung</dc:creator>
      <pubDate>Fri, 13 Jun 2025 01:37:00 +0000</pubDate>
      <link>https://dev.to/algo_sync/how-to-structure-a-react-project-in-2025-clean-scalable-and-practical-15j6</link>
      <guid>https://dev.to/algo_sync/how-to-structure-a-react-project-in-2025-clean-scalable-and-practical-15j6</guid>
      <description>&lt;p&gt;How should you organize a React project?&lt;br&gt;&lt;br&gt;
Have you ever asked yourself that question when starting a new React app? Whether it’s a tiny side project or a big production app, I’m pretty sure we’ve all wondered: “What’s the best way to structure this so it looks clean and scales well later?”&lt;/p&gt;

&lt;p&gt;Well, here’s the truth: There’s &lt;strong&gt;no official standard&lt;/strong&gt;. Since React is just a &lt;strong&gt;library&lt;/strong&gt;, not a full-blown framework, it doesn’t force you into any specific folder structure or project layout.&lt;/p&gt;

&lt;p&gt;That’s why in this post, I’ll be sharing what’s worked for me, based on personal experience and a lot of research. Hopefully, it’ll give you a solid starting point to organize your own React projects in a clean and scalable way.&lt;/p&gt;


&lt;h2&gt;
  
  
  🧠 The Philosophy: Structure Based on Scale
&lt;/h2&gt;

&lt;p&gt;First, let me clarify this:&lt;br&gt;&lt;br&gt;
A React project should be structured based on &lt;strong&gt;the size of the app&lt;/strong&gt; and &lt;strong&gt;its complexity&lt;/strong&gt;. The bigger the project, the more important it becomes to separate concerns, reuse logic, and isolate features.&lt;/p&gt;

&lt;p&gt;So, here’s a &lt;strong&gt;general structure&lt;/strong&gt; I recommend for most small-to-medium React projects, with explanations for each folder:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;src/
├── assets/
├── components/
├── pages/
├── routes/
├── hooks/
├── services/
├── utils/
├── contexts/
├── styles/
├── App.jsx
├── main.jsx
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Let’s go through each of them.&lt;/p&gt;




&lt;h2&gt;
  
  
  📁 &lt;code&gt;assets/&lt;/code&gt; – Static Files &amp;amp; Media
&lt;/h2&gt;

&lt;p&gt;This folder contains &lt;strong&gt;static resources&lt;/strong&gt; such as:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Images&lt;/li&gt;
&lt;li&gt;Fonts&lt;/li&gt;
&lt;li&gt;Icons&lt;/li&gt;
&lt;li&gt;Global SCSS/CSS files&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;Use this for anything that doesn't contain logic, just visual or media assets.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;assets/
├── images/
├── fonts/
├── styles/
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;






&lt;h2&gt;
  
  
  📁 &lt;code&gt;components/&lt;/code&gt; – Shared UI Components
&lt;/h2&gt;

&lt;p&gt;This is for &lt;strong&gt;reusable components&lt;/strong&gt; like buttons, modals, inputs, etc., that are used across multiple parts of your app.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;components/
├── Button/
│ ├── Button.jsx
│ └── Button.module.css
├── Modal/
│ ├── Modal.jsx
│ └── Modal.module.css
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;






&lt;h2&gt;
  
  
  📁 &lt;code&gt;pages/&lt;/code&gt; – Route-Level Components
&lt;/h2&gt;

&lt;p&gt;Each file here corresponds to a route in your app. Think of it as the &lt;strong&gt;screen-level UI&lt;/strong&gt;. &lt;/p&gt;

&lt;p&gt;This helps separate page layout logic from reusable UI pieces.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;pages/
├── Home.jsx
├── Login.jsx
├── PostDetail.jsx
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;






&lt;h2&gt;
  
  
  📁 &lt;code&gt;routes/&lt;/code&gt; – Routing Configuration
&lt;/h2&gt;

&lt;p&gt;All your route definitions and &lt;code&gt;React Router&lt;/code&gt; setup can live here. It makes routing &lt;strong&gt;centralized&lt;/strong&gt; and easy to update when your app grows.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;routes/
├── AppRoutes.jsx
└── PrivateRoute.jsx
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;






&lt;h2&gt;
  
  
  📁 &lt;code&gt;hooks/&lt;/code&gt; – Custom Hooks
&lt;/h2&gt;

&lt;p&gt;If you create your own hooks (which you will!), this is where they live:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;hooks/
├── useAuth.js
├── useToggle.js
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;&lt;strong&gt;Tips:&lt;/strong&gt;&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Keep reusable logic here
&lt;/li&gt;
&lt;li&gt;Prefix them with &lt;code&gt;use&lt;/code&gt; to follow React convention&lt;/li&gt;
&lt;/ul&gt;




&lt;h2&gt;
  
  
  📁 &lt;code&gt;services/&lt;/code&gt; – External API Logic
&lt;/h2&gt;

&lt;p&gt;Anything related to API calls, database interactions, or third-party integrations goes here. This way, your components stay &lt;strong&gt;clean and declarative&lt;/strong&gt;.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;services/
├── api.js
├── postService.js
└── authService.js
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;






&lt;h2&gt;
  
  
  📁 &lt;code&gt;utils/&lt;/code&gt; – Utility Functions
&lt;/h2&gt;

&lt;p&gt;Helper functions that don't belong to a specific feature.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;utils/
├── formatDate.js
├── validateEmail.js
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;&lt;strong&gt;Tips&lt;/strong&gt;:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Keep logic centralized
&lt;/li&gt;
&lt;li&gt;Avoid duplication across features&lt;/li&gt;
&lt;/ul&gt;




&lt;h2&gt;
  
  
  📁 &lt;code&gt;contexts/&lt;/code&gt; - React Context Providers
&lt;/h2&gt;

&lt;p&gt;If you're using &lt;strong&gt;React Context API&lt;/strong&gt; for global state or shared configurations (like theme, auth status, or language settings), it's a good idea to organize them in their own folder.&lt;/p&gt;

&lt;p&gt;Each context file typically includes:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;The &lt;code&gt;createContext()&lt;/code&gt; call&lt;/li&gt;
&lt;li&gt;A context provider component&lt;/li&gt;
&lt;li&gt;Any relevant logic or default values
&lt;/li&gt;
&lt;/ul&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;contexts/
├── AuthContext.jsx
├── ThemeContext.jsx
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;






&lt;h2&gt;
  
  
  📁 &lt;code&gt;styles/&lt;/code&gt; - Global Styling &amp;amp; Theme Config
&lt;/h2&gt;

&lt;p&gt;While individual component styles can live in Button.module.css or *.scss, this folder is perfect for your global CSS setup, such as:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Tailwind or SCSS config&lt;/li&gt;
&lt;li&gt;Theme variables&lt;/li&gt;
&lt;li&gt;Reset or normalize files
&lt;/li&gt;
&lt;/ul&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;styles/
├── global.css
├── variables.css
├── tailwind.config.js
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;






&lt;h2&gt;
  
  
  📄 &lt;code&gt;App.jsx&lt;/code&gt; &amp;amp; &lt;code&gt;main.jsx&lt;/code&gt; – Entry Points
&lt;/h2&gt;

&lt;ul&gt;
&lt;li&gt;
&lt;code&gt;App.jsx&lt;/code&gt; is your main application shell (where routes, providers, and layout go). 
&lt;strong&gt;Example&lt;/strong&gt;: Vite + React
&lt;/li&gt;
&lt;/ul&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;import { useState } from 'react'
import reactLogo from './assets/react.svg'
import viteLogo from '/vite.svg'
import './App.css'

function App() {
  const [count, setCount] = useState(0)

  return (
    &amp;lt;&amp;gt;
      &amp;lt;div&amp;gt;
        &amp;lt;a href="https://vite.dev" target="_blank"&amp;gt;
          &amp;lt;img src={viteLogo} className="logo" alt="Vite logo" /&amp;gt;
        &amp;lt;/a&amp;gt;
        &amp;lt;a href="https://react.dev" target="_blank"&amp;gt;
          &amp;lt;img src={reactLogo} className="logo react" alt="React logo" /&amp;gt;
        &amp;lt;/a&amp;gt;
      &amp;lt;/div&amp;gt;
      &amp;lt;h1&amp;gt;Vite + React&amp;lt;/h1&amp;gt;
      &amp;lt;div className="card"&amp;gt;
        &amp;lt;button onClick={() =&amp;gt; setCount((count) =&amp;gt; count + 1)}&amp;gt;
          count is {count}
        &amp;lt;/button&amp;gt;
        &amp;lt;p&amp;gt;
          Edit &amp;lt;code&amp;gt;src/App.jsx&amp;lt;/code&amp;gt; and save to test HMR
        &amp;lt;/p&amp;gt;
      &amp;lt;/div&amp;gt;
      &amp;lt;p className="read-the-docs"&amp;gt;
        Click on the Vite and React logos to learn more
      &amp;lt;/p&amp;gt;
    &amp;lt;/&amp;gt;
  )
}

export default App
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;ul&gt;
&lt;li&gt;
&lt;code&gt;main.jsx&lt;/code&gt; is the actual root file where React is rendered to the Document Object Model. 
&lt;strong&gt;Example&lt;/strong&gt;: Vite + React
&lt;/li&gt;
&lt;/ul&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;import { StrictMode } from 'react'
import { createRoot } from 'react-dom/client'
import './index.css'
import App from './App.jsx'

createRoot(document.getElementById('root')).render(
  &amp;lt;StrictMode&amp;gt;
    &amp;lt;App /&amp;gt;
  &amp;lt;/StrictMode&amp;gt;,
)
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;






&lt;h2&gt;
  
  
  &lt;strong&gt;🚀 As Your Project Grows...&lt;/strong&gt;
&lt;/h2&gt;

&lt;p&gt;When things scale even further (teams, business complexity, domains), you can transition to a &lt;strong&gt;feature-sliced&lt;/strong&gt; or &lt;strong&gt;domain-driven&lt;/strong&gt; structure:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;src/
├── entities/      // business models like User, Post
├── features/      // login, comment, create post
├── shared/        // shared components, hooks, utils
├── widgets/       // composed UI units (e.g., Header, Sidebar)
├── pages/
├── processes/     // flows (e.g., sign-in flow)

&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;This is inspired by Feature-Sliced Design. Check it out here: &lt;a href="https://feature-sliced.design" rel="noopener noreferrer"&gt;https://feature-sliced.design/docs&lt;/a&gt;&lt;/p&gt;




&lt;h2&gt;
  
  
  🧩 Final Thoughts
&lt;/h2&gt;

&lt;p&gt;React gives you freedom, but with freedom comes responsibility.&lt;br&gt;
If you don’t plan your project structure early, you’ll face chaos later.&lt;/p&gt;

&lt;p&gt;Start small and flat.&lt;br&gt;
Then, organize by features.&lt;br&gt;
Eventually, evolve into a modular, domain-based architecture.&lt;/p&gt;

&lt;p&gt;Whatever the size of your app, the goal is the same:&lt;br&gt;
&lt;strong&gt;Readable, maintainable, and scalable code.&lt;/strong&gt;&lt;/p&gt;

</description>
      <category>webdev</category>
      <category>react</category>
      <category>productivity</category>
      <category>discuss</category>
    </item>
  </channel>
</rss>
