HextaUI

Toast: Promise

toast.promise shows a spinner, then turns into a success or error toast in place, with the icon popping in as it changes.

"use client"

import { Button } from "@/components/ui/button"
import { toast } from "@/components/ui/toast"

let attempt = 0

function deploy() {
  attempt += 1
  const fails = attempt % 2 === 0
  return new Promise<{ url: string }>((resolve, reject) =>
    setTimeout(
      () =>
        fails
          ? reject(new Error("Build failed"))
          : resolve({ url: "hextaui.com" }),
      1800
    )
  )
}

export function ToastPromise() {
  return (
    <Button
      variant="outline"
      onClick={() =>
        toast.promise(deploy(), {
          loading: "Deploying…",
          success: (data) => ({
            title: "Deployed",
            description: `Live at ${data.url}`,
          }),
          error: (error) => ({
            title: "Deploy failed",
            description: error instanceof Error ? error.message : "Try again.",
          }),
        })
      }
    >
      Deploy (fails every other time)
    </Button>
  )
}

This adds the example as components/examples/toast/promise.tsx, together with the Toast component and the HextaUI theme tokens it needs.

pnpm dlx shadcn@latest add https://hextaui.com/r/toast-promise.json

To add only the component, follow the Toast installation.

See them all, with keyboard support and accessibility notes, on the Toast page.