Cookbook Router
Practical Patterns

Block unsaved changes

Use a navigation blocker for dirty forms without hijacking every browser event.

Protect unfinished work at the navigation layer. useBlocker() covers unsaved changes and other client-side leave guards.

function NewMessage() {
  const [formData, setFormData] = React.useState({
    name: '',
    email: '',
    message: '',
  });

  useBlocker({
    when: Boolean(formData.name || formData.email || formData.message),
    message: 'Your message has not been sent. Leave and discard your draft?',
  });

  // ...
}

The blocker applies whether the route is rendered canonically or through an intercepted slot.

On this page