Mastering React Imports: Relative vs Aliases (../
vs @/
) 🚀
If you’ve ever wondered whether to write:
import { HomePage } from '../features/heroes/HomePage';
…or:
import { HomePage } from '@/features/heroes/HomePage';
You’ve touched on one of those subtle but professional-level React/TypeScript project structuring questions.
Let’s break it down like a senior React developer mentoring their team.
🟢 BASIC — Relative Imports (../
)
Relative imports literally walk the filesystem.
-
..
= “go up one directory”. - So
../features/heroes/HomePage
= “go up one folder, then intofeatures/heroes
”.
✅ Pros
- Works out-of-the-box in Node, React, Vite, Next, etc.
- No extra config needed.
❌ Cons
- Becomes ugly and fragile in deep folder trees:
import { Button } from '../../../../components/ui/Button';
- If you move files, imports break.
- Harder to scan visually: “Where is this pointing to?”
🟡 MEDIUM — Path Aliases (@/
)
Path aliases (aka module aliases) map a symbol (commonly @
) to your src/
folder.
tsconfig.json
{ "compilerOptions": { "baseUrl": "src", "paths": { "@/*": ["*"] } } }
vite.config.ts
import { defineConfig } from 'vite'; import react from '@vitejs/plugin-react'; import path from 'path'; export default defineConfig({ plugins: [react()], resolve: { alias: { '@': path.resolve(__dirname, 'src'), }, }, });
✅ Pros
- Flat imports regardless of depth:
import { Button } from '@/components/ui/Button';
- Easier to move files around.
- Clear mental model:
@/
= root of your source. - Industry standard in large React / Next.js / Vite apps.
❌ Cons
- Requires config (
tsconfig.json
+ bundler). - New devs must know
@
is a shortcut.
🔵 ADVANCED — Blended Best Practice
As a pro React dev:
- Use aliases (
@/…
) for imports across feature boundaries or shared libs. - Use relative imports for local siblings inside the same feature.
This keeps features self-contained while global imports stay clean.
Example
// Inside src/features/heroes/HomePage.tsx import { HeroGrid } from './HeroGrid'; // relative (local sibling) import { CustomJumbotron } from '@/components/ui'; // alias (shared UI lib)
Result:
✔️ Clarity (local code portable).
✔️ Scalability (global code stays readable).
🟣 EXPERT — The Analogy
Think of it like navigation:
../…
= step-by-step directions
(“go up one block, turn left, go inside”)@/…
= GPS address
(“start from the city center =src/
”)
Both get you there, but one scales much better in a growing city (your project).
⚡ Senior Takeaway
In professional React/Vite/Next projects:
- Always configure
@
(or~
, orsrc
) aliases intsconfig.json
and bundler. - Reserve relative imports for local siblings.
- Use aliases for cross-feature or shared imports.
👉 This keeps codebases readable, maintainable, and resilient to refactors.
✍️ Written by: Cristian Sifuentes — Full-stack React/TypeScript developer, passionate about clean architecture, DX, and teaching dev teams to scale projects like pros.
Top comments (0)