在传递给AWS S3之前更改find​​命令的输出

时间:2018-08-22 14:14:03

标签: bash shell amazon-web-services amazon-s3 git-bash

我必须gzip CSS和JS文件并将它们上传到AWS S3存储桶。问题是当我运行gzip并尝试上传它们时,它们的初始目录结构没有保留。相反,它们都被复制到S3存储桶的根文件夹中。我意识到发生这种情况是因为find命令返回输出的方式。

$ find . -type f \( -iname \*.js -o -iname \*.css \) -exec gzip -9 "{}" \; -exec mv "{}.gz" "{}" \; -exec aws s3 cp "{}" s3://somebucket/ --dryrun \;
(dryrun) upload: .\service-worker.js to s3://somebucket/service-worker.js
(dryrun) upload: static\css\main.5b39ffb6.css to s3://somebucket/main.5b39ffb6.css

为解决上述问题,我在目标路径中也使用了{},但是现在的问题是最终路径具有./(紧随s3://somebucket/之后),如下所示:

$ find . -type f \( -iname \*.js -o -iname \*.css \) -exec gzip -9 "{}" \; -exec mv "{}.gz" "{}" \; -exec aws s3 cp "{}" s3://somebucket/{} --dryrun \;
(dryrun) upload: .\service-worker.js to s3://somebucket/./service-worker.js
(dryrun) upload: static\css\main.5b39ffb6.css to s3://somebucket/./static/css/main.5b39ffb6.css

我以为可以使用./{}cut的{​​{1}}部分剥离,但是当我尝试检查输出时,它会装饰我的整个终端都有无法读取的内容。似乎它不在输出文件名上起作用,而是在其内容上起作用。不知道发生了什么。

sed

有什么办法可以解决此问题,以便S3可以按其正确的目录结构复制文件?

1 个答案:

答案 0 :(得分:2)

您可以在-exec操作中创建一个子shell并在其中操作文件名:

find . \
    -type f \
    \( -iname '*.js' -o -iname '*.css' \) \
    -exec bash -c '
        f=${1#./}
        gzip "$f"
        mv "$f".gz "$f"
        aws s3 cp "$f" s3://somebucket/"$f" --dryrun' _ {} \;

-exec操作运行命令bash -c '<list>' _ {}:命令列表,其中虚拟参数_分配给$0,文件名分配给$1

因为我们使用的是-exec,所以文件路径看起来像./static/css/main.5b39ffb6.css,即仍然包含我们要删除的./

命令f=${1#./}从路径的开头删除./;从现在开始,我们只能使用$f


您说对了sed修改了文件的内容(如果它们作为参数给出);要直接更改字符串,您必须通过管道进行sed,如

sed 's/x/y/' <<< 'A string with x'

echo 'A string with x' | sed 's/x/y'