useRouter and usePathname

Navigating in Code

Inside a Client Component, the useRouter hook from next/navigation lets you navigate after an event (form submit, button click).

components/BuyNowButton.tsx

'use client';

import { useRouter } from 'next/navigation';

export default function BuyNowButton({ productId }: { productId: number }) {
  const router = useRouter();

  function buyNow() {
    // ...add to cart, then go to checkout
    router.push('/checkout?item=' + productId);
  }

  return <button onClick={buyNow}>Buy Now</button>;
}
MethodDoes
router.push(url)Go to a URL, add a history entry
router.replace(url)Go without adding history (login → dashboard)
router.back()Browser back
router.refresh()Re-fetch Server Components of the current page, keep client state
router.prefetch(url)Prefetch manually

Note: Import from next/navigation, not next/router. next/router is the old Pages Router API and throws in the App Router.

Active Link with usePathname

usePathname() returns the current path, e.g. /products/42. A common use is highlighting the active menu item:

'use client';

import Link from 'next/link';
import { usePathname } from 'next/navigation';

const links = [
  { href: '/', label: 'Home' },
  { href: '/products', label: 'Products' },
  { href: '/account', label: 'Account' },
];

export default function NavLinks() {
  const pathname = usePathname();
  return (
    <nav>
      {links.map((l) => {
        const active = l.href === '/' ? pathname === '/' : pathname.startsWith(l.href);
        return (
          <Link key={l.href} href={l.href} className={active ? 'font-bold text-blue-600' : ''}>
            {l.label}
          </Link>
        );
      })}
    </nav>
  );
}

Example

The active-link rule on its own. Note why / must use an exact match:

function isActive(href: string, pathname: string): boolean {
  if (href === '/') return pathname === '/';
  return pathname === href || pathname.startsWith(href + '/');
}

const cases: [string, string][] = [
  ['/', '/'],
  ['/', '/products'],
  ['/products', '/products/42'],
  ['/products', '/products-sale'],
  ['/account', '/account/orders'],
];
for (const [href, path] of cases) {
  console.log(href.padEnd(10), path.padEnd(16), isActive(href, path));
}

Output

/          /                true
/          /products        false
/products  /products/42     true
/products  /products-sale   false
/account   /account/orders  true

Reading Query Parameters

useSearchParams() reads ?category=books&sort=price in a Client Component (pages can also read searchParams as a prop).

'use client';

import { useSearchParams } from 'next/navigation';

export default function SortLabel() {
  const params = useSearchParams();
  const sort = params.get('sort') ?? 'relevance';
  return <span>Sorted by: {sort}</span>;
}