浏览器电子表格解决方案:Luckysheet、Univer

Luckysheet

梦数科技,英文名Dream Num,JavaScript+CSS+HTML实现、开源(GitHub,16.6K Star,2.6K Fork)电子表格解决方案。项目已于25年10月30日归档,官方建议使用升级版Univer。官方文档。

特性:

  • 格式设置:样式、条件格式、文本对齐与旋转、文本截断、溢出、自动换行、多种数据类型、单元格分割样式
  • 单元格:拖放、填充柄、多选、查找与替换、定位、合并单元格、数据验证
  • 行与列:隐藏、插入、删除行或列、冻结、拆分文本
  • 操作:撤销、重做、复制、粘贴、剪切、快捷键、格式刷、拖放选择
  • 公式与函数:内置公式、远程公式和自定义公式
  • 表格:筛选、排序
  • 增强功能:数据透视表、图表、评论、协同编辑、插入图片、矩阵计算、截图、复制为其他格式、Excel导入导出等

生态

项目 描述
Luckysheet Vue 在Vue CLI3项目中使用
Luckysheet Vue3 在Vue3+Vite项目
Luckysheet React 在React项目
Luckyexcel Node 在Koa2中
Luckysheet Server Java后端
Luckysheet Server Starter LuckySheet Server Docker部署启动模板

Java

LuckysheetServer:开源(GitHub,459 Star,179 Fork)Java后端,Docker部署启动模板。

采用Maven多模块化设计

创建数据库

sql 复制代码
CREATE DATABASE luckysheetdb

创建序列

sql 复制代码
DROP SEQUENCE IF EXISTS "public"."luckysheet_id_seq";
CREATE SEQUENCE "public"."luckysheet_id_seq"
INCREMENT 1
MINVALUE  1
MAXVALUE 9999999999999
START 1
CACHE 10;

创建表

sql 复制代码
DROP TABLE IF EXISTS "public"."luckysheet";
CREATE TABLE "luckysheet" (
  "id" int8 NOT NULL,
  "block_id" varchar(200) COLLATE "pg_catalog"."default" NOT NULL,
  "row_col" varchar(50),
  "index" varchar(200) COLLATE "pg_catalog"."default" NOT NULL,
  "list_id" varchar(200) COLLATE "pg_catalog"."default" NOT NULL,
  "status" int2 NOT NULL,
  "json_data" jsonb,
  "order" int2,
  "is_delete" int2
);
CREATE INDEX "block_id" ON "public"."luckysheet" USING btree (
  "block_id" COLLATE "pg_catalog"."default" "pg_catalog"."text_ops" ASC NULLS LAST,
  "list_id" COLLATE "pg_catalog"."default" "pg_catalog"."text_ops" ASC NULLS LAST
);
CREATE INDEX "index" ON "public"."luckysheet" USING btree (
  "index" COLLATE "pg_catalog"."default" "pg_catalog"."text_ops" ASC NULLS LAST,
  "list_id" COLLATE "pg_catalog"."default" "pg_catalog"."text_ops" ASC NULLS LAST
);
CREATE INDEX "is_delete" ON "public"."luckysheet" USING btree (
  "is_delete" "pg_catalog"."int2_ops" ASC NULLS LAST
);
CREATE INDEX "list_id" ON "public"."luckysheet" USING btree (
  "list_id" COLLATE "pg_catalog"."default" "pg_catalog"."text_ops" ASC NULLS LAST
);
CREATE INDEX "order" ON "public"."luckysheet" USING btree (
  "list_id" COLLATE "pg_catalog"."default" "pg_catalog"."text_ops" ASC NULLS LAST,
  "order" "pg_catalog"."int2_ops" ASC NULLS LAST
);
CREATE INDEX "status" ON "public"."luckysheet" USING btree (
  "list_id" COLLATE "pg_catalog"."default" "pg_catalog"."text_ops" ASC NULLS LAST,
  "status" "pg_catalog"."int2_ops" ASC NULLS LAST
);
ALTER TABLE "public"."luckysheet" ADD CONSTRAINT "luckysheet_pkey" PRIMARY KEY ("id");

插入初始化语句

