Alert
Persistent inline notifications for status, warnings, errors, and hints.
Playground
<Alert
title="Heads up!"
>
This is an alert with important information.
</Alert>01 Examples
An Alert takes an intent, a title and its message as
children. The icon and actions snippets and the dismiss
button are opt-in.
With Icon
<Alert intent="success" title="Deployment complete">
{#snippet icon()}
<CheckCircleIcon class="h-5 w-5" />
{/snippet}
Build #347 deployed to production in 42 seconds.
</Alert>
<Alert intent="danger" title="Build failed">
{#snippet icon()}
<DangerCircleIcon class="h-5 w-5" />
{/snippet}
TypeScript compilation failed with 3 errors. Check the logs for details.
</Alert>With Actions
<Alert intent="warning" title="Unsaved changes">
{#snippet icon()}
<WarningTriangleIcon class="h-5 w-5" />
{/snippet}
You have unsaved changes that will be lost if you navigate away.
{#snippet actions()}
<Button size="sm" variant="ghost" intent="warning">Discard</Button>
<Button size="sm" variant="filled" intent="warning">Save now</Button>
{/snippet}
</Alert>
<Alert intent="danger" variant="inline" title="Delete workspace?">
This action cannot be undone. All projects and data will be permanently removed.
{#snippet actions()}
<Button size="sm" variant="ghost" intent="neutral">Cancel</Button>
<Button size="sm" variant="filled" intent="danger">Delete</Button>
{/snippet}
</Alert>Dismissible
{#if !dismissedSoft}
<Alert
intent="primary"
title="Welcome back!"
dismissible
onDismiss={() => (dismissedSoft = true)}
>
You have 5 unread notifications since your last visit.
</Alert>
{/if}
{#if !dismissedInline}
<Alert
intent="success"
variant="inline"
title="Trial activated"
dismissible
onDismiss={() => (dismissedInline = true)}
>
Your 14-day Pro trial starts now. No credit card required.
</Alert>
{/if}
{#if dismissedSoft || dismissedInline}
<Button
size="sm"
variant="ghost"
intent="neutral"
onclick={() => {
dismissedSoft = false;
dismissedInline = false;
}}
>
Reset dismissed alerts
</Button>
{/if}02 Customization
Terminal log
<Alert
class="border-l-4 border-emerald-500 bg-neutral-950 font-mono"
slotClasses={{
title: 'font-bold text-emerald-400',
description: 'text-xs text-neutral-400'
}}
title="[OK] Build succeeded"
>
Compiled 847 modules in 1.2s · 0 warnings · 0 errors
</Alert>
<Alert
class="border-l-4 border-red-500 bg-neutral-950 font-mono"
slotClasses={{
title: 'font-bold text-red-400',
description: 'text-xs text-neutral-400'
}}
title="[ERR] Process exited"
>
SIGTERM received · pid 4821 · exit code 137
</Alert>This is one of five ways to restyle a block. See Customization for class, slotClasses, unstyled, preset and provider-level overrides.
03 Accessibility
Built-in ARIA
The role follows intent: danger and warning render role="alert", an assertive live region that cuts into
whatever a screen reader is saying; every other intent renders role="status", which waits for a pause, so a
confirmation does not interrupt a sentence. An explicit role wins over the derived one: role="alert" where a success message genuinely has to
interrupt, role="note" for a static callout that
announces nothing, role={undefined} where the
alert already sits inside a live region of your own. Dismissible alerts get a close button with
a localized label.
When the announcement happens
The two roles announce on different terms. An alert is announced when it enters the page, so mount
it in response to the event. A status is a polite
region, and a polite region has to exist before its content changes — an Alert that is the thing you mount when the request returns may never be announced at all.
Two ways out: keep a persistent role="status" wrapper
and fill it (auth's FormErrorAlert is built that way,
with the inner alert taking role={undefined}), or pass role="alert" where the interruption is what you want.
Keyboard
The dismiss button is focusable via Tab and activates with Enter / Space.
04 API Reference
15 propsProp | Type | Default | Description | |
|---|---|---|---|---|
actions | Snippet | — | Action buttons snippet | |
children | Snippet | — | Description content (children slot) | |
class | string | — | Custom CSS class | |
dismissible | boolean | false | Show dismiss/close button | |
icon | Snippet | — | Custom icon snippet (replaces default intent icon) | |
intent | primaryinfosuccesswarning +2 more | 'primary' | Semantic color intent — and the announced urgency with it: danger and warning
render role="alert" (assertive), every other intent role="status" (polite).
An explicit role overrides the derived one. | |
onDismiss | () => void | — | Callback when dismissed | |
preset | string | — | Apply a named preset registered via <BlocksProvider presets={{ Alert: {...} }}>.
Prefer this over class overrides when the requested look falls outside the
semantic intent palette — presets keep hover/active/dark-mode logic coherent
and make the custom look reusable across the project. | |
size | smmdlg | 'md' | Size | |
slotClasses | Partial<Record<AlertSlots, string>> | — | Per-slot class overrides. Slots: base | icon | content | title | description | actions | dismissButton | |
title | string | — | Alert title (bold header text) | |
unstyled | boolean | — | Remove default styles | |
variant | softinlinefilled | 'soft' | Visual style | |
...AlertVariants variant | VariantProps | — | Styling variants from AlertVariants | |
...HTMLAttributes<HTMLDivElement> inherited | HTMLAttributes | — | HTML attributes (excluding: 'title' | 'children') |
05 Types
Local type definitions used by this component.
Name | Kind | Category | Used by | Description | |
|---|---|---|---|---|---|
AlertProps | interface | props | 0 | Props interface for Alert component | |
AlertVariants | type | variant | 1 | — | |
AlertSlots | type | variant | 0 | Slot names derived from the tv() config — single source of truth for slotClasses. |
06 Installation
Import
import { Alert } from '@urbicon-ui/blocks';