Docs
sonner

sonner

An opinionated toast component for React.

About

Sonner is built and maintained by emilkowalski_.

Installation

Run the following command:

npx duck-ui@latest add sonner
npx duck-ui@latest add sonner

Add the Toaster component

app/layout.tsx
import { Toaster } from '@/components/ui/sonner'
 
export default function RootLayout({ children }) {
  return (
    <html lang="en">
      <head />
      <body>
        <main>{children}</main>
        <Toaster />
      </body>
    </html>
  )
}
app/layout.tsx
import { Toaster } from '@/components/ui/sonner'
 
export default function RootLayout({ children }) {
  return (
    <html lang="en">
      <head />
      <body>
        <main>{children}</main>
        <Toaster />
      </body>
    </html>
  )
}

Usage

import { toast } from 'sonner'
import { toast } from 'sonner'
toast('Event has been created.')
toast('Event has been created.')

Examples

Default

API Reference

Sonner Props

  • theme ('light' | 'dark' | 'system', default: 'system') – Specifies the theme for the toaster. Uses the current theme from next-themes if available.
  • className (string, default: 'toaster') – Adds additional CSS classes to the main toaster wrapper.
  • toastOptions (object, default: {}) – Customizes individual toast components. See ToastOptions below.
  • classNames (object) – Custom CSS classes for different toast elements.
  • classNames.toast (string) – Styles applied to the toast container.
  • classNames.description (string) – Styles applied to the toast description text.
  • classNames.actionButton (string) – Styles applied to action buttons inside the toast.
  • classNames.cancelButton (string) – Styles applied to cancel buttons inside the toast.

SonnerUpload

  • progress (number, required) Current upload progress percentage (0–100).
  • attachments (number, required) Number of files being uploaded.
  • remainingTime (number, optional) Estimated remaining upload time in seconds.
  • onCancel ((e: React.MouseEvent<HTMLButtonElement>, dismiss: (id: string) => void) => void, optional) Callback triggered when the Cancel button is clicked. Receives the click event and a function to dismiss the toast by ID.
  • onComplete ((e: React.MouseEvent<HTMLButtonElement>, dismiss: (id: string) => void) => void, optional) Callback triggered when the Complete button is clicked. Receives the click event and a function to dismiss the toast by ID.

Behavior: Renders a UI showing upload progress with animated icons, progress bar, dynamic text for number of files and remaining time, and buttons to cancel or confirm completion. The Cancel button is visible during upload; Complete button appears after upload finishes.


Utility Function

formatTime(seconds: number): string

Formats a duration in seconds into a human-readable string:

  • Returns days if >= 1 day ('Xd '),
  • else hours if >= 1 hour ('Xh '),
  • else minutes if >= 1 minute ('Xm '),
  • else seconds ('Xs').

Types

export type UploadSonnerProps = {
  progress: number
  attachments: number
  remainingTime?: number
  onCancel?: (
    e: React.MouseEvent<HTMLButtonElement>,
    dismiss: (id: string) => void
  ) => void
  onComplete?: (
    e: React.MouseEvent<HTMLButtonElement>,
    dismiss: (id: string) => void
  ) => void
}
 
export type ToasterProps = React.ComponentProps<typeof Sonner>
export type UploadSonnerProps = {
  progress: number
  attachments: number
  remainingTime?: number
  onCancel?: (
    e: React.MouseEvent<HTMLButtonElement>,
    dismiss: (id: string) => void
  ) => void
  onComplete?: (
    e: React.MouseEvent<HTMLButtonElement>,
    dismiss: (id: string) => void
  ) => void
}
 
export type ToasterProps = React.ComponentProps<typeof Sonner>