Parcel Complete Guide | Zero Config Build Tool

Parcel Complete Guide | Zero Config Build Tool

이 글의 핵심

Parcel is a zero-configuration web application bundler. It offers blazing fast performance with multi-core compilation and requires no configuration to get started.

Introduction

Parcel is a web application bundler that requires zero configuration. Unlike Webpack, you don’t need to write config files - Parcel automatically handles everything.

The Problem with Traditional Bundlers

Webpack:

// webpack.config.js - hundreds of lines
module.exports = {
  entry: './src/index.js',
  output: { /* ... */ },
  module: {
    rules: [
      { test: /\.js$/, use: 'babel-loader' },
      { test: /\.css$/, use: ['style-loader', 'css-loader'] },
      { test: /\.(png|jpg)$/, use: 'file-loader' },
      // ... many more rules
    ]
  },
  plugins: [/* ... */]
};

Parcel:

# No config needed!
parcel index.html

1. Installation

npm install --save-dev parcel

Quick Start:

<!-- index.html -->
<!DOCTYPE html>
<html>
<head>
  <title>My App</title>
</head>
<body>
  <div id="app"></div>
  <script type="module" src="./src/index.js"></script>
</body>
</html>
// src/index.js
import './styles.css';

console.log('Hello from Parcel!');
# Development
npx parcel index.html

# Production
npx parcel build index.html

2. Features Out of the Box

Automatic Dependencies

Parcel automatically installs dependencies when needed:

// Just import - Parcel handles the rest
import React from 'react';
import ReactDOM from 'react-dom';

// Even works with CSS
import './styles.css';

// Images
import logo from './logo.png';

Hot Module Replacement

// Automatically enabled in dev mode
if (module.hot) {
  module.hot.accept();
}

Multiple Entry Points

parcel src/index.html src/admin.html

3. React Example

No configuration needed!

// src/App.jsx
import React from 'react';

export default function App() {
  return (
    <div>
      <h1>Hello, Parcel!</h1>
    </div>
  );
}
// src/index.jsx
import React from 'react';
import ReactDOM from 'react-dom';
import App from './App';

ReactDOM.render(<App />, document.getElementById('root'));
<!-- index.html -->
<!DOCTYPE html>
<html>
<body>
  <div id="root"></div>
  <script type="module" src="./src/index.jsx"></script>
</body>
</html>
parcel index.html
# Parcel automatically:
# - Detects React
# - Transpiles JSX
# - Sets up HMR
# - Optimizes for production

4. TypeScript Support

Zero config!

// src/index.ts
interface User {
  name: string;
  age: number;
}

const user: User = {
  name: 'Alice',
  age: 30
};

console.log(user);
parcel index.html
# Parcel automatically detects and compiles TypeScript

5. CSS and Styling

Plain CSS

/* styles.css */
.button {
  background: blue;
  color: white;
}
import './styles.css';

CSS Modules

/* Button.module.css */
.button {
  background: blue;
}
import styles from './Button.module.css';

function Button() {
  return <button className={styles.button}>Click</button>;
}

PostCSS

npm install --save-dev postcss autoprefixer
// .postcssrc
{
  "plugins": {
    "autoprefixer": {}
  }
}

SASS/SCSS

npm install --save-dev sass
// styles.scss
$primary: blue;

.button {
  background: $primary;
}
import './styles.scss';
// Parcel automatically compiles SCSS

6. Image Optimization

// Automatically optimized
import image from './image.jpg';

// WebP support
import webp from './image.webp';

// SVG as component (React)
import Logo from './logo.svg';
<!-- Automatic optimization -->
<img src="./image.jpg" alt="Image">

7. Code Splitting

Dynamic Imports

// Automatic code splitting
button.addEventListener('click', async () => {
  const module = await import('./heavy-module');
  module.default();
});

React Lazy

import React, { lazy, Suspense } from 'react';

const Heavy = lazy(() => import('./HeavyComponent'));

function App() {
  return (
    <Suspense fallback={<div>Loading...</div>}>
      <Heavy />
    </Suspense>
  );
}

8. Environment Variables

# .env
API_URL=https://api.example.com
API_KEY=secret123
console.log(process.env.API_URL);
console.log(process.env.API_KEY);
# Production
parcel build index.html
# Automatically inlines environment variables

9. Production Build

parcel build index.html

Automatic optimizations:

  • ✅ Minification (Terser for JS, cssnano for CSS)
  • ✅ Tree shaking
  • ✅ Scope hoisting
  • ✅ Compression
  • ✅ Source maps
  • ✅ Content hashing
// package.json
{
  "scripts": {
    "dev": "parcel index.html",
    "build": "parcel build index.html",
    "preview": "parcel build index.html --no-optimize"
  }
}

10. Configuration (Optional)

Parcel works without config, but you can customize:

// package.json
{
  "source": "src/index.html",
  "browserslist": "> 0.5%, last 2 versions, not dead",
  "@parcel/transformer-js": {
    "inlineFS": false,
    "inlineEnvironment": ["NODE_ENV"]
  }
}

11. Multi-Page Application

project/
├── index.html
├── about.html
├── contact.html
└── src/
    ├── index.js
    ├── about.js
    └── contact.js
parcel src/*.html

12. Library Mode

// package.json
{
  "name": "my-library",
  "main": "dist/index.js",
  "module": "dist/index.mjs",
  "source": "src/index.js",
  "targets": {
    "main": {
      "optimize": true
    },
    "module": {
      "optimize": true
    }
  }
}
parcel build

13. Performance

Parcel is incredibly fast:

BundlerCold StartHMR
Parcel 21.2s<50ms
Webpack 53.5s~200ms
Rollup2.8sN/A

Why Parcel is fast:

  • Multi-core compilation
  • Aggressive caching
  • Rust-based compiler
  • Minimal overhead

14. Best Practices

1. Use package.json Scripts

{
  "scripts": {
    "dev": "parcel src/index.html --open",
    "build": "parcel build src/index.html --public-url ./",
    "clean": "rm -rf dist .parcel-cache"
  }
}

2. Gitignore

# .gitignore
dist/
.parcel-cache/

3. Environment-Specific Config

const apiUrl = process.env.NODE_ENV === 'production'
  ? 'https://api.production.com'
  : 'http://localhost:3000';

15. Common Issues

Problem: Module not found

# Clear cache
rm -rf .parcel-cache

Problem: Port already in use

parcel index.html --port 1234

Problem: CORS in development

{
  "scripts": {
    "dev": "parcel --port 3000 --host localhost"
  }
}

Summary

Parcel simplifies web development with zero config:

  • Zero configuration required
  • Blazing fast with multi-core compilation
  • Hot module replacement built-in
  • Automatic dependency resolution
  • Production-ready optimizations

Key Takeaways:

  1. No config files needed
  2. Works with React, Vue, TypeScript out of box
  3. Automatic code splitting
  4. Fast HMR (<50ms)
  5. Perfect for quick projects and prototypes

Next Steps:

  • Try Vite for even faster builds
  • Learn Webpack for complex setups
  • Explore esbuild for bundler plugins

Resources: