Hash-Based Routing and Fragment Identifiers
Understand how the URL hash (fragment identifier) works, its role in single-page application routing, anchor navigation, and why the hash is never sent to the server.
Detailed Explanation
URL Hash / Fragment Identifier
The hash (also called fragment identifier) is the part of a URL that follows the # symbol. It has a unique property: it is never sent to the server in the HTTP request.
Basic Behavior
https://docs.example.com/guide/setup#installation
\_________/
hash
When a browser requests this URL, it sends:
GET /guide/setup HTTP/1.1
Host: docs.example.com
The #installation part stays entirely on the client side.
Traditional Use: Anchor Navigation
The original purpose of the hash is to link to a specific element on the page:
<!-- Link to a section -->
<a href="#faq">Jump to FAQ</a>
<!-- Target section -->
<section id="faq">
<h2>FAQ</h2>
...
</section>
SPA Hash Routing
Single-page applications (SPAs) use the hash for client-side routing because changing the hash does not cause a page reload:
https://app.example.com/#/dashboard
https://app.example.com/#/users/123
https://app.example.com/#/settings?tab=profile
Frameworks like Vue Router, Angular, and older versions of React Router support hash mode:
// Vue Router hash mode
const router = createRouter({
history: createWebHashHistory(),
routes: [...]
});
Hash vs History API Routing
| Feature | Hash Routing | History API |
|---|---|---|
| URL appearance | example.com/#/page |
example.com/page |
| Server config | None needed | Requires fallback to index.html |
| SEO | Poor (search engines may ignore hash) | Good |
| Page reload | No | No |
| Server-side rendering | Not possible | Possible |
hashchange Event
JavaScript can listen for hash changes:
window.addEventListener("hashchange", (event) => {
console.log("Old URL:", event.oldURL);
console.log("New URL:", event.newURL);
console.log("Hash:", window.location.hash);
});
Important Properties
- The hash includes the
#character:url.hashreturns"#section", not"section" - An empty hash (
#) is different from no hash at all - The hash can contain query-like parameters:
#/page?key=value(but these are not real query params)
Use Case
Hash-based routing is still widely used in applications deployed on static hosting without server-side URL rewriting (GitHub Pages, S3 static hosting, basic shared hosting). It is also used for smooth-scroll navigation within documentation sites, wiki pages, and content-heavy websites. Understanding how the hash works is essential for building bookmarkable views in SPAs.