本文介绍如何使用钉钉 DWS 命令行工具,将钉钉知识库中的在线文档导出为本地 Office 文件,再上传到独立部署的 TorchV AIS 知识库。

图1:首先在钉钉知识库里面创建了一个新的知识库AIS,然后新建了两个文档。

图2:自动导出成功之后,两个文档已经在我指定的AIS知识库目录中。
本文以已经跑通的测试为例:
- 钉钉知识库:
AIS
- 钉钉空间链接:
https://alidocs.dingtalk.com/i/spaces/BpLm*********X2g/overview
- 测试文档:
水星1号、火星1号
- AIS目标目录:
卢向东的个人知识库/钉钉知识库导入存放目录
本教程重点说明导出、上传和验证流程,不讨论 AIS 对特定 Office 文件的解析兼容性。
一、整体流程
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16
| 钉钉 OAuth 登录 ↓ 解析知识库 workspaceId ↓ 列出知识库节点 ↓ 读取节点类型 ├─ adoc:导出为 DOCX / Markdown / PDF ├─ axls:导出为 XLSX └─ 普通附件:原文件下载 ↓ 保存到本地 staging 目录 ↓ 上传到 AIS 指定目录 ↓ 按 AIS 文档编码读回验证
|
二、准备条件
1. 本地环境
需要准备:
- Node.js 16.7 或更高版本;
- npm;
- 可以登录钉钉的浏览器;
- 可以访问 AIS 的网络环境;
- 已配置可用的 AIS Open Key。
检查 Node.js 和 npm:
1 2
| node --version npm --version
|
2. 创建同步项目
1 2 3 4 5
| mkdir -p dingtalk-ais-sync cd dingtalk-ais-sync npm init -y npm install --save-exact dingtalk-workspace-cli@1.0.59 mkdir -p staging state
|
定义本教程使用的命令路径:
1 2 3
| SYNC_PROJECT="$(pwd)" DWS_BIN="$SYNC_PROJECT/node_modules/.bin/dws" AIS_KB_BIN="/Users/lu/Documents/Codex/.agents/bin/ais-kb.sh"
|
验证 DWS:
1 2
| "$DWS_BIN" version "$DWS_BIN" auth status --format json
|
三、登录钉钉并授权
执行:
浏览器会打开钉钉登录和授权页面。完成扫码、登录和企业授权。
本场景只需要以下四个业务域:
wiki:查询知识库及节点;
doc:导出在线文字文档;
sheet:导出在线电子表格;
drive:获取文档存储信息和下载普通附件。
如果授权界面默认选择了其他业务域,应取消与本任务无关的权限。
登录后检查状态:
1
| "$DWS_BIN" auth status --format json
|
应重点检查:
1 2 3 4 5
| { "authenticated": true, "token_valid": true, "refresh_token_valid": true }
|
OAuth 方式适合功能验证。正式生产同步建议使用企业内部应用,并只申请需要的只读权限。
四、解析钉钉知识库
1. 根据知识库链接获取 workspaceId
1 2 3 4 5
| DINGTALK_SPACE_URL="https://alidocs.dingtalk.com/i/spaces/BpLm*********X2g/overview"
"$DWS_BIN" wiki +space-get \ --workspace "$DINGTALK_SPACE_URL" \ --format json
|
本次返回的关键内容:
1 2 3 4
| { "name": "AIS", "workspaceId": "BpLm*********X2g" }
|
保存空间ID:
1
| DINGTALK_WORKSPACE_ID="BpLm*********X2g"
|
不要仅凭 URL 结构猜测 workspaceId,应以接口返回为准。
2. 列出知识库全部节点
1 2 3 4 5
| "$DWS_BIN" wiki +node-list \ --workspace "$DINGTALK_WORKSPACE_ID" \ --page-all \ --max-items 500 \ --format json
|
全量读取时应确认:
autoPageComplete=true;
hasMore=false;
- 返回的节点数量符合预期。
本次得到两个节点:
| 名称 |
nodeId |
| 水星1号 |
gpG2NdyVXQg*******7LY3AD0JMwvDqPk |
| 火星1号 |
QPGYqjpJYRY******7OOM68akx1Z5N |
五、识别节点类型
分别读取节点元数据:
1 2 3 4 5 6 7
| "$DWS_BIN" wiki +node-get \ --node "gpG2NdyVXQg*******7LY3AD0JMwvDqPk" \ --format json
"$DWS_BIN" wiki +node-get \ --node "QPGYqjpJYRY******7OOM68akx1Z5N" \ --format json
|
重点读取 extension:
| extension |
内容类型 |
导出方式 |
adoc |
钉钉在线文字文档 |
dws doc +export |
axls |
钉钉在线电子表格 |
dws sheet export |
xlsx、docx、pdf 等 |
普通文件 |
dws drive download |
本次识别结果:
不要把在线表格当作普通文件下载,也不要把在线文字文档交给表格命令处理。
六、导出到本地
所有导出文件统一放在 staging/ 目录。
1. 导出在线电子表格
1 2 3 4
| "$DWS_BIN" sheet export \ --node "gpG2NdyVXQg*******7LY3AD0JMwvDqPk" \ --output "./staging/水星1号.xlsx" \ --format json
|
sheet export 会自动完成提交任务、轮询状态和下载,不需要在外部编写轮询程序。
2. 导出在线文字文档
1 2 3 4 5
| "$DWS_BIN" doc +export \ --node "QPGYqjpJYRY******7OOM68akx1Z5N" \ --export-format docx \ --output "./staging/火星1号.docx" \ --format json
|
文字文档也可以导出为:
必须显式传入 --export-format。
3. 检查导出文件
1 2
| file ./staging/水星1号.xlsx ./staging/火星1号.docx shasum -a 256 ./staging/水星1号.xlsx ./staging/火星1号.docx
|
建议记录:
- 钉钉
workspaceId;
nodeId;
- 源文档更新时间;
- 导出格式;
- 文件大小;
- SHA-256;
- 导出任务
jobId。
1. 检查目标目录
1 2
| "$AIS_KB_BIN" \ "kb tree 卢向东的个人知识库/钉钉知识库导入存放目录/ --depth 2 --limit 50"
|
本次 AIS 目标目录编码为:
2. 上传 XLSX
1 2 3
| "$AIS_KB_BIN" \ --upload-file "$SYNC_PROJECT/staging/水星1号.xlsx" \ --path-name "/卢向东的个人知识库/钉钉知识库导入存放目录"
|
3. 上传 DOCX
1 2 3
| "$AIS_KB_BIN" \ --upload-file "$SYNC_PROJECT/staging/火星1号.docx" \ --path-name "/卢向东的个人知识库/钉钉知识库导入存放目录"
|
上传成功后,接口会返回 AIS 稳定文档编码。此次结果为:
| 文件 |
AIS文档编码 |
| 水星1号.xlsx |
2091437*****02834432 |
| 火星1号.docx |
2091437*****6623104 |
八、验证 AIS 导入结果
1. 验证目录结构
1 2
| "$AIS_KB_BIN" \ "kb tree 卢向东的个人知识库/钉钉知识库导入存放目录/ --depth 2 --limit 50"
|
确认两个文件都已出现在目标目录。
2. 按稳定编码读取解析内容
1 2 3 4 5
| "$AIS_KB_BIN" \ "kb cat --code 2091437*****02834432 --head 120"
"$AIS_KB_BIN" \ "kb cat --code 2091437*****6623104 --head 120"
|
如果返回“文件转换中”,等待 AIS 完成知识加工后,再使用同一个文档编码重新读取。
不能只根据上传接口的 SUCCESS 判断整个导入完成;只有目录中存在文件并且 kb cat 能读取解析结果,才算完成了端到端验证。
九、保存同步清单
建议为每个源文档记录以下信息:
1 2 3 4 5 6 7 8 9 10 11 12 13 14
| { "sourceSystem": "dingtalk", "workspaceId": "BpLmk*******6X2g", "sourceNodeId": "gpG2NdyVXQg*******7LY3AD0JMwvDqPk", "sourceName": "水星1号", "sourceExtension": "axls", "sourceUpdatedAt": "2026-08-23T15:39:09+08:00", "exportFormat": "xlsx", "localFile": "staging/水星1号.xlsx", "sha256": "86a0187680cfad73cf4**************184b67bad9547ea7e5852a4787f784f", "aisDirectoryCode": "20914**********19392", "aisDocumentCode": "209*********834432", "syncStatus": "SUCCESS" }
|
后续同步不能只用文件名判断是否为同一文档,应以钉钉 nodeId 作为源对象主键。
十、常见问题
1. DWS显示“未登录”
重新执行:
如果提示企业没有启用 CLI 数据访问,需要在浏览器提交申请,并由企业管理员批准。
2. 知识库链接中的ID是否就是 workspaceId
不能直接假定。应执行 wiki +space-get,使用真实返回的 workspaceId。
3. 找不到文档
检查:
- 是否登录了正确的企业组织;
- 当前用户是否有知识库访问权限;
node-list 是否完成全部分页;
- 文档是否位于子目录,必要时继续列出对应
folderId 下的节点。
4. 导出命令应该选哪一个
先执行 wiki +node-get:
extension=adoc:使用 doc +export;
extension=axls:使用 sheet export;
- 普通 Office/PDF 文件:使用
drive download。
5. AIS上传成功但暂时无法读取
Office 文件上传后需要经过解析、清洗和知识加工。出现“文件转换中”时,保留文档编码,稍后重新执行 kb cat --code <AIS文档编码>。
十一、从POC升级到生产同步
本教程使用个人 OAuth 登录,适合验证可行性。生产环境建议增加:
- 创建钉钉企业内部应用,采用服务端身份运行;
- 只申请知识库、文档、表格和文件下载所需的最小只读权限;
- 使用
nodeId + updateTime + SHA-256 判断内容是否变化;
- 保存钉钉节点与 AIS 文档编码之间的映射;
- 增加定时任务、失败重试、限流和审计日志;
- 同步处理源文档删除、移动和权限收回;
- 在正式发布给 Agent 前完成 AIS 侧权限映射和内容审核。
十二、最短命令清单
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23
| "$DWS_BIN" auth login
"$DWS_BIN" wiki +space-get --workspace "$DINGTALK_SPACE_URL" --format json
"$DWS_BIN" wiki +node-list --workspace "$DINGTALK_WORKSPACE_ID" --page-all --max-items 500 --format json
"$DWS_BIN" wiki +node-get --node "<NODE_ID>" --format json
"$DWS_BIN" doc +export --node "<NODE_ID>" --export-format docx --output "./staging/文档.docx" --format json
"$DWS_BIN" sheet export --node "<NODE_ID>" --output "./staging/表格.xlsx" --format json
"$AIS_KB_BIN" --upload-file "$SYNC_PROJECT/staging/文件名" --path-name "/知识库/目标目录"
"$AIS_KB_BIN" "kb cat --code <AIS文档编码> --head 120"
|
完成以上步骤,即可建立“钉钉知识库 → 本地标准文件 → 独立部署 AIS”的基本导入链路。