我有一个for循环,该循环列出了所有可以正常工作的子目录,但是我想进入每个目录,运行命令,然后移至下一个目录,但它只是停留在它输入的第一个目录中。
脚本:
#!/bin/bash
for i in $(ls -l ../terraform/envs/ | grep ^d | tr -s ' ' | cut -d ' ' -f 9 );
do
echo $i | awk -v i="$i" !'/maint|template/'
cd ../terraform/envs//$i
echo $PWD
break
#terragrunt plan
done
答案 0 :(得分:1)
使用pushd
代替cd
;那么您可以使用popd
返回到原始目录。
不相关,但无需使用ls
。改用glob。
cd terraform/envs
for i in */; do
pushd "$i" > /dev/null
echo "$PWD"
popd > /dev/null
done
(当然,这里,循环前的cd
命令意味着您可以只使用cd "$i"
和cd ..
,但是pushd
/ popd
可以很好地工作进行任意目录更改,而不仅仅是简单的一步一步的操作。)
(请注意,如果多次使用pushd
,则需要向popd
传递适当的参数,以确保返回正确的堆栈条目,或调用popd
适当的次数。)
答案 1 :(得分:0)
首先,要回答您的问题,多亏了cd -
命令,您可以返回上一个目录。它将打印出您回到的目录。如果您不想要该输出,请重定向到/dev/null
,例如:
#!/bin/bash
for i in $(ls -l ../terraform/envs/ | grep ^d | tr -s ' ' | cut -d ' ' -f 9 );
do
echo $i | awk -v i="$i" !'/maint|template/'
cd ../terraform/envs//$i
echo $PWD
cd - > /dev/null
break
#terragrunt plan
done
此外,就像@Cyrus提到的那样,解析ls
输出通常是一个坏主意。有很多选择,我建议您从find
中读取变量,例如:
while read i;
do
# do something
done < <(find ../terraform/envs/ -mindepth 1 -maxdepth 1 -type d)
最后但并非最不重要的一点是,您应该尽可能经常地将变量放在引号中,例如echo
和cd
中的内容,就像您对awk
所做的一样。
总而言之,您应该得到这样的东西:
#!/bin/bash
while read i;
do
echo "$i" | awk -v i="$i" !'/maint|template/'
cd "../terraform/envs//$i"
echo $PWD
cd - > /dev/null
break
#terragrunt plan
done < <(find ../terraform/envs/ -mindepth 1 -maxdepth 1 -type d)