@jeyabbalas/data-table

中文文档
0.10.1发布于 2026/11/01MITTypeScriptES Module零依赖构建来源已验证

一个客户端JavaScript库,用于使用DuckDB WASM的交互式、可探索的数据表

中文使用文档
文档目录23 节
  1. 安装
  2. 快速启动
  3. 调整容器大小
  4. 没有它会出什么问题
  5. 安装后调整大小
  6. 文档
  7. 框架的集成
  8. 反应
  9. Vue 3
  10. 功能切换
  11. 跳过CodeMirror
  12. 事件
  13. 主题
  14. CSS隔离
  15. 错误处理
  16. 多表、CSP和脱机
  17. 可访问性
  18. 自定义可视化
  19. 国际化
  20. 浏览器支持
  21. 高级:模块化API
  22. 开发
  23. 许可证

@jeyabbalas /数据表

一个客户端TypeScript库,用于交互式、可探索的数据表。 建立在 DuckDB WASM ——所有 分析完全在浏览器中运行,所以没有数据离开用户 机器。

尝试现场演示:打开CSV文件, JSON或Parquet文件,或Excel工作簿,演示程序将其转换,以及 探索它。参见 例子 和 键盘快捷键.

  • 逐列可视化(直方图、值计数、日期/时间直方图) 带笔刷/点击交叉滤镜;嵌套列获得非空/空摘要 Bar,它不过滤
  • 手动过滤UI每列+ raw-SQL WHERE 过滤器
  • 固定/隐藏/重新排序/调整列的大小;虚拟滚动
  • 派生列(SQL表达式或js提供的值向量) 同名依赖关系的替换
  • 稳定的合成 __rowid__ +精确只读值读取 (actions.getColumnValues, actions.getCellValue)为应用程序端行 对齐和图表馈送
  • 嵌套列(列表、数组、结构体、映射、联合、变体):DuckDB的 单元格中的文本,限制为32项;按值排序;CSV格式的标准JSON 在剪贴板上。对于它们和JSON列:精确过滤 比较文本(过滤器面板的,或) valueType: 'text' 在代码中),a 将整个值显示为键盘树的值检查器(F2 或者 双击)并将其复制为JSON,以及一个提取按钮,该按钮可以将任何 字段放入自己的列中(actions.addNestedFieldColumn 在代码)
  • 可编程的行/列/单元格注释-严重性层,弹出窗口, JSON往返,会话持久化,一百万次测试; F8 从1开始 到下一个,过滤器只显示带注释的行
  • 编程的列头工具提示- xss安全的结构化弹出窗口 (标题/描述/项目+枚举芯片)
  • 自定义列统计面板-替换内置的两行统计信息 在列标题中显示您自己的DOM和DuckDB查询 BaseStatsPanel +每个 StatsPanelRegistry
  • 公共CodeMirror SQL编辑器原语-嵌入模式-和 DuckDB-aware SQL编辑器在您自己的UI shell中的任何地方 createSqlExtensions / buildCompletionContext (filter-preset 编辑器、派生列向导、查询模板编辑器);生活或 文字模式,可选的库主题
  • 过滤器预设(导入/导出JSON)
  • 撤销/重做和IndexedDB会话持久性
  • CSV / JSON /拼花导出
  • 通过CSS自定义属性自动亮/暗模式

安装

npm install @jeyabbalas/data-table \
  @duckdb/duckdb-wasm \
  @codemirror/autocomplete @codemirror/commands @codemirror/lang-sql \
  @codemirror/language @codemirror/state @codemirror/view @lezer/highlight

