diff --git a/doc/PRODUCT.md b/doc/PRODUCT.md
index 97560d6d9ea..b47d36a50b4 100644
--- a/doc/PRODUCT.md
+++ b/doc/PRODUCT.md
@@ -232,3 +232,12 @@ to Tasks. A Views menu on the task list covers the inbox views (Mine, Unread,
Blocked, Recent, Everything) and the task-status views (All, Active, Backlog,
Done). Bare `/issues` opens the last-used view, defaulting to Mine; links that
carry a task filter open All. Old `/inbox` links redirect to the matching view.
+
+### CSV file previews
+
+Task attachment and workspace file tabs render CSV files as tables by default.
+The first record supplies column headers. Row numbers, row and column counts,
+and sticky headers help operators scan exports. Rendered and raw view icons
+remain next to download; raw view preserves the original source. The table
+shows up to 500 data rows and 100 columns, with a notice when the preview is
+limited. Download retains the complete file.
diff --git a/ui/src/components/CsvPreview.tsx b/ui/src/components/CsvPreview.tsx
new file mode 100644
index 00000000000..8a855aed044
--- /dev/null
+++ b/ui/src/components/CsvPreview.tsx
@@ -0,0 +1,41 @@
+import { useMemo } from "react";
+import { parseCsv } from "@/lib/csv-preview";
+
+const MAX_VISIBLE_ROWS = 500;
+const MAX_VISIBLE_COLUMNS = 100;
+
+export function CsvPreview({ text, title }: { text: string; title: string }) {
+ const parsed = useMemo(() => {
+ try { return { rows: parseCsv(text), error: null }; }
+ catch (error) { return { rows: [], error: (error as Error).message }; }
+ }, [text]);
+ if (parsed.error) return