# How to Use the shadcn Search Command to Find Components in the Registry

> Easily find shadcn components with the search command. Query built-in or custom registries using fuzzy matching for quick CLI or API access to paginated JSON results.

- Repository: [shadcn-ui/ui](https://github.com/shadcn-ui/ui)
- Tags: how-to-guide
- Published: 2026-02-26

---

**The `shadcn search` command (aliased as `list`) queries any Shadcn registry—built-in or custom—using fuzzy matching against component names and descriptions, returning paginated JSON results via the CLI or programmatic API.**

The shadcn search command is a core feature of the `shadcn-ui/ui` CLI that enables developers to discover installable UI components without browsing documentation. Whether you are targeting the official `@shadcn` registry or a privately hosted custom registry, the command handles configuration loading, registry validation, and fuzzy search execution through a pipeline defined in the source code.

## Understanding the shadcn Search Command Architecture

### CLI Registration and Entry Point

The search command is registered in the global CLI entry point at [`packages/shadcn/src/index.ts`](https://github.com/shadcn-ui/ui/blob/main/packages/shadcn/src/index.ts) (lines 32-39). It is added alongside other commands like `init`, `add`, and `diff`:

```typescript
program
  .addCommand(init)
  .addCommand(create)
  .addCommand(add)
  .addCommand(diff)
  .addCommand(view)
  .addCommand(search)   // Registers 'search' and 'list' aliases
  .addCommand(migrate)

```

### Command Parsing and Configuration

The command implementation resides in [`packages/shadcn/src/commands/search.ts`](https://github.com/shadcn-ui/ui/blob/main/packages/shadcn/src/commands/search.ts) (starting at line 25). It accepts several options:

- `--cwd <path>`: Working directory (defaults to `process.cwd()`)
- `--query <text>`: Fuzzy search string for filtering components
- `--limit <number>`: Maximum results to return (default 100)
- `--offset <number>`: Number of results to skip for pagination

The command first loads the local [`components.json`](https://github.com/shadcn-ui/ui/blob/main/components.json) configuration. If the file is missing or incomplete, it constructs a **shadow config** using defaults (`style: "new-york"`) to ensure the search pipeline always has valid configuration (lines 66-75).

### Registry Resolution and Validation

Before executing the search, the command normalizes registry identifiers through `ensureRegistriesInConfig` (lines 88-99). This helper:

1. Converts namespace-style registries (e.g., `@shadcn`) to their full registry paths (`@shadcn/registry`)
2. Validates that custom URLs are properly formatted
3. Merges new registries into the configuration without writing to disk (`writeFile: false`)

The command then validates all registries using `validateRegistryConfigForItems` (line 101) to ensure they can serve component metadata.

### Search Execution and Fuzzy Matching

The core search logic lives in [`packages/shadcn/src/registry/search.ts`](https://github.com/shadcn-ui/ui/blob/main/packages/shadcn/src/registry/search.ts) (lines 8-61). The `searchRegistries` function performs the following steps:

1. **Fetch registry data**: For each registry, it calls `getRegistry` (from [`registry/api.ts`](https://github.com/shadcn-ui/ui/blob/main/registry/api.ts)), which downloads and validates the registry's [`components.json`](https://github.com/shadcn-ui/ui/blob/main/components.json) against `registrySchema`.
2. **Flatten items**: Maps each registry's items to a uniform structure including `name`, `type`, `description`, `registry`, and `addCommandArgument`.
3. **Fuzzy filtering**: If a query is provided, the internal `searchItems` helper (lines 76-104) uses **fuzzysort** to match against both `name` and `description` fields.
4. **Pagination**: Applies `offset` and `limit` to the results, returning a pagination object with `total`, `offset`, `limit`, and `hasMore` flags.

The final output is validated against `searchResultsSchema` and returned as JSON.

## Using the shadcn Search Command: Practical Examples

### Basic CLI Usage

To search the official registry for button components:

```bash
npx shadcn search @shadcn -q button

```

This returns a JSON array of components matching "button" in their name or description.

### Advanced Filtering and Pagination

For large registries, use pagination to browse results incrementally:

```bash

# Get 5 results, skipping the first 10

npx shadcn search @shadcn -q modal -l 5 -o 10

```

The output includes a `pagination` object indicating if more results are available via `hasMore: true`.

### Searching Multiple Registries

You can query multiple registries simultaneously by providing additional arguments:

```bash
npx shadcn search @shadcn https://example.com/my-registry -q card

```

The command normalizes both namespace-style (`@shadcn`) and full URL registries before executing the search.

### Programmatic Usage in Node.js

You can import the search functionality directly in scripts for custom tooling:

```typescript
import { searchRegistries } from "@shadcn/ui/registry/search"
import { getConfig } from "@shadcn/ui/utils/get-config"

async function findComponents() {
  const config = await getConfig(process.cwd())
  
  const result = await searchRegistries(
    ["@shadcn"],                    // Registry identifiers
    { 
      query: "button", 
      limit: 10,
      offset: 0,
      config 
    }
  )
  
  console.log(result.items)           // Array of matching components
  console.log(result.pagination)    // { total, offset, limit, hasMore }
}

findComponents()

```

This approach leverages the same fuzzy search and validation logic used by the CLI.

## Key Source Files and Implementation Details

| File | Purpose | Location |
|------|---------|----------|
| [`packages/shadcn/src/index.ts`](https://github.com/shadcn-ui/ui/blob/main/packages/shadcn/src/index.ts) | CLI entry point that registers the `search` command | [View Source](https://github.com/shadcn-ui/ui/blob/main/packages/shadcn/src/index.ts#L32-L39) |
| [`packages/shadcn/src/commands/search.ts`](https://github.com/shadcn-ui/ui/blob/main/packages/shadcn/src/commands/search.ts) | Command definition, argument parsing, config loading, and registry validation | [View Source](https://github.com/shadcn-ui/ui/blob/main/packages/shadcn/src/commands/search.ts#L25-L44) |
| [`packages/shadcn/src/registry/search.ts`](https://github.com/shadcn-ui/ui/blob/main/packages/shadcn/src/registry/search.ts) | Core search algorithm including fuzzy matching and pagination | [View Source](https://github.com/shadcn/ui/blob/main/packages/shadcn/src/registry/search.ts#L8-L61) |
| [`packages/shadcn/src/registry/api.ts`](https://github.com/shadcn-ui/ui/blob/main/packages/shadcn/src/registry/api.ts) | Registry fetching and validation via `getRegistry` and `fetchRegistry` | [View Source](https://github.com/shadcn-ui/ui/blob/main/packages/shadcn/src/registry/api.ts#L43-L70) |
| [`packages/shadcn/src/schema.ts`](https://github.com/shadcn-ui/ui/blob/main/packages/shadcn/src/schema.ts) | Zod schemas for registry items and search results validation | [View Source](https://github.com/shadcn-ui/ui/blob/main/packages/shadcn/src/schema.ts) |

## Summary

- The **shadcn search command** (aliased as `list`) queries component registries using fuzzy matching against names and descriptions.
- It supports both built-in namespaces (`@shadcn`) and custom registry URLs, normalizing them through `ensureRegistriesInConfig`.
- The command implements **shadow configuration** to work with partial or missing [`components.json`](https://github.com/shadcn-ui/ui/blob/main/components.json) files.
- **Fuzzy search** is powered by `fuzzysort` in [`packages/shadcn/src/registry/search.ts`](https://github.com/shadcn-ui/ui/blob/main/packages/shadcn/src/registry/search.ts), with pagination controlled via `--limit` and `--offset` flags.
- Output is structured JSON suitable for piping to other tools or programmatic consumption via the `searchRegistries` API.

## Frequently Asked Questions

### What is the difference between shadcn search and shadcn list?

There is no functional difference—`list` is simply an alias for `search` registered in the CLI at [`packages/shadcn/src/index.ts`](https://github.com/shadcn-ui/ui/blob/main/packages/shadcn/src/index.ts). Both commands invoke the same underlying logic in [`packages/shadcn/src/commands/search.ts`](https://github.com/shadcn-ui/ui/blob/main/packages/shadcn/src/commands/search.ts) and accept identical options for querying, limiting, and offsetting results.

### How does the shadcn search command handle fuzzy matching?

The command uses the **fuzzysort** library to perform fuzzy string matching against both the `name` and `description` fields of registry items. This logic resides in the `searchItems` helper within [`packages/shadcn/src/registry/search.ts`](https://github.com/shadcn-ui/ui/blob/main/packages/shadcn/src/registry/search.ts) (lines 76-104). The matching is case-insensitive and tolerates typos, returning results ranked by relevance score.

### Can I search custom registries with the shadcn search command?

Yes. The command accepts any number of registry arguments, which can be either namespace-style identifiers like `@shadcn` or full URLs such as `https://example.com/my-registry`. The `ensureRegistriesInConfig` function in [`packages/shadcn/src/commands/search.ts`](https://github.com/shadcn-ui/ui/blob/main/packages/shadcn/src/commands/search.ts) normalizes these inputs and validates them before executing the search across all specified sources.

### How do I paginate results when using shadcn search?

Pagination is controlled via the `--limit` (`-l`) and `--offset` (`-o`) flags. For example, `npx shadcn search @shadcn -l 10 -o 20` returns 10 results starting from the 21st item. The JSON output includes a `pagination` object with `total`, `offset`, `limit`, and `hasMore` properties, allowing you to determine if additional pages exist.