git filter-branch 在比较 bash 语法上失败



我写了一个脚本来重写存储库,就好像文件在子文件夹中一样。

这个有效:

git filter-branch --tree-filter 'd="subfolder"; [ ! -f "$d" ] && mkdir -p "$d" && for file in *; do if [ "$file" != "$d" ]; then mv "$file" "$d"; fi; done' -- test

虽然这个返回了一个错误,说Rewrite a92e7d6bd57d523fdffa227bffdc76d7b9eb7c7a (1/5)tree filter failed

git filter-branch --tree-filter 'd="subfolder"; [ ! -f "$d" ] && mkdir -p "$d" && for file in *; do [ "$file" != "$d" ] && mv "$file" "$d"; done' -- test

我对修订版 a92e7d6bd57d523fdffa227bffdc76d7b9eb7c7a 进行了进一步测试,它也按预期工作:

d="subfolder"; [ ! -f "$d" ] && mkdir -p "$d" && for file in *; do [ "$file" != "$d" ] && mv "$file" "$d"; done

我很困惑:(如果[ ];那么...;fi)应该等同于([ ] &&...)不是吗?有人可以解释为什么吗?

答案可以在下面找到:

bash$ for i in a; do false && mv foo bar; done; echo $?
1
bash$ for i in a; do if false; then mv foo bar; fi; done; echo $?
0

就运行的内容而言,两者确实是等价的。 区别在于外壳的退出状态,如果它在done后立即退出。 Git 的filter-branch脚本检查每个过滤器的退出状态,如果该状态不为零,则中止。

(您始终可以在prog1 && prog2序列的末尾添加:; true以强制其成功。

最新更新