@duckdb/duckdb-wasm 是必需的对等依赖项。这个 @codemirror/* 和 @lezer/* 包是可选的对等体——只有在使用时才安装它们 默认的SQL表达式编辑器(用于派生列和原始SQL过滤器)。 如果你提供你自己的 editorFactory 或者禁用这些功能,你可以 忽略它们。

为了严格的内容安全策略,自己提供DuckDB-WASM的文件 或者离线部署,安装 @duckdb/duckdb-wasm 在完全 1.33.1-dev57.0 (npm install --save-exact):看 CSP和离线部署.

快速启动

给容器一个有界的高度——表根据它进行虚拟化,并且 如果没有一个,虚拟化就会被悄无声息地打败。看到 调整容器大小.

<div id="my-table" style="height: 600px"></div>
import { createDataTable } from '@jeyabbalas/data-table';
import '@jeyabbalas/data-table/styles';

const table = await createDataTable({
  container: document.getElementById('my-table')!,
  source: myCsvFileOrUrl, // File | string URL | ArrayBuffer | Blob
});

table.on('filterChange', ({ filters, filteredRowCount }) => {
  console.log(`${filters.length} filters, ${filteredRowCount} rows match`);
});

// When unmounting (e.g., route change in an SPA):
await table.destroy();

对于文件选择器、URL输入或“交换数据集”流,只需挂载一次即可加载 关于用户操作——没有 destroy()/重现需要的舞蹈:

const table = await createDataTable({
  container: document.getElementById('my-table')!,
});

document.getElementById('file-picker')!.addEventListener('change', async (e) => {
  const file = (e.target as HTMLInputElement).files?.[0];
  if (file) await table.loadData(file);
});

loadData(source) 接受一个 File,绝对URL (https://…, http://…, file:, data:, blob:),与协议相关的URL (//host/…),根相对路径(/data.csv),一个点前缀的亲戚 路径(./data.csv, ../data.csv),一个 ArrayBuffer,一个 Blob,或内联 CSV/JSON内容(多行文本,或以 [ / {)。 相对url解析 window.location.href,所以。 <base href> 在 该页不适用于它们。二义字符串(单行) sample.csv 没有 例如,前导斜杠)抛出 LoadError 使用代码 SOURCE_AMBIGUOUS 而不是将文本解析为CSV内容。

在安装前探测所需的浏览器api:

import { checkBrowserSupport } from '@jeyabbalas/data-table';

const support = checkBrowserSupport();
if (!support.supported) {
  renderUnsupportedScreen(support.missing); // ['Worker', 'WebAssembly', …]
  return;
}
// safe to call createDataTable(...) here

图书馆是 ESM-only 因为v0.4.0。使用 import 语法(每个现代的) bundle - Vite, webpack 5, Rollup, esbuild, Bun -解析ESM构建 默认情况下)。它仅限浏览器,在SSR期间评估是不安全的 框架的集成 下面是客户端 安装模式。

调整容器大小

挂载容器必须具有限定高度。这是一个要求,不是 风格偏好-这是什么使表快。

表是虚拟化的:它只呈现适合视图的行,大约 ⌈containerHeight / rowHeight⌉ + 10 它们。它知道是多少 测量容器。因此,集装箱的高度就是旋钮 限制每个滚动,过滤和排序需要做多少工作- 600像素 无论数据集有1000行还是10行,容器都会呈现~29行 百万。

用以下两种方式给它一个高度:

<!-- 1. An explicit height — simplest, and always correct -->
<div id="my-table" style="height: 600px"></div>
/* 2. A flex or grid child that fills the space left over */
html,
body {
  height: 100%;
  margin: 0;
}
body {
  display: flex;
  flex-direction: column;
}
#my-table {
  flex: 1;
  min-height: 0; /* required — see below */
}

min-height: 0 在伸缩情况下不是可选的。Flex项默认为 min-height: auto,它拒绝缩小到内容的内在 高度——这个表的内容是数据集中的每一行。省略它 在下面的容器中,您将看到无限制生长失败 尺寸是正确的。这同样适用于网格子节点。

height: 100% 在容器上单独做什么,除非 每一个 祖先 视口也有一个已解决的高度。这是通常的原因 “有高度”的容器仍然表现得好像没有高度一样。

没有它会出什么问题

没有什么错误。表呈现,在一个小数据集上它看起来很好 这就是为什么这很容易发布,但之后会很痛苦。

如果高度没有限定,则库的根元素(height: 100%)解决 设置为内容大小。然后是滚动区域 生长到其顶高- min(rowCount × rowHeight, 15,000,000 px) 所以滚轮测量的“可见区域”是这样的 整个范围. 虚拟化被悄无声息地打败了:表为表中的每一行构建DOM range和问题块获取来填充所有这些。

在默认的32像素行高,帽对应于~468,750行,所以 这就是伤害饱和的地方,而不是随着数据集的变化而变化 安慰:成千上万的DOM行和大量的块读取 填满。标签页停滞不前,内存上升,滚动无法使用。与一个 有界容器相同的数据集呈现~29行并保持交互。

简并的情况正好相反:容器是 零高在 Mount根本不呈现任何行,并且库记录一个控制台警告 所以。容器,仅仅是 无限 没有警告,因为它有 完美的非零高度——只是错了。

安装后调整大小

在安装之前给集装箱一个高度,最好是一个高度 浏览器通过CSS (flex: 1, 100%, vh)除以你指定的1 在事实发生之后。坐垫:坐垫后变化的高度: 每当表的主体调整大小时,表就会计算出哪些行在视图中 窗口大小调整,面板在其上方折叠,或表安装在隐藏的 选项卡和后面显示的填充行没有滚动。

