Toast Notifications
Toast notifications provide a non-intrusive way to display temporary messages to users, typically for confirming actions or showing error states.
Implementation
Basic Redirect with Toast
Use the redirectWithToast
utility for simple redirects with notifications:
import { redirectWithToast } from '#app/utils/toast.server' ,[object Object],
return redirectWithToast(,[object Object],, { description: 'Item successfully created', type: 'success' }) }
Direct Toast Headers
Create toast notifications without redirects:
import { createToastHeaders } from '#app/utils/toast.server' ,[object Object],
return json( { success: true }, { headers: await createToastHeaders({ description: 'Item updated successfully', type: 'success' }) } ) }
Multiple Headers
Combine toast headers with other headers:
import { combineHeaders } from '#app/utils/misc'
export async function action() { return json( { success: true }, { headers: combineHeaders( await createToastHeaders({ description: 'Profile updated', type: 'success' }), { 'Cache-Control': 'no-cache', 'X-Custom-Header': 'value' } ) } ) }
Toast Types and Styling
Success Toast
return redirectWithToast('/dashboard', { description: 'Changes saved successfully', type: 'success', duration: 3000 })
Error Toast
return redirectWithToast('/form', { description: 'Please fix the errors below', type: 'error', duration: 5000 })
Info Toast
return redirectWithToast('/dashboard', { description: 'New features available', type: 'info', duration: 4000 })
Advanced Usage
Custom Toast Component
function CustomToast({ message, type }: ToastProps) { return ( <div className={`toast toast-${type}`}> <div className="toast-content"> {type === 'success' && <SuccessIcon />} {type === 'error' && <ErrorIcon />} <p>{message}</p> </div> </div> ) }
Toast Manager
function ToastManager() { const toasts = useToasts()
return ( <div className="toast-container"> {toasts.map(toast => ( <CustomToast key={toast.id} message={toast.description} type={toast.type} /> ))} </div> ) }
Best Practices
Message Content
- Keep messages concise
- Be specific about actions
- Use consistent language
- Provide clear next steps
Toast Duration
const durations = { short: 2000, // Quick confirmations medium: 3000, // Default duration long: 5000 // Important messages }
Error Handling
try { await processAction() return redirectWithToast('/success', { type: 'success', description: 'Action completed' }) } catch (error) { return redirectWithToast('/error', { type: 'error', description: error.message }) }
Accessibility
function AccessibleToast({ message, type }: ToastProps) { return ( <div role="alert" aria-live="polite" className={`toast toast-${type}`} > {message} </div> ) }
For more information about server-side utilities, see the server documentation. For client-side components, refer to the components documentation.