Get the hash (#fragment) of the current URL in JavaScript
The part of a URL after # is the fragment, often called the hash. It points to a place inside the page, and scripts use it to remember a tab or a filter. It lives only in the browser: it is never sent to the server, so ASP.NET's Request.Url cannot read it.
Reading it
// URL: https://www.example.com/help.aspx?topic=forms#validation
var hash = window.location.hash; // "#validation" ("" if none)
var name = hash.slice(1); // "validation"
var decoded = decodeURIComponent(name); // handles %20 and other escapes
// From any URL string, not just the current page:
var u = new URL("https://www.example.com/a.aspx#step-2");
console.log(u.hash); // "#step-2"
location.hash includes the #. Decode it before comparing, because a fragment such as #caf%C3%A9 arrives encoded.
Changing it
location.hash = "settings"; // adds a history entry, scrolls to #settings
history.replaceState(null, "", "#settings"); // changes it without a new history entry or scrolling
Reacting to changes
function showTab() {
var id = decodeURIComponent(location.hash.slice(1)) || "overview";
document.querySelectorAll("[role=tabpanel]").forEach(function (p) {
p.hidden = p.id !== id;
});
}
window.addEventListener("hashchange", showTab);
showTab(); // also on first load
With jQuery: $(window).on("hashchange", showTab);. The event fires for links like <a href="#details">, for the back and forward buttons and for script changes through location.hash (not for history.replaceState).
The server never sees it
Browsers strip the fragment before sending the request. If the server needs the value, for example to preselect a tab after a postback, copy it into a hidden field before the form is posted:
<asp:HiddenField ID="hfTab" runat="server" />
<script>
document.forms[0].addEventListener("submit", function () {
document.getElementById("<%= hfTab.ClientID %>").value = location.hash.slice(1);
});
</script>
A Response.Redirect to a URL containing #section works: the browser keeps the fragment of the redirect target. For values the server must read from the URL, use the query string instead: Read the query string in the browser.
Common uses and pitfalls
- Deep links to sections. Give headings an
idand link topage.aspx#section; no script needed. - Remembering UI state. Tabs, filters or an open accordion panel can be stored in the hash so the back button and bookmarks restore them.
- Not for secrets. The hash stays in browser history and can be read by any script on the page.
- Fixed headers hide the target. Add
scroll-margin-topto the target elements in CSS so the heading is not hidden under a sticky header.