JavaScript Routing with Hash and History API
Routing in JavaScript is about updating the URL and displaying the corresponding content without reloading the page. This improves user experience by preventing unnecessary refreshes and preserving state. The two primary routing techniques used in Single Page Applications (SPAs) are hash-based routing and history-based routing.
1. Hash-Based Routing
Hash routing uses the URL fragment (#something) to control navigation without triggering a full page reload.
How It Works
- The part after
#never triggers a server request. - JavaScript listens for
hashchangeevents and updates the UI accordingly. - Ideal for simple SPAs because it needs no server configuration.
Basic Example
html
<ul>
<li><a href="#/home">Home</a></li>
<li><a href="#/about">About</a></li>
</ul>
<div id="app"></div>
<script>
const routes = {
'/home': '<h2>Home Page</h2>',
'/about': '<h2>About Page</h2>',
};
function routerView() {
const hash = location.hash.substring(1) || '/home';
document.getElementById('app').innerHTML = routes[hash] || '<h2>404 Not Found</h2>';
}
window.addEventListener('DOMContentLoaded', routerView);
window.addEventListener('hashchange', routerView);
</script>Pros and Cons
Pros:
- No server config needed
- Works everywhere
- Easy to implement
Cons:
- URL looks less clean (
/#/about) - Not ideal for SEO
2. History API Routing
The History API uses clean URLs like /home without page reloads.
How It Works
- Use
history.pushState()to change the URL. - Listen for
popstateevents (back/forward buttons). - Requires server configuration (redirect all requests to
index.html).
Basic Example
html
<ul>
<li><a href="/home" class="nav-link">Home</a></li>
<li><a href="/about" class="nav-link">About</a></li>
</ul>
<div id="app"></div>
<script>
const routes = {
'/home': '<h2>Home Page</h2>',
'/about': '<h2>About Page</h2>',
};
function routerView() {
const path = location.pathname;
document.getElementById('app').innerHTML = routes[path] || '<h2>404 Not Found</h2>';
}
document.querySelectorAll('.nav-link').forEach(link => {
link.addEventListener('click', event => {
event.preventDefault();
const href = link.getAttribute('href');
history.pushState({}, '', href);
routerView();
});
});
window.addEventListener('popstate', routerView);
window.addEventListener('DOMContentLoaded', routerView);
</script>Pros and Cons
Pros:
- Clean, SEO-friendly URLs
- Matches modern SPA frameworks (React Router, Vue Router)
Cons:
- Requires server rewrite rules
- Slightly more complex
⚖️ Hash vs History: Quick Comparison
| Feature | Hash Routing | History API |
|---|---|---|
| URL Style | /#/route | /route |
| Requires Server Config | ❌ No | ✅ Yes |
| SEO Friendly | ❌ No | ✅ Yes |
| Browser Support | Excellent | Excellent |
| Easiest for Beginners | ✅ Yes | ❌ No |
Summary
To build client-side routing:
- Intercept navigation to avoid page reloads
- Update the URL using hash or History API
- Render content dynamically based on the current route
- Listen for changes (
hashchangeorpopstate)
Mastering both routing styles prepares you for building full-featured SPAs and understanding popular frameworks’ internals.