ConvertX 完整指南:一条 Docker 命令搭建支持 1000+ 格式的自托管文件转换器
【免费下载链接】ConvertX💾 Self-hosted online file converter. Supports 1000+ formats ⚙️项目地址: https://gitcode.com/GitHub_Trending/co/ConvertX
ConvertX 是一款开源的自托管在线文件转换服务,用 TypeScript、Bun 和 Elysia 构建,内置 FFmpeg、ImageMagick、Pandoc 等 20 个转换引擎,合计覆盖超过 1000 种格式。它解决的核心问题是:不经过任何第三方服务器,在自己的机器上就能完成图片、视频、文档、电子书、3D 模型之间的格式互转。适合经常跨设备传文件、又介意文件被上传到陌生平台的个人和小团队。
场景:什么时候你需要一个自托管文件转换器
先想两个很具体的场景:
- 手机拍的照片,电脑打不开。iPhone 默认保存 HEIC 格式,Windows 或某些老设备根本不认;反过来,同事发来的 TIFF 扫描件你想转成 PNG 发给客户。这类"格式互传"是日常最高频的需求。
- 文件不想经过别人的服务器。在线转换网站用起来省事,但合同、证件照、内部文档一旦上传,就等于把文件交给第三方保管。文件会不会被留存?会不会被限速或加水印?这些问题你无法控制。
ConvertX 的思路很直接:把转换引擎装进一个 Docker 镜像,部署在你自己的服务器或 NAS 上,提供一个带账号登录的网页界面。文件只在你自己的硬盘里流转,转换完还能自动清理。
快速上手:Docker 一键部署 ConvertX
整个服务就是一个容器,镜像里已经装好了全部转换工具,不需要在宿主机上装任何东西。
最简单的方式是直接跑:
docker run -p 3000:3000 -v ./data:/app/data ghcr.io/c4illin/convertx或者写一个 compose 文件,生产环境更推荐这种方式:
services: convertx: image: ghcr.io/c4illin/convertx container_name: convertx restart: unless-stopped ports: - "3000:3000" environment: - JWT_SECRET=一串足够长的随机字符串 volumes: - ./data:/app/data启动后访问http://localhost:3000,首次访问会进入设置页,直接创建第一个账号(密码保护 + 多账户是内置功能)。有两个细节值得提前知道:
- 别把没配置的服务暴露到公网。在第一个账号创建之前,任何人都能注册,所以记得先设好
JWT_SECRET(未设置时会用一次性的随机 UUID 签名 token,容器重建后旧登录态会失效)。 - 非 localhost 且非 HTTPS 的访问方式需要显式开启,设置
HTTP_ALLOWED=true(官方建议仅在本地这样用)。
另外,如果启动时看到 "unable to open database file" 的错误,给挂载的./data目录补一下权限即可(chown -R $USER:$USER ./data)。
日常使用:从上传到下载只需 4 步
登录后的操作路径非常直白:
- 上传文件:在首页选择文件,支持一次选多个。每个转换任务会分配一个独立的 jobId,文件按"用户 ID / 任务 ID"的目录结构存放在
./data下,互相隔离。 - 选择目标格式:页面会根据文件扩展名动态列出所有可行的输出格式(这个列表由各转换引擎的 from/to 清单自动聚合,见 src/converters/main.ts)。
- 点击转换:请求返回后立即跳转到结果页,转换本身在后台进行,批量文件会分块并发处理,不用盯着页面等。
- 下载与清理:结果页逐个下载,历史页可以看所有任务状态;上传的文件默认每 24 小时自动检查一次并删除超龄文件(由
AUTO_DELETE_EVERY_N_HOURS控制,设为 0 则关闭自动清理)。
对"偶尔转一个文件"的用户来说,流程到此就够了。
能力拆解:1000+ 格式是怎么做到的
ConvertX 自己不做格式解析,它的"万格式"来自对 20 个成熟转换工具的封装,全部源码在 src/converters/ 下,每个文件对应一个引擎。几个主力选手的覆盖规模(来自 README.md):
| 引擎 | 用途 | 可读取格式 | 可输出格式 |
|---|---|---|---|
| FFmpeg | 音视频 | 约 472 | 约 199 |
| ImageMagick | 图像 | 245 | 183 |
| GraphicsMagick | 图像 | 167 | 130 |
| Assimp | 3D 模型 | 77 | 23 |
| Pandoc | 文档 | 43 | 65 |
| LibreOffice | 办公文档 | 41 | 22 |
| Calibre | 电子书 | 26 | 19 |
调用逻辑集中在main.ts的mainConverter函数:每个引擎导出自己的convert函数和from/to格式清单,运行时按"源扩展名 + 目标扩展名"去匹配清单,命中谁就调用谁(比如 EMF 文件会优先交给 Inkscape 而不是 ImageMagick,因为处理得更好)。没匹配到就直接返回"不支持",不会乱跑。
批量处理方面,handleConvert会用一个chunks函数按MAX_CONVERT_PROCESS把文件列表切块:块内所有文件通过Promise.all并发转换,块与块之间串行推进。默认值 0 表示不限制并发,小内存机器上建议设成 2~4 防止多个 FFmpeg 进程把内存打满。
安全机制层面:登录态用 JWT 签发(7 天有效期),密钥来自JWT_SECRET;文件名经过 sanitize 处理防止路径注入;上传、输出、结果查询都校验 jobId 归属,一个账号看不到另一个账号的文件。
进阶玩法:调参、自定义参数与二次开发
常用环境变量
| 变量 | 默认值 | 作用 |
|---|---|---|
FFMPEG_ARGS | 空 | 传给 FFmpeg 输入端,如-hwaccel vaapi开启硬件解码 |
FFMPEG_OUTPUT_ARGS | 空 | 传给 FFmpeg 输出端,如-preset veryfast加快编码 |
MAX_CONVERT_PROCESS | 0(不限) | 并发转换进程数上限 |
AUTO_DELETE_EVERY_N_HOURS | 24 | 每 n 小时清理超过 n 小时的文件,0 为关闭 |
ACCOUNT_REGISTRATION | false | 是否允许注册新账号,单人使用时保持关闭 |
WEBROOT | 空 | 挂载子路径,设为/convert则站点在example.com/convert/下 |
HIDE_HISTORY | false | 隐藏历史页 |
LANGUAGE | en | 日期等字符串的语言(BCP 47 标签) |
ALLOW_UNAUTHENTICATED | false | 允许免登录使用,仅限本地场景 |
有硬件转码需求的用户重点看FFMPEG_ARGS,比如 N 卡机器可以尝试 vaapi/vulkan 加速,官方 README 里附有相关 issue 的讨论线索。
镜像提供:latest(跟随 release)和:main(跟随 main 分支最新提交)两个 tag,常规使用选:latest。
二次开发
开发流程是标准的前端项目套路:装好 Bun 和 Git 后克隆仓库,然后:
git clone https://gitcode.com/GitHub_Trending/co/ConvertX cd ConvertX bun install bun run dev想加一个新转换器的路径也很清晰:在src/converters/新建文件,导出convert函数和from/to格式属性(可参考 ffmpeg.ts 的结构),再到 main.ts 的properties表里注册一行即可参与路由分发。tests/converters/下有现成的测试模板可以照着写。
收尾:把它放进你的服务列表
ConvertX 的价值不在某个炫酷功能,而在于把"格式转换"这件碎事变成了基础设施:一条 Docker 命令部署,数据全程不出自己的机器,1000+ 格式按需取用。跑起来之后,可以接着探索的方向包括:用WEBROOT把它挂到现有域名子路径下、给 FFmpeg 配上硬件加速、按内存情况调低并发数,以及为团队开启多账号并关闭注册。
【免费下载链接】ConvertX💾 Self-hosted online file converter. Supports 1000+ formats ⚙️项目地址: https://gitcode.com/GitHub_Trending/co/ConvertX
创作声明:本文部分内容由AI辅助生成(AIGC),仅供参考