每一个 可运行的例子 使用flex模式,和 docs/integrations/cdn.md 有一个完整的 可复制粘贴的HTML启动器。

文档

完整文件位于 docs/。快速索引:

从这里开始

  • 快速入门(如上 可运行的例子
  • 调整容器大小 -虚拟表所针对的有界高度;在报告性能问题之前,请先阅读本文
  • AGENTS.md -面向代理的指南:能力矩阵,澄清问题清单,规范片段,陷阱

参考

  • API参考 -每个选项、事件、动作、错误、过滤器形状、派生列类型
  • 故障排除 - 46个错误代码和26个常见问题faq与修复片段

指南

概念

集成

来源

框架的集成

图书馆是 浏览器只 -它使用Web Workers, window, document, 和IndexedDB,在SSR期间评估不安全。挂载 表在框架的客户端生命周期钩子中。

反应

import { useEffect, useRef } from 'react';
import { createDataTable, type DataTable } from '@jeyabbalas/data-table';
import '@jeyabbalas/data-table/styles';

export function Table({ source }: { source: File | string }) {
  const hostRef = useRef<HTMLDivElement>(null);
  useEffect(() => {
    if (!hostRef.current) return;
    let cancelled = false;
    let instance: DataTable | undefined;
    void createDataTable({ container: hostRef.current, source }).then((t) => {
      if (cancelled) {
        void t.destroy();
        return;
      }
      instance = t;
    });
    return () => {
      cancelled = true;
      if (instance && !instance.isDestroyed()) void instance.destroy();
    };
  }, [source]);
  return <div ref={hostRef} style={{ height: 600 }} />;
}

这个 cancelled Flag处理效果之前重新运行的情况 createDataTable 解决了。 isDestroyed() 防止双重破坏 当React的严格模式在dev中双重调用效果时。

Vue 3

<script setup lang="ts">
import { onMounted, onBeforeUnmount, ref } from 'vue';
import { createDataTable, type DataTable } from '@jeyabbalas/data-table';
import '@jeyabbalas/data-table/styles';

const host = ref<HTMLElement | null>(null);
let table: DataTable | undefined;

onMounted(async () => {
  if (host.value) table = await createDataTable({ container: host.value, source: props.source });
});
onBeforeUnmount(async () => {
  if (table && !table.isDestroyed()) await table.destroy();
});
</script>

<template>
  <div ref="host" style="height: 600px" />
</template>

后 destroy(),公共方法(loadData, on, off, openExportDialog, clearSession, setColorScheme)把 DestroyedError. 检查 table.isDestroyed() 在调用长寿命闭包之前。

功能切换

所有功能都是默认开启的;通过 false 或者一个要自定义的配置对象:

选项默认的笔记
persistencetrue自动保存过滤器/排序/列到IndexedDB
presetstrue显示“预设”按钮,用于保存过滤器设置
undoRedotrueCtrl/Cmd+Z, Ctrl/Cmd+Shift+Z和Ctrl+Y键盘快捷键
expressionFiltertrue显示“表达式”(原始SQL)筛选按钮
derivedColumnstrue显示“+”, f(x) 和嵌套的/JSON提取按钮,以及值检查器的“添加为列”
visualizationstrue自动附加列标题图(直方图,值计数,…)
exportDialogtruetable.openExportDialog() 打开CSV/JSON/Parquet模式
annotationNavigationtrueF8 / Shift+F8 和 Alt+↓ / Alt+↑ 转到下一个/上一个注释

有关完整的选项界面(安装、worker、UI、自定义),请参见 文档/ api-reference.md # createdatatableoptions.

跳过CodeMirror

当两个 expressionFilter: false 和 derivedColumns: false 是固定的, 库在运行时不再达到codemmirror绑定的模态。的消费者 此配置可以省略 @codemirror/* 和 @lezer/highlight 同行 依赖项(已标记) optional 在 peerDependenciesMeta) -现代 打包器将模态块拆分为单独的运行时模块 无法到达的代码路径永远不会加载。编程API (actions.addFilter({ type: 'raw-sql' }), actions.addDerivedColumn, FilterPresetManager)一直在这种模式下工作。当旗子升起的时候 第一次点击SQL或派生列按钮现在获取一个小模态块 按需加载,而不是急切地将其加载到桌面安装上。

事件

订阅与 table.on(event, handler) -返回退订函数。 事件总线包括 ready, loadStart / loadProgress / loadComplete / loadError, filterChange, sortChange, selectionChange, columnChange, derivedChange ( kind: 'added' | 'removed' | 'replaced' | 'updated' 鉴别者和受影响者 columnName), undoChange, destroy,再加上 error 和 warning 对于可恢复的故障模式。注释突变 流经一个独立的 table.annotations.on('change', …) 频道-见 这个 注释指南。有效载荷类型 看到 文档/ api-reference.md #事件目录.

主题

所有颜色、间距、排版和z索引都由CSS自定义驱动 属性(74 --dt-* 令牌-覆盖整个调色板,大小比例, z索引堆叠阶梯、注释严重性色调和列标头 工具提示分层)。覆盖你关心的那些 :root,在…上 每个实例元素,或在运行时。

:root {
  --dt-primary: #10b981;
  --dt-radius: 4px;
  --dt-z-modal: 1500; /* raise above your app's modal layer */
  --dt-panel-width: 420px; /* widen filter / preset / derived-edit panels */
}

