-
Notifications
You must be signed in to change notification settings - Fork 0
useURL
A highly sophisticated hook that intercepts browser navigation and shreds the current URL into a deeply parsed, React-friendly object. It acts as a lightweight router alternative, instantly reacting to History API changes (pushState, replaceState), hash changes, and back/forward navigation without requiring a bloated external library.
Extracting query parameters and path segments without wrestling with the native URLSearchParams API.
import { useURL } from "react-hook-lab";
function ProductPage() {
const { pathname, segments, query } = useURL();
// If URL is: https://example.com/products/shoes?category=sneakers&sort=price
console.log(pathname); // "/products/shoes"
console.log(segments); // ["products", "shoes"]
console.log(query); // { category: "sneakers", sort: "price" }
return <div>Viewing {segments[1]} in category: {query.category}</div>;
}Rendering dynamic breadcrumbs automatically based on the URL structure.
import { useURL } from "react-hook-lab";
function BreadcrumbNav() {
const { breadcrumbs } = useURL();
// If URL is: https://example.com/admin/dashboard/users
// Breadcrumbs auto-generates:
// [{name: "Home", path: "/"}, {name: "Admin", path: "/admin"}, ...]
return (
<nav>
{breadcrumbs.map((crumb, index) => (
<span key={crumb.path}>
<a href={crumb.path}>{crumb.name}</a>
{index < breadcrumbs.length - 1 && " > "}
</span>
))}
</nav>
);
}Detecting file paths (like images or documents) in the URL, and identifying if the user has navigated since they landed on the page.
import { useURL } from "react-hook-lab";
function FileViewer() {
const { filename, extension, changed, previous } = useURL();
// If URL is: https://example.com/downloads/report.pdf
if (extension === "pdf") {
return (
<div>
<h2>Viewing Document: {filename}</h2>
{changed && <p>You came here from {previous}</p>}
</div>
);
}
return <p>No file selected</p>;
}Returns an object of type UseURLReturn containing exhaustive URL metrics. Key properties include:
-
href(string): The complete, raw URL string. -
pathname(string): The path component (e.g.,"/blog/post"). -
query(Record<string, string | string[]>): A fully parsed dictionary of query parameters. Duplicate keys automatically form an array (e.g.,?id=1&id=2becomes{ id: ["1", "2"] }). -
hash(string): The fragment identifier (e.g.,"#section-2"). -
segments(string[]): The path neatly split into an array (e.g.,["blog", "post"]). -
filename(string | null): The detected file name, if present in the path. -
extension(string | null): The detected file extension (e.g.,"jpg","pdf"). -
breadcrumbs(Breadcrumb[]): Pre-calculated objects to easily render a breadcrumb UI. -
isHome(boolean): True if the pathname is exactly"/". -
isSecure(boolean): True if served overhttps:. -
previous(string | null): The pathname of the previous URL before the last navigation. -
changed(boolean): True if the user has navigated away from their initial landing path.
useURL is exceptionally robust.
-
Monkey-Patching History: Because standard React apps use
window.history.pushStateto navigate without reloading, native DOM events don't fire.useURLsafely monkey-patchespushStateandreplaceStateglobally to emit custom events (pushstate,replacestate). It listens to these, plus nativepopstateandhashchangeevents. -
Deep Parsing: On every navigation, the raw URL is fed into the native
new URL()constructor. The hook then aggressively dissects the path intosegments, calculatesbreadcrumbs, tests the final segment for fileextensionpatterns, and parsesURLSearchParamsinto a plain JavaScript Object. -
Memoization: To prevent massive performance bottlenecks during rendering, all parsing logic is wrapped in
useMemo. The complexUseURLReturnobject strictly maintains its memory reference unless the rawwindow.location.hrefactually changes.
Built with ❤️ by Saurav-TB-Pandey. | Report an Issue | NPM