curl 下载得到 dl.pl 文件名:让 Content-Disposition 决定名称
浏览器下载名正常,curl -O 却采用接口名称;核对响应的 filename 字段,用 -OJ 或明确指定 -o 名称。
浏览器从下载接口保存为 report.gz,curl 用 -O 却保存成 dl.pl 或其他接口名称。先检查响应的 Content-Disposition,这通常是本地命名策略不同,不意味着下载内容必然错误。
本文适用于 curl 命令行通过 HTTP 或 HTTPS 下载。-J 从 curl 7.20.0 起提供;旧版本应选择自己指定文件名,或升级到受支持版本。
-O 从 URL 取名,-J 才读取响应建议
接口 URL 可能是下面这种结构:
https://example.com/download/dl.pl?id=2
-O 根据给定 URL 的文件部分决定本地名称,并不自动采用浏览器显示的下载名称。服务器可能通过以下响应头另行提供文件名;这是响应示例:
Content-Disposition: attachment; filename="report.gz"
希望使用这个名字时,在可信下载目录内使用 -O 和 -J;接口有重定向时再加 -L:
curl --fail --location --remote-name --remote-header-name \
'https://example.com/download/dl.pl?id=2'
域名和接口路径均为示例。--fail 让 HTTP 错误响应造成失败;它不能判断返回的内容是否真是压缩文件,也不能识别状态码为 200 的登录页。
只加 -J 而没有 -O,不能得到这组按响应头命名的行为。-L 负责跟随跳转,也不会单独把接口名称变成响应头里的名称。
没有 filename,或只提供 filename* 时
检查最终下载响应是否包含普通 filename=。如果服务器没有提供可用名称,-J 仍可能回退到 URL 名称。当前 curl 的这个选项不支持 filename*=;只发送这种扩展字段的服务,不能靠重复添加 -J 修复。
有权限修改下载服务时,应核对它实际发出的 Content-Disposition。客户端不能控制服务时,可以用小写 -o 明确指定自己的文件名:
curl --fail --location --output report.gz \
'https://example.com/download/dl.pl?id=2'
这个命令会写入指定文件;执行前确认目标路径没有需要保留的文件,或先选择新的名称。不要把大写 -O 和小写 -o 的行为混在一起。
文件名由服务器决定,也需要检查落盘结果
使用 -J 时服务器可以选择本地文件名。应从可信服务下载,并使用专门的空目录;得到文件后先检查类型和名称,不因扩展名看起来正常就执行它。当前规则下,服务器建议的名称若已经存在,curl 默认不会覆盖;遇到已有文件错误时,先检查那个文件的用途,再选择新目录或显式 -o。
普通重定向使用 -L 即可。不要为了取文件名额外启用 --location-trusted:它可能把认证信息发送给跳转到的其他主机,文件命名并不需要这个选项。
验收时同时确认三件事:curl 的退出状态成功、落盘名称符合预期、内容是目标下载物。若文件实际是登录 HTML,即使名称变成 report.gz,仍应回到下载授权和跳转链检查。