接着是明暗模式 prefers-color-scheme 默认情况下。通过 colorScheme: 'light' | 'dark' | 'auto' 强加一个主题或号召 table.setColorScheme(...) 在运行时;身体传送的情态保持同步。

看到 文档/指导/ theming.md 对于完整的 变量参考与亮/暗默认值并排,暗模式 作用域模型、堆栈阶梯深度挖掘和每个实例覆盖模式。

CSS隔离

所有选择器都带有 dt- 前缀。列拖动光标,CodeMirror 自动完成和模态堆叠都是有作用域的,所以它们不会碰撞 主持人的风格。为实现更严格的隔离(一页上有两个库副本), 严品牌墙),过关 classPrefix: 'myapp-dt' 每个选择器, 模式,并且工具提示以该前缀重新呈现。

阴影DOM故意不使用-模态传送到光DOM,所以他们 可以继承 --dt-* 变量 :root。将图书馆包裹在阴影中 如果你需要的话,把你自己根起来,然后转发主题变量+ portalTarget 相应的行动。

错误处理

每个错误都会扩展 DataTableError (延伸 Error). 订阅 这个 error 事件到由子系统路由,或到 warning 对非致命 退化等 STYLESHEET_MISSING / PERSISTENCE_UNAVAILABLE:

table.on('error', ({ error, source }) => {
  if (error.code === 'PARSE_FAILED') toast('Could not read that file.');
  else if (source === 'persistence') console.warn(error);
  else reportToSentry(error);
});

有关带有触发器和修复程序的错误代码的完整列表,请参见 文档/ troubleshooting.md.

多表、CSP和脱机

  • 多个表: 共享一个 WorkerBridge (可选) SessionStore / FilterPresetManager)以避免旋转两个DuckDB 实例。给每个表一个不同的名称 tableName 会话快照 不要互相攻击。
  • CSP /气隙式: 从您的原始文件中复制DuckDB-WASM文件 从 @duckdb/duckdb-wasm 精确地固定在一起 1.33.1-dev57.0,并通过 他们是 bridgeOptions.duckdbBundles (相对url解析 页面)。镜子DuckDB的 icu, parquet 和 json 扩展和集合 custom_extension_repository,并发送一个策略,与 'wasm-unsafe-eval' 和 worker-src 'self' blob:,每一个回应。

看到 代理。md§3 (h) 用于共享桥接 片段, CSP和离线部署 用于 自托管配方,和 文档/故障排除。md§4 当DuckDB未启动时。

可访问性

网格目标为WCAG 2.1 AA: role="grid" 与 aria-rowcount / aria-colcount,通过发布的单个游标 aria-activedescendant 和 由方向键(+)驱动 F2 要访问列的控件, Shift+F2 调整大小和重新排序,和 F8 去下一个 注释),一个不随 列数,礼貌 aria-live 关于过滤/排序/行计数的通知 更改,焦点陷阱+ escape-to-close的每个模式,和 axe-core 作为CI 门。已知范围外:单元内编辑,移动触摸手势,RTL。

自定义可视化

子类 BaseVisualization (从 /advanced),并在网上登记 每个 VisualizationRegistry:

import { createDataTable, VisualizationRegistry } from '@jeyabbalas/data-table';
import { BaseVisualization } from '@jeyabbalas/data-table/advanced';

class MyViz extends BaseVisualization {
  /* a constructor that starts the first fetch, fetchData(), render() and six input handlers */
}