sql 复制代码
INSERT INTO "public"."luckysheet" VALUES (nextval('luckysheet_id_seq'), 'fblock', '', '1', '1079500#-8803#7c45f52b7d01486d88bc53cb17dcd2c3', 1, '{"row":84,"name":"Sheet1","chart":[],"color":"","index":"1","order":0,"column":60,"config":{},"status":0,"celldata":[],"ch_width":4748,"rowsplit":[],"rh_height":1790,"scrollTop":0,"scrollLeft":0,"visibledatarow":[],"visibledatacolumn":[],"jfgird_select_save":[],"jfgrid_selection_range":{}}', 0, 0);
INSERT INTO "public"."luckysheet" VALUES (nextval('luckysheet_id_seq'), 'fblock', '', '2', '1079500#-8803#7c45f52b7d01486d88bc53cb17dcd2c3', 0, '{"row":84,"name":"Sheet2","chart":[],"color":"","index":"2","order":1,"column":60,"config":{},"status":0,"celldata":[],"ch_width":4748,"rowsplit":[],"rh_height":1790,"scrollTop":0,"scrollLeft":0,"visibledatarow":[],"visibledatacolumn":[],"jfgird_select_save":[],"jfgrid_selection_range":{}}', 1, 0);
INSERT INTO "public"."luckysheet" VALUES (nextval('luckysheet_id_seq'), 'fblock', '', '3', '1079500#-8803#7c45f52b7d01486d88bc53cb17dcd2c3', 0, '{"row":84,"name":"Sheet3","chart":[],"color":"","index":"3","order":2,"column":60,"config":{},"status":0,"celldata":[],"ch_width":4748,"rowsplit":[],"rh_height":1790,"scrollTop":0,"scrollLeft":0,"visibledatarow":[],"visibledatacolumn":[],"jfgird_select_save":[],"jfgrid_selection_range":{}}', 2, 0);

实战

官方提供在线演示环境

支持导入本地文件

或直接使用官方提供的演示数据文件(上上图)。

另一个在线演示环境

HTML极简示例:

html 复制代码
<!DOCTYPE html>
<html lang="zh-CN">
<head>
  <meta charset="UTF-8" />
  <title>Luckysheet 极简示例</title>
  <link rel="stylesheet" href="https://cdn.jsdelivr.net/npm/luckysheet@2.1.13/dist/plugins/css/pluginsCss.css" />
  <link rel="stylesheet" href="https://cdn.jsdelivr.net/npm/luckysheet@2.1.13/dist/plugins/plugins.css" />
  <link rel="stylesheet" href="https://cdn.jsdelivr.net/npm/luckysheet@2.1.13/dist/css/luckysheet.css" />
  <link rel="stylesheet" href="https://cdn.jsdelivr.net/npm/luckysheet@2.1.13/dist/assets/iconfont/iconfont.css" />
  <script src="https://cdn.jsdelivr.net/npm/luckysheet@2.1.13/dist/plugins/js/plugin.js"></script>
  <script src="https://cdn.jsdelivr.net/npm/luckysheet@2.1.13/dist/luckysheet.umd.js"></script>
</head>
<body>
  <div id="luckysheet" style="width: 100%; height: 600px;"></div>
  <script>
    luckysheet.create({
      container: 'luckysheet',
      lang: 'zh',
      data: [
        {
          name: 'Sheet1',
          celldata: [
            { r: 0, c: 0, v: 'Hello' },
            { r: 0, c: 1, v: 'Luckysheet' }
          ]
        }
      ]
    });
  </script>
</body>
</html>

Univer

