You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何在Rust的Command中正确传递含括号的find命令参数?

在Rust的Command中正确传递find的分组参数

我有一段可正常运行的bash命令:

find content/posts \( -iname '*.jpg' \) -print0 | xargs -0 -P8 -n2 mogrify -auto-orient

尝试将其转换为Rust代码:

let mut cmd = Command::new("/usr/bin/find")
        .args([
                post.dest_dir(&dest_dir).as_os_str().to_str().unwrap(),
                "(-iname '*.jpg')",
                "-print0",
        ])
        .stdout(Stdio::piped())
        .spawn()
        .unwrap();

let output = Command::new("/usr/bin/xargs")
        .args(["-0", "-P8", "-n2", "mogrify", "-auto-orient"])
        .stdin(cmd.stdout.take().unwrap())
        .output()
        .unwrap_or_else(|e| panic!("failed to execute process: {}", e));

执行后报错:

find: (-iname '*.jpg'): No such file or directory
exit code: exit status: 1

mogrify: no decode delegate for this image format `' @ error/constitute.c/ReadImage/741.
mogrify: no decode delegate for this image format `MD' @ error/constitute.c/ReadImage/741.

mogrify: insufficient image data in file `content/posts/2021-06-26-united-states/DSCF1507.JPG' @ error/jpeg.c/ReadJPEGImage_/1120.

问题原因与解决方案

问题核心是find的参数传递错误:

  • bash中的\( -iname '*.jpg' \),反斜杠是用来规避shell对括号的解析;但Rust的Command直接将参数传递给find进程,不需要转义括号。
  • 你把整个分组条件作为单个参数传递,会被find当成文件名查找,自然报错。正确做法是将每个部分拆分为独立参数:(、-iname、*.jpg、)。
  • bash中的单引号是防止shell扩展通配符,Rust传递参数不经过shell解析,无需添加单引号。

修正后的Rust代码:

let mut cmd = Command::new("/usr/bin/find")
        .args([
                post.dest_dir(&dest_dir).as_os_str().to_str().unwrap(),
                "(",
                "-iname",
                "*.jpg",
                ")",
                "-print0",
        ])
        .stdout(Stdio::piped())
        .spawn()
        .unwrap();

let output = Command::new("/usr/bin/xargs")
        .args(["-0", "-P8", "-n2", "mogrify", "-auto-orient"])
        .stdin(cmd.stdout.take().unwrap())
        .output()
        .unwrap_or_else(|e| panic!("failed to execute process: {}", e));

进阶优化

如果路径可能包含非UTF-8字符,建议使用OsStr传递参数,避免to_str().unwrap()的panic:

use std::ffi::OsStr;

let mut cmd = Command::new("/usr/bin/find")
        .args_os([
                post.dest_dir(&dest_dir).as_os_str(),
                OsStr::new("("),
                OsStr::new("-iname"),
                OsStr::new("*.jpg"),
                OsStr::new(")"),
                OsStr::new("-print0"),
        ])
        .stdout(Stdio::piped())
        .spawn()
        .unwrap();

内容的提问来源于stack exchange,提问作者tanman

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.19 15:50:27