<!-- Generated by scripts/gen-docs.mts from the JSDoc in registry/. Do not edit; run `pnpm run docs`. -->

# DescriptionList

One thing's details as pairs of a term and its value: a recipe's prep time and servings, an order's date and total, an account's email. On a phone each term sits above its details; from 640px the terms form a column beside them, with a line between the pairs.

```tsx
import { DescriptionList } from "@/components/ouro/description-list/description-list";
```

## Example

```tsx
<DescriptionList
  items={[
    { term: "Prep time", details: "20 minutes" },
    { term: "Cook time", details: "4 hours" },
    { term: "Serves", details: "6" },
  ]}
/>
```

## Use instead when

- Use `Table` instead to compare many things across the same columns, and `ItemGroup` for a list of things a person opens or acts on.

## Props

Type: `DescriptionListProps`.

| Prop | Type | Default | Description |
| --- | --- | --- | --- |
| `className` | `string` |  | Layout only: margins, width (`mt-6`, `max-w-2xl`). Appearance classes warn in development. |
| `items` (required) | `readonly DescriptionListItem[]` |  | The pairs, in order: `{ term, details }`. |
| `ref` | `Ref<HTMLDListElement>` |  | Reaches the rendered element. |
| `stackBelow` | `"sm" \| "md"` | `"sm"` | Below this breakpoint each term sits above its details, as on a phone; from it up, the terms form a column beside them. |

## Native attributes

Also accepts the attributes in React's `HTMLAttributes` (`id`, `aria-*`, event handlers), passed to the rendered element, except those named on this page.

## Don't use

These are not props. Passing one fails the type check with the fix in the error, and in development a console message names the fix.

- `children`: Not a prop. The list comes from `items`: `<DescriptionList items={[{ term, details }]}>`.
- `data`: Not a prop. Ouro UI uses `items`: `<DescriptionList items={[{ term, details }]}>`.

## `className` is for layout only

Pass margins, width and grid placement (`mt-4`, `w-full`, `col-span-2`). Your classes always win over Ouro UI's: DescriptionList merges `className` last with `cn` (tailwind-merge), so a class that conflicts with its own replaces it.[^layout-classes]

Appearance comes from props, not classes. In development, a class that sets appearance logs one warning per component instance, naming the prop to use instead. A class sets appearance when, after its variants (`hover:`, `sm:`) and any `!` are removed, it starts with `bg-`, `text-`, `border-`, `rounded-`, `shadow-`, `font-`, `ring-`, `from-`, `via-`, `to-`, `fill-` or `stroke-`, or is `border`, `rounded`, `shadow` or `ring`, or has a `dark:` variant. Text wrapping, overflow and table layout classes (`text-wrap`, `text-ellipsis`, `border-collapse`) are layout and do not warn.

Alignment classes (`text-center`) warn too: set alignment on a parent element.

## Types

### `DescriptionListItem`

One pair in a `DescriptionList`: what it is, and its value.

```ts
interface DescriptionListItem {
  /** What the details describe: "Prep time", "Email". */
  term: ReactNode;
  /** The value: text, a link, a badge. */
  details: ReactNode;

  /** Not a prop. Ouro UI uses `term`: `{ term: "Prep time", details: "20 minutes" }`. */
  label?: { 'Use term: "Prep time"': never };
  /** Not a prop. Ouro UI uses `details`: `{ term: "Prep time", details: "20 minutes" }`. */
  value?: { 'Use details: "20 minutes"': never };
  /** Not a prop. Ouro UI uses `details`: `{ term: "Prep time", details: "20 minutes" }`. */
  description?: { 'Use details: "20 minutes"': never };
}
```

[^layout-classes]: test:registry/ouro/components/ouro/description-list/description-list.test.tsx::DescriptionList > passes attributes and a ref through, and lets layout classes win verify:testExists(registry/ouro/components/ouro/description-list/description-list.test.tsx::DescriptionList > passes attributes and a ref through, and lets layout classes win)
