Reset Password Block
ResetPassword is a controlled two-step reset flow (request and confirm_password) built on MUI.
Installation
- npm
- yarn
- pnpm
- bun
npm install @nodeblocks/frontend-reset-password-block@0.5.0
yarn add @nodeblocks/frontend-reset-password-block@0.5.0
pnpm add @nodeblocks/frontend-reset-password-block@0.5.0
bun add @nodeblocks/frontend-reset-password-block@0.5.0
What You Need
| Item | Why it matters |
|---|---|
data | Single source of truth for form state |
onDataChange | Receives updated state + metadata on field changes |
view | Switches between email request and password confirmation UI |
onSendRequest | Called when the request form is submitted (view="request") |
onResetPassword | Called when the confirm form is submitted (view="confirm_password") |
errors (optional) | Displays field-level error feedback |
viewResetPassword does not own form state. Keep state in your app and pass it through data. Use view="request" with { email } data, or view="confirm_password" with { password, confirmPassword } data.
Code Examples
- Quick Start
- Labels and URLs
- Compound Components
- Block Override
function Example() { const [view] = React.useState('request'); const [data, setData] = React.useState({email: ''}); return ( <ResetPassword view={view} data={data} onDataChange={setData} onSendRequest={formData => { alert(`Send request:\n${JSON.stringify(formData, null, 2)}`); }} onResetPassword={formData => { alert(`Reset password:\n${JSON.stringify(formData, null, 2)}`); }} /> ); }
Customize title, description, labels, placeholders, and the active view.
function Example() { const [view] = React.useState('confirm_password'); const [data, setData] = React.useState({password: '', confirmPassword: ''}); return ( <ResetPassword view={view} data={data} description={null} resetPasswordTitle="Set a new password" labels={{ passwordField: 'New password', confirmPasswordField: 'Confirm password', resetPasswordButton: 'Update password', }} placeholders={{ passwordField: 'Enter a new password', confirmPasswordField: 'Re-enter your password', }} errors={{ password: 'Use at least 8 characters.', confirmPassword: 'Passwords do not match.', }} onDataChange={setData} onSendRequest={formData => { alert(`Send request:\n${JSON.stringify(formData, null, 2)}`); }} onResetPassword={formData => { alert(`Reset password:\n${JSON.stringify(formData, null, 2)}`); }} /> ); }
Pass resetPasswordTitle and description on the root. Use labels and placeholders for field and button copy, or override via subcomponent props (see Compound Components tab). Set description={null} to hide the description block on the confirm step.
Use child blocks to customize layout while keeping controlled state behavior. Fields render based on view (EmailField for request; password fields for confirm_password).
function Example() { const [view] = React.useState('request'); const [data, setData] = React.useState({email: ''}); return ( <ResetPassword view={view} data={data} onDataChange={setData} onSendRequest={formData => { alert(`Send request:\n${JSON.stringify(formData, null, 2)}`); }} onResetPassword={formData => { alert(`Reset password:\n${JSON.stringify(formData, null, 2)}`); }} > <ResetPassword.Title>Reset Your Password</ResetPassword.Title> <ResetPassword.Description>Enter your email to receive reset instructions</ResetPassword.Description> <ResetPassword.Form> <ResetPassword.Form.EmailField view={view} label="Email Address" placeholder="Enter your email" /> <ResetPassword.Form.PasswordField view={view} label="New Password" placeholder="Enter new password" /> <ResetPassword.Form.ConfirmPasswordField view={view} label="Confirm Password" placeholder="Confirm new password" /> <ResetPassword.Form.ResetPasswordButton>Reset Password</ResetPassword.Form.ResetPasswordButton> </ResetPassword.Form> </ResetPassword> ); }
Use function children to override default blocks and order.
function Example() { const [view] = React.useState('request'); const [data, setData] = React.useState({email: ''}); return ( <ResetPassword view={view} data={data} onDataChange={setData} onSendRequest={formData => { alert(`Send request:\n${JSON.stringify(formData, null, 2)}`); }} onResetPassword={formData => { alert(`Reset password:\n${JSON.stringify(formData, null, 2)}`); }} > {({defaultBlocks, defaultBlockOrder}) => ({ blocks: { ...defaultBlocks, customBlock: ( <div style={{ background: '#eef4ff', border: '1px solid #cddcff', borderRadius: '8px', padding: '12px', fontSize: '14px', textAlign: 'center', }} > Custom notification or help text </div> ), }, blockOrder: ['customBlock', ...defaultBlockOrder], })} </ResetPassword> ); }
When to use block overrides
Use overrides when you need to change order, replace default UI blocks, or inject custom content while preserving shared state handling. Default order is title, description, form.
Important Props
Core Props
| Prop | Type | Required | Default | Description |
|---|---|---|---|---|
data | ResetPasswordFormData ({ email? } or { password?, confirmPassword? }, or extended Record<string, unknown>) | Yes | - | Current form data; shape should match view |
onDataChange | (data, meta) => void | Yes | - | Called on updates; meta includes name, value, cause (input, change, blur, clear, reset, programmatic), optional event |
view | 'request' | 'confirm_password' | Yes | 'request' | Active step of the reset flow |
onSendRequest | (data) => void | Yes | - | Submit handler for view="request" |
onResetPassword | (data) => void | Yes | - | Submit handler for view="confirm_password" |
errors | Partial<Record<Paths<T, { bracketNotation: true }>, string | string[]>> | No | - | Field errors keyed by a valid data path (for example, email, password, or confirmPassword) |
Content Props
| Prop | Type | Required | Default | Description |
|---|---|---|---|---|
resetPasswordTitle | ReactNode | No | 'Reset Password' | Title content |
description | ReactNode | No | 'Please enter your email address you registered' | Description below the title; pass null to hide |
labels | { emailField?, passwordField?, confirmPasswordField?, resetPasswordButton? } | No | emailField: 'Email', passwordField: 'Password', confirmPasswordField: 'Confirm Password', resetPasswordButton: 'Reset Password' | Override field and button labels |
placeholders | { emailField?, passwordField?, confirmPasswordField? } | No | emailField: 'Please enter your email', passwordField: 'Please enter your new password', confirmPasswordField: 'Please confirm your password' | Override field placeholders |
showPassword | boolean | No | - | Password visibility for Form.PasswordField (confirm_password view); defaults to internal false state |
onShowPasswordClick | (show: boolean) => void | No | - | Controls password visibility when supplied |
showConfirmPassword | boolean | No | - | Confirm-password visibility for Form.ConfirmPasswordField; defaults to internal false state |
onShowConfirmPasswordClick | (show: boolean) => void | No | - | Controls confirm-password visibility when supplied |
Layout and Composition Props
| Prop | Type | Required | Default | Description |
|---|---|---|---|---|
children | BlocksOverride | ReactNode | No | - | Override default blocks or provide custom JSX children |
component | React.ElementType | No | 'div' | Root Stack element type |
className | string | No | - | Class name for the root container |
sx | SxProps | No | - | MUI system styles for the root container |
ResetPassword also inherits StackProps (except children and onSubmit), so standard stack props like id, spacing, and component are supported. Form submit is handled inside ResetPassword.Form. Default block order without overrides: title, description, form (defaultBlockOrder).
Default UI Blocks
| Block | Built on | Notes |
|---|---|---|
ResetPassword (root) | Stack | Controlled container; its default element is a div; submit handlers live on Form |
ResetPassword.Title | Typography | Title text block (variant="h4"); default Reset Password |
ResetPassword.Description | Typography | Description text (variant="body2"); default Please enter your email address you registered; hidden when description is null |
ResetPassword.Form | Stack (component="form") | Form container; calls onSendRequest or onResetPassword by view |
ResetPassword.Form.EmailField | TextField | Shown only when view="request"; name="email"; default Email / Please enter your email |
ResetPassword.Form.PasswordField | TextField + IconButton | Shown only when view="confirm_password"; name="password"; default Password / Please enter your new password; visibility toggle |
ResetPassword.Form.ConfirmPasswordField | TextField + IconButton | Shown only when view="confirm_password"; name="confirmPassword"; default Confirm Password / Please confirm your password; separate visibility toggle |
ResetPassword.Form.ResetPasswordButton | Button | Submit button (variant="contained", type="submit"); default Reset Password |
TypeScript
import { ResetPassword, type ResetPasswordFormData } from '@nodeblocks/frontend-reset-password-block';
type MyResetPasswordData = ResetPasswordFormData & {
token?: string;
};