官网、TypeScript实现、开源(GitHub,22.3K Star,1.9K Fork)SDK、插件化架构、Canvas渲染引擎、公式引擎和统一Facade API, 可用于浏览器和Node.js,提供电子表格、文档和演示文稿体验所需的基础能力,不强制使用托管应用或固定UI。官方文档(https://docs.univer.ai]。

能力:

  • 大型场景也流畅:Canvas渲染与独立公式引擎,让复杂工作簿保持响应
  • 插件化扩展:按需组合、替换、延迟加载或扩展能力,无需引入整套功能
  • Headless AI基建:在Node.js中运行工作簿和文档逻辑,为Agent、自动化和服务端流程提供底层能力
  • 面向产品集成:框架适配器、Facade API、预设和无头运行时,覆盖真实集成路径
  • 主题就绪:UI组件和渲染引擎都支持浅色与深色主题
  • 统一Facade API:共享一致API,在浏览器和Node.js中操作工作簿、区域、公式和文档

优势:

  • 同构设计:既可在浏览器中运行UI应用,也可在Node.js中运行无头处理逻辑
  • 插件优先架构:每个能力都以可组合插件的形式提供,功能可以添加、移除、替换或延迟加载
  • Preset Mode便于快速集成:希望快速获得可运行应用时,可使用本仓库presets/中的预设插件集合
  • Plugin Mode提供完整控制:当你需要自定义加载、更小包体或深度集成时,可手动组合包和插件
  • Facade API:通过更高层API操作工作簿、工作表、区域、文档、公式、命令和事件
  • Canvas渲染引擎:支持大型可编辑文档界面,并在多种文档类型之间复用渲染层
  • 可扩展UI:支持React、Vue、Web Components和不同框架下的应用外壳集成

产品

领域 开源能力 UniverPro扩展
Sheets 工作簿、工作表、区域、选择、公式、数字格式、筛选、排序、数据验证、条件格式、超链接、评论、查找替换、批注、表格、绘图集成和可扩展UI插件。 实时协同、编辑历史、导入导出、打印、图表、数据透视表、迷你图、分级显示、形状、单元格内图形、数据连接器、服务端计算和增强公式能力
Docs 富文本文档模型、编辑UI、列表、超链接、绘图集成、评论、快捷插入和共享文档架构。 协同、导入导出、打印、增强表格和列表、分栏、提示块、代码块、引用块、形状和远程评论资源
Slides 演示文稿数据模型和编辑UI包。 Pro演示文稿模型和UI、幻灯片导入导出、图表和表格模型/UI插件,以及共享形状编辑基础设施
Bases 基于Univer的插件、命令和模型架构构建自定义结构化数据体验。 Base数据库模型、命令、公式集成、工作台UI、字段编辑器和渲染引擎视图
Runtime 浏览器应用、Node.js无头使用、WebWorker/RPC模式、多实例使用和服务端自动化。 协同客户端/服务端包、Node.js协同客户端、Pro服务端服务、SSR、计算委托、服务端计算和changeset回放工具
Integrations React、Vue、WebComponents、框架模板、主题、本地化和自定义插件。 Pro预设和企业部署包

解读:Sheets、Docs和Slides基于Univer的共享架构,分别提供电子表格、文档和演示文稿编辑能力,并使用一致的插件系统、命令系统和Facade API。

生态

包括:

  • 核心SDK:dream-num/univer
  • Presets:本仓库的presets/,面向浏览器和Node.js应用的预设插件集合
  • AI agent skills:dream-num/univer-sdk-skills,供Agent使用的可复用说明,覆盖Univer集成、Pro功能、插件开发和Node后端
  • Web SDK:在浏览器和Node.js中提供嵌入式编辑器与无头处理能力
  • Server SDK:将协作与文件转换接入应用的存储、身份认证和权限系统
  • AI SDK:通过Agent工作流检查、编辑和验证办公内容
  • AI原生spreadsheets:dream-num/univer-mcp,用于通过自然语言驱动Univer Sheets的Univer Platform、MCP集成

基于Univer Office SDK构建的开源项目

项目 说明
Univer Office for DeepSeek Harness 面向DeepSeek Harness的办公插件,支持关联内容、验证和用于Agent协作的独立Worktree
Univer CLI 供Agent创建、编辑、检查和交付办公内容的本地命令行工作空间
Univer Office for WorkBuddy 面向WorkBuddy的本地办公集成,支持MCP预览和草稿审阅。目前为开发预览版
Univer Office for OpenClaw 在OpenClaw中创建、审阅和交付办公内容的工具
Univer Workspace 支持自行部署的开源工作空间,人与Agent可在其中创建、协作处理和审阅办公内容。开发者可参考完整实现,学习如何集成SDK,并构建个人产品

Mode

包括3种模式

选择 适用场景
Plugin Mode 需严格控制包、已配置的依赖、延迟加载或自定义运行时组合
Preset Mode 希望用最少配置获得可运行的Sheets、Docs或Node设置
Headless Mode 需要在没有UI的情况下进行服务端工作簿/文档处理、公式计算或自动化

同一Univer协调发布线中的@univerjs/* SDK包应保持版本一致。@univerjs/icons、@univerjs/icons-svg等独立发布的包应使用各包清单声明的兼容版本,而不是跟随SDK版本。使用Univer Pro时,也请让@univerjs-pro/*与对应的协调发布线保持一致。

Plugin Mode

可获得完整的产品能力覆盖并精确控制组合方式,能够更底层地控制包、样式导入、locale合并、Facade API注册和插件配置。

bash 复制代码
pnpm add @univerjs/core @univerjs/design @univerjs/docs @univerjs/docs-ui @univerjs/engine-formula @univerjs/engine-render @univerjs/sheets @univerjs/sheets-formula @univerjs/sheets-formula-ui @univerjs/sheets-numfmt @univerjs/sheets-numfmt-ui @univerjs/sheets-ui @univerjs/ui

示例:

ts 复制代码
import { LocaleType, mergeLocales, Univer } from '@univerjs/core'
import { FUniver } from '@univerjs/core/facade'
import DesignEnUS from '@univerjs/design/locale/en-US'
import { UniverDocsPlugin } from '@univerjs/docs'
import { UniverDocsUIPlugin } from '@univerjs/docs-ui'
import DocsUIEnUS from '@univerjs/docs-ui/locale/en-US'
import { UniverFormulaEnginePlugin } from '@univerjs/engine-formula'
import { UniverRenderEnginePlugin } from '@univerjs/engine-render'
import { UniverSheetsPlugin } from '@univerjs/sheets'
import SheetsEnUS from '@univerjs/sheets/locale/en-US'
import { UniverSheetsFormulaPlugin } from '@univerjs/sheets-formula'
import SheetsFormulaEnUS from '@univerjs/sheets-formula/locale/en-US'
import { UniverSheetsFormulaUIPlugin } from '@univerjs/sheets-formula-ui'
import SheetsFormulaUIEnUS from '@univerjs/sheets-formula-ui/locale/en-US'
import { UniverSheetsNumfmtPlugin } from '@univerjs/sheets-numfmt'
import { UniverSheetsNumfmtUIPlugin } from '@univerjs/sheets-numfmt-ui'
import SheetsNumfmtUIEnUS from '@univerjs/sheets-numfmt-ui/locale/en-US'
import { UniverSheetsUIPlugin } from '@univerjs/sheets-ui'
import SheetsUIEnUS from '@univerjs/sheets-ui/locale/en-US'
import { UniverUIPlugin } from '@univerjs/ui'
import UIEnUS from '@univerjs/ui/locale/en-US'

import '@univerjs/design/lib/index.css'
import '@univerjs/ui/lib/index.css'
import '@univerjs/docs-ui/lib/index.css'
import '@univerjs/sheets-ui/lib/index.css'
import '@univerjs/sheets-formula-ui/lib/index.css'
import '@univerjs/sheets-numfmt-ui/lib/index.css'

import '@univerjs/engine-formula/facade'
import '@univerjs/ui/facade'
import '@univerjs/sheets/facade'
import '@univerjs/sheets-ui/facade'
import '@univerjs/sheets-formula/facade'
import '@univerjs/sheets-numfmt/facade'

const univer = new Univer({
  locale: LocaleType.EN_US,
  locales: {
    [LocaleType.EN_US]: mergeLocales(
      DesignEnUS,
      UIEnUS,
      DocsUIEnUS,
      SheetsEnUS,
      SheetsUIEnUS,
      SheetsFormulaEnUS,
      SheetsFormulaUIEnUS,
      SheetsNumfmtUIEnUS,
    ),
  },
})

univer.registerPlugin(UniverRenderEnginePlugin)
univer.registerPlugin(UniverFormulaEnginePlugin)
univer.registerPlugin(UniverUIPlugin, { container: 'app' })
univer.registerPlugin(UniverDocsPlugin)
univer.registerPlugin(UniverDocsUIPlugin)
univer.registerPlugin(UniverSheetsPlugin)
univer.registerPlugin(UniverSheetsUIPlugin)
univer.registerPlugin(UniverSheetsFormulaPlugin)
univer.registerPlugin(UniverSheetsFormulaUIPlugin)
univer.registerPlugin(UniverSheetsNumfmtPlugin)
univer.registerPlugin(UniverSheetsNumfmtUIPlugin)

const univerAPI = FUniver.newAPI(univer)
univerAPI.createWorkbook({})

Preset Mode

对于受支持的Sheets、Docs和Node配置,提供更简短的预设方案。一组经过整理的Univer插件集合,包含所需的Facade API注册和样式。

bash 复制代码
pnpm add @univerjs/presets @univerjs/preset-sheets-core

示例:

ts 复制代码
import { UniverSheetsCorePreset } from '@univerjs/preset-sheets-core'
import UniverPresetSheetsCoreEnUS from '@univerjs/preset-sheets-core/locales/en-US'
import { createUniver, LocaleType, mergeLocales } from '@univerjs/presets'

import '@univerjs/preset-sheets-core/lib/index.css'

const { univerAPI } = createUniver({
  locale: LocaleType.EN_US,
  locales: {
    [LocaleType.EN_US]: mergeLocales(UniverPresetSheetsCoreEnUS),
  },
  presets: [
    UniverSheetsCorePreset({
      container: 'app',
    }),
  ],
})
univerAPI.createWorkbook({})

原理

仓库结构

复制代码
.
├── packages/	核心包、引擎、文档类型、UI 插件和功能插件
├── examples/	用于本地浏览器开发的一体化 Vite 工作台
├── common/		共享内部工具、storybook 和工具函数
├── tests/		其他集成测试项目
└── docs/		架构说明、图片和仓库内文档

兼容性

  • 浏览器运行时:Univer 的编译目标是 Chrome 88,并尽力支持 Edge >=88、Firefox >=90、Chrome >=88、Safari >=14.1 和 Electron >=12。
  • Polyfills:Univer 依赖 Intl.Segmenter。如果目标浏览器或运行时不支持,请添加 @formatjs/intl-segmenter 等 polyfill。
  • 构建工具:推荐使用 Vite、esbuild 或 Webpack 5。如果构建工具不支持 package.json 中的 exports 字段(Webpack 4 中较常见),可能需要额外配置路径映射。
  • React:Univer 的视图层基于 React 18 构建,支持 React 18 和 19,并对 React 16.9+ 与 17 提供最低限度的兼容支持。
  • Node.js运行时:Headless Univer支持Node.js>=18.17.0,开发本monorepo需要Node.js>=22.18。

开源与Pro

本仓库包含Univer的开源核心和第一方OSS插件。Univer Pro作为商业扩展层单独开发,面向高级产品界面、协同、服务端能力和企业集成。

类别 开源 Univer Pro/商业版
基础能力 核心SDK、插件系统、渲染引擎、公式引擎、Facade API、主题、i18n和框架适配器 Pro预设和企业部署包
Sheets 核心电子表格编辑、公式、数字格式、筛选/排序、数据验证、条件格式、批注、表格、超链接、评论、绘图、查找替换。 协同、编辑历史、导入导出、打印、图表、数据透视表、迷你图、分级显示、形状、单元格内图形、数据连接器、区域预处理和增强公式引擎能力
Docs 文档模型和编辑UI、列表、超链接、评论、快捷插入和绘图集成。 协同、导入导出、打印、增强表格/列表、分栏、提示块、代码块、引用块、形状和远程线程评论资源
Slides OSS演示文稿模型和UI包 Pro演示文稿模型/UI包、幻灯片导入导出、图表、表格和可复用形状编辑器UI
Bases 用于自定义数据类产品的可扩展插件架构 Base数据库核心模型、命令、变更、公式集成、工作台UI、字段编辑器和渲染引擎集成
服务端与运行时 Node.js无头运行时、RPC/Web Worker模式和面向服务端自动化的基础能力 协同服务端、Node.js协同客户端、SSR服务、计算委托、服务端计算和协同changeset回放工具

Pro功能参考 Univer Pro指南。

实战

基于源码部署

bash 复制代码
git clone https://github.com/dream-num/univer.git
cd univer
pnpm install
pnpm dev

常用命令:

命令 用途
pnpm dev 构建并预览低内存、无HMR的一体化工作台
pnpm dev:source 启动支持HMR的源码工作台,冷启动和内存占用更高
pnpm build 构建workspace包,不包含内部common包
pnpm test 通过Turbo运行单元测试
pnpm typecheck 通过Turbo运行TypeScript检查
pnpm lint 运行ESLint
pnpm storybook:dev 启动用于UI组件开发的Storybook
相关推荐
火柴盒zhang1 年前
websheet在线电子表格(spreadsheet)在集团型企业财务报表中的应用
前端·html·报表·合并·spreadsheet·websheet·集团财务
火柴盒zhang1 年前
基于HTML CANVAS和EXCEL的xlsx文件展示工具websheet
前端·javascript·html·spreadsheet·websheet
火柴盒zhang1 年前
websheet之 编辑器
开发语言·前端·javascript·编辑器·spreadsheet·websheet
sdk大全3 年前
Securing Spreadsheets in ASP.NET Core Apps
spreadsheet