Skip to content

feat: add share --link mode with server-side allowlist - #12

Merged
toads merged 1 commit into
mainfrom
feature/share-link
Aug 12, 2026
Merged

feat: add share --link mode with server-side allowlist#12
toads merged 1 commit into
mainfrom
feature/share-link

Conversation

@toads

@toads toads commented Aug 12, 2026

Copy link
Copy Markdown
Owner

概述

share.js 新增 --link 模式:以符号链接(而非复制)把外部文件/目录挂入 shared/,配套服务端白名单机制,仅放行显式登记过的链接穿透既有的 realpath 反目录穿越防护。

动机

复制模式对大文件/大目录既占磁盘又耗时;软链接模式零拷贝、即时生效。但服务端 resolveSharedEntry() 的 realpath 防护会拒绝一切逃出 shared/ 的路径(安全设计,不能简单放开),因此引入 data/shared-links.json 显式授权清单:只有用户通过 share.js --link 登记过的目标才允许穿透,未登记符号链接行为完全不变。

改动

  • lib/shared-links.js(新增):白名单读写工具 —— 原子写(临时文件 + rename)、服务端 mtime 缓存读取、条目校验(key 仅限顶层 basename,value 必须是绝对 realpath)、跨平台路径比较(win32 大小写不敏感)
  • share.js:--link <路径...> 创建符号链接并登记(不复制、不调度云上传);--list 显示 名字 -> 目标 (链接);--clear 同步清空登记文件
  • server.js:resolveSharedEntry 仅当路径第一段是已登记链接名且 realpath 在登记目标内时放行越界;walkDir 只展示已登记顶层链接;tar.create 增加 follow: true(containsSymlink 拦截不变,未登记/嵌套符号链接仍会导致打包被拒,不会泄露内容)
  • scripts/integration-test.js:已登记链接可列出/下载/打包;未登记链接不可见且下载被拒;符号链接创建不可用时用例 skip 而非 fail
  • README.md / AGENTS.md:用法与模块说明同步更新

跨平台兼容

  • Windows 目录链接使用 junction(无需管理员权限,要求绝对路径——登记的本来就是 realpath);Windows 文件链接遇 EPERM/EACCES/ENOTSUP 给出中文提示(需管理员权限或开发者模式),建议改用复制模式
  • Linux/macOS 使用标准 dir/file 类型符号链接
  • 所有路径比较先 realpath 规范化,win32 下统一小写

测试

  • npm test(smoke + integration)通过,链接用例真实执行(非 skip)
  • 手动验证 --link / --list / --clear 行为符合预期

@toads
toads merged commit e0fe572 into main Aug 12, 2026
0 of 2 checks passed
@toads
toads deleted the feature/share-link branch August 12, 2026 08:16
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant