File Browser
A folder-aware browser that descends into common prefixes via list({ delimiter }), with a breadcrumb trail and cursor-based load more - driven by useFiles.
Lists a folder with list({ delimiter }), so common prefixes surface as folders you can click into. A breadcrumb trail tracks where you are, and cursor-based “load more” pages through large folders. On adapters with no folder concept (capabilities().delimiter is false, e.g. UploadThing or Convex) it lists flat instead: every file under the current prefix, labelled with its path relative to it. A failed listing shows the error with a retry button rather than an empty folder.
"use client";
import { useState } from "react";
import { demoFiles } from "@/lib/demo-files";
import { FileBrowser } from "@/registry/files-sdk/file-browser/file-browser";
const Example = () => {
const files = demoFiles;
const [selected, setSelected] = useState<string>();
return (
<div className="flex w-full max-w-md flex-col gap-3">
<FileBrowser
files={files}
initialPrefix="documents/"
onSelect={(file) => setSelected(file.key)}
/>
{selected && (
<p className="text-muted-foreground text-xs">Selected: {selected}</p>
)}
</div>
);
};
export default Example;
Installation
npx shadcn@latest add https://files-sdk.dev/r/file-browser.jsonUsage
import { useFiles } from "files-sdk/react";
import { FileBrowser } from "@/components/files-sdk/file-browser";
export function Browser() {
const files = useFiles({ endpoint: "/api/files" });
return (
<FileBrowser
files={files}
initialPrefix="photos/"
onSelect={(file) => console.log(file.key)}
/>
);
}
Folders come straight from list()’s prefixes, which the gateway returns whenever the adapter supports a delimiter; the component reads capabilities() once on mount to decide which listing to use. The component owns its own navigation state; pass onSelect to react to file clicks (open a preview, generate a share link, etc.).
Each file row also carries a File Actions menu — download, copy, rename, move and delete — unless you pass readOnly. Mutations re-list the current folder automatically; pass onChanged to refresh anything else (a Trash Bin, a usage meter) alongside it.
Props
filesUseFilesResult
A `useFiles()` instance — folders and files are listed through it.
UseFilesResultinitialPrefix?string
Folder to open on mount, e.g. `"photos/"`. Defaults to the root.
stringdelimiter?string
Delimiter that marks a folder boundary. Default `"/"`.
stringonSelect?(file: StoredFile) => void
Called when a file row (not a folder) is clicked.
(file: StoredFile) => voidonChanged?() => void
Called after a successful copy/rename/move/delete from a row's actions menu.
() => voidreadOnly?boolean
Hide the per-file actions menu.
booleanclassName?string
string