一个自托管的 Web 文件管理器:服务端解压/压缩(文件不经过浏览器,零带宽浪费)、响应式苹果风界面(桌面 + 移动端)、账号登录 + TOTP 两步验证,一条 docker run 即可运行。
| 能力 | 说明 |
|---|---|
| 服务器端解压 / 压缩 | 点击"解压"后由主机 CPU/磁盘直接处理,前端只轮询进度。不会先把压缩包下载到手机再上传回服务器 |
| 服务器端复制 / 移动 | 同样只发指令,由主机 rename / 流式复制完成,大目录自动转为后台任务并显示进度 |
| 现代交互 | 桌面:右键菜单、双击打开、拖拽上传、Cmd/Ctrl 点选多选;移动端:长按弹出操作表、下拉刷新、底部 Tab、FAB |
| 选择模式 | 桌面端顶栏「选择」进入多选、或 Cmd/Ctrl 直接点选;移动端长按文件后选「选择」进入。选中后桌面显示横幅、移动端升起底部操作条,可全选/全不选、批量移动、复制、压缩、删除 |
| 苹果风设计 | SF 字体栈、毛玻璃、弹簧缓动、跟随系统的深浅色,网格/列表双视图 |
| 账号体系 | 注册/登录、bcrypt 密码哈希、JWT 会话、登录限速;默认 admin / admin |
| 两步验证 | 标准 TOTP(Google Authenticator、1Password、微软验证器等),绑定二维码 |
| 预览 | 图片、视频(支持 Range 拖动进度)、音频、文本/代码、PDF |
| 其他 | 递归搜索、重命名、移动、复制、新建目录、存储用量、断点续传下载 |
支持解压:zip / tar / tar.gz / tgz(zip 内含 GBK 文件名会自动识别,不乱码)
cd filenest
docker compose up -d --build
打开 http://localhost:8080,用 admin / admin 登录。
docker build -t filenest:latest .
docker run -d --name filenest \
-p 8080:8080 \
-v $(pwd)/data:/data \
-e TZ=Asia/Shanghai \
--restart unless-stopped \
filenest:latest
本项目的发布镜像为 linux/amd64(x86_64),适用于:
验证镜像架构:
docker inspect <你的用户名>/filenest:1.0.0 --format '{{.Os}}/{{.Architecture}}'
# linux/amd64
docker run --rm --entrypoint sh <你的用户名>/filenest:1.0.0 -c 'uname -m'
# x86_64
如果你的 NAS 是 ARM 机型(DS223、树莓派、M 系列 Mac),amd64 镜像无法运行,会报
exec format error或no matching manifest。这种情况需要 arm64 镜像,见下方多架构构建。
| 变量 | 默认值 | 说明 |
|---|---|---|
PORT | 8080 | 监听端口 |
DATA_DIR | /data | 账号、JWT 密钥等应用数据 |
FILES_DIR | $DATA_DIR/files | 文件根目录 |
SITE_NAME | FileNest | 页面标题 |
ALLOW_REGISTRATION | true | 是否开放注册 |
MAX_UPLOAD_MB | 0(不限) | 单文件上传上限 |
MAX_CONCURRENT_TASKS | 2 | 后台解压/压缩并发数 |
TOKEN_TTL | 7d | 登录有效期 |
PUID / PGID | 1000 | 容器运行用户(避免挂载目录权限问题) |
TZ | Asia/Shanghai | 时区 |
admin 密码(设置 → 修改密码)。ALLOW_REGISTRATION 设为 false。源文件在 web/public/(构建时自动进镜像),同时单独导出到 release/icons/ 便于取用:
| 文件 | 用途 |
|---|---|
icon.svg | 主图标(1024 矢量),favicon 与现代浏览器 |
icon-small.svg | 小尺寸专用版(去掉纸张、图形放大、圆角略小) |
icon-1024.png | 位图母版 |
icon-512.png / icon-192.png | PWA manifest、Docker Hub 仓库 Logo |
icon-180.png / apple-touch-icon.png | iOS「添加到主屏幕」 |
icon-64.png / icon-32.png | 浏览器标签页 |
manifest.webmanifest | PWA 清单(standalone、主题色、图标声明) |
设计:苹果风 squircle + 蓝→深蓝渐变 + 白色文件夹与探出的纸张,主色取自界面变量 --blue: #0071e3。
浏览器(React + Vite)
│ HTTP / JSON,仅传指令与进度
▼
Node.js (Express) ──► 任务队列(并发上限可配)
│ ├─ yauzl 流式解压 zip
│ ├─ node-tar 流式解压 tar/tgz
│ ├─ archiver 流式打包 zip
│ └─ fs.rename / 流式复制 移动与复制
▼
宿主机文件系统(Docker volume / bind mount)
所有重 IO 操作都在主机侧完成:解压、压缩、复制、移动统一走任务队列。前端只调用 POST /api/files/archive/extract(或 /copy、/move),立即拿到 202 + task,随后轮询 GET /api/tasks 读进度——浏览器全程不接触文件内容,只传指令和几百字节的 JSON。
| 操作 | 服务端实现 | 前端行为 |
|---|---|---|
| 解压 | 流式逐条目写出(yauzl / node-tar) | 立即返回,轮询进度 |
| 压缩 | archiver 流式打包 | 立即返回,轮询进度 |
| 移动 | fs.rename(同盘瞬间完成);跨挂载点自动退化为流式复制 + 删除 | 立即返回,轮询进度 |
| 复制 | 先统计字节数,再逐文件流式复制,按字节上报百分比 | 立即返回,轮询进度 |
| 重命名 / 删除 | 直接 fs.rename / fs.rm | 同步等待(通常 < 100ms) |
任务可随时取消:运行中的任务通过 AbortController 中断流,复制中途取消不会留下写了一半的文件句柄。
上传走 multipart 流式落盘,下载支持 HTTP Range(视频可拖动、可断点续传)。
filenest/
├── Dockerfile # 多阶段构建(前端构建 → 生产依赖 → 精简运行镜像)
├── docker-compose.yml
├── docker-entrypoint.sh # PUID/PGID 降权与目录初始化
├── server/ # Express 后端
│ ├── index.js # 装配、静态托管、健康检查
│ ├── auth.js # 登录、注册、JWT、TOTP 2FA、限速
│ ├── files.js # 列表/上传/下载/搜索/移动/重命名/解压入口
│ ├── tasks.js # 后台任务队列与压缩包处理
│ ├── fsutil.js # 路径越界防护、文件类型识别
│ ├── store.js # 用户存储(JSON + 原子写)
│ └── config.js
└── web/ # React 前端
└── src/
├── views/ # Login、Browser
├── components/ # 文件项、菜单、任务面板、预览、设置
├── api.js icons.jsx utils.js styles.css
npm install
npm --prefix web install
# 终端 1:后端(:8080)
DATA_DIR=./data npm start
# 终端 2:前端热更新(:5173,自动代理 /api)
npm --prefix web run dev
生产构建(前端产物由后端直接托管):
npm --prefix web run build
npm start
zip(解压支持 zip/tar/tar.gz)。7z、rar 需要外部二进制,未内置。欢迎 issue 与 PR。本地开发流程见上方「本地开发」一节;提交前请确保 npm --prefix web run build 通过。
本项目以 MIT 协议 开源,可自由用于个人与商业用途。
仓库中的
release/(镜像 tar、图标导出)不纳入版本控制,发布镜像请使用 Docker Hub / GitHub Releases。
Content type
Image
Digest
sha256:2816f6c52…
Size
65.3 MB
Last updated
2 days ago
docker pull xdxy/filenest