const registry = new VisualizationRegistry();
registry.register({
  name: 'my-viz',
  isApplicable: (t) => t === 'float',
  constructor: MyViz,
  priority: 10,
});
const table = await createDataTable({ container, source, visualizationRegistry: registry });

可运行版本 例子/ 08-custom-visualization.

国际化

每个面向用户的字符串都来自类型 Strings 对象。通过一项 DeepPartial<Strings> 通过 messages;丢失的钥匙回到英语 默认值。消息在构造时一次解析—重新创建表 切换语言环境。

await createDataTable({
  container,
  source,
  messages: {
    common: { close: 'Fermer', apply: 'Appliquer' },
    filters: { panelTitle: 'Filtres' },
  },
});

可运行版本 例子/ 07-i18n-french.

浏览器支持

API用于
WorkerDuckDB运行在一个专用的worker中
WebAssemblyDuckDB被编译成Wasm
IndexedDB会话持久性(跳过) persistence: false)
ResizeObserver列大小调整,响应式可视化
BigIntDuckDB整型列作为BigInt跨越worker边界
structuredClone桥接快照结果集

大概是Chrome/Edge 98+, Firefox 94+, Safari 15.4+。在运行时探测 checkBrowserSupport() 或者选择通过自动快速初始化 strictBrowserCheck: true. 看到 文档/ api-reference.md # browser-support-probe.

高级:模块化API

根条目(@jeyabbalas/data-table)暴露了立面加上一个小的 一套稳定的挂钩。想要直接编排堆栈的高级用户 自定义可视化生命周期,无头使用,驱动桥 自己——可以从 /advanced:

import {
  TableContainer,
  FilterBar,
  ExportDialog,
  BaseVisualization /* … */,
} from '@jeyabbalas/data-table/advanced';

这个 /advanced 表面以稳定性换取灵活性:的确如此 不 由与根条目相同的semver保证覆盖。看到 文档/ api-reference.md # tier-2-exports 查看完整的符号列表。

开发

看到 DEVELOPMENT.md 对于本地设置、测试、构建管道和发布工作流。看到 CONTRIBUTING.md 了解如何报告错误和提交更改。

许可证

麻省理工学院

版本与发布记录

@jeyabbalas/data-table 共发布 12 个版本,首次发布于 2026/04/28;过去 12 个月发布了 12 个版本。最新版本附带 npm provenance 构建来源证明,可追溯到公开的 CI 构建记录。

版本发布日期距今
0.10.1latest2026/11/011 天前
0.10.02026/10/1123 天前
0.9.02026/10/0925 天前
0.9.0-next.0next2026/09/271 个月前
0.8.02026/09/271 个月前
0.7.02026/08/072 个月前

关于 @jeyabbalas/data-table 的常见问题

@jeyabbalas/data-table 是什么?

一个客户端JavaScript库,用于使用DuckDB WASM的交互式、可探索的数据表

如何安装 @jeyabbalas/data-table?

在项目目录运行 npm install @jeyabbalas/data-table,或使用 pnpm add / yarn add / bun add。它还需要宿主项目提供 peer 依赖:@duckdb/duckdb-wasm(^1.33.1-dev57.0)。npm 7 及以上与 pnpm 8 及以上默认会自动安装必需的 peer 依赖,Yarn 需要手动安装。

@jeyabbalas/data-table 支持 TypeScript 吗?

支持。包内自带 TypeScript 类型声明(package.json 声明了 types 入口),安装后即可获得类型提示,无需再安装 @types 包。

@jeyabbalas/data-table 支持 ESM 还是 CommonJS?

以 ES Module 形式发布,推荐使用 import 引入。在 CommonJS 项目中,Node.js 20.19+ / 22.12+ 可以直接 require() 不含顶层 await 的 ES Module,更早的版本需要改用动态 import()。

@jeyabbalas/data-table 需要什么版本的 Node.js?

package.json 的 engines 字段要求 Node.js >=20。版本不符时 npm 默认只给出警告,开启 engine-strict 后会拒绝安装。

@jeyabbalas/data-table 可以商用吗?

@jeyabbalas/data-table 使用 MIT 许可。宽松许可:允许商业使用、修改和再分发,通常只需在分发时保留原版权与许可声明。以上为概括,不构成法律意见,请以许可原文为准。

@jeyabbalas/data-table 还在维护吗?

最新版本 0.10.1 发布于 2026/11/01(1 天前);至今共发布 12 个版本,其中过去 12 个月发布了 12 个;首次发布于 2026/04/28。发布频率只是参考信号:功能稳定的工具可能很少需要更新,建议结合源码仓库的 issue 和提交记录判断。