Bash script to loop over all sub-directories, check existence of a script directory, and run a script there
I’m new to bash scripting and I’m trying to make a script which uses a for
loop to find all the folders in the directory where it is started, and then use an if
statement to find another folder within them which has a name templates
, in which I then want to run a python command to execute python scripts stored in that folder.
- My directory structure looks like this:
all/ this_script.sh one/ templates/ render_j2.py two/ templates/ render_j2.py
- What I’ve tried for
this_script-sh
isfor file in *; do if [[ "$file"==*"templates"* ]]; then cd $file fi done
and also tried this:
for file in *; do find . templates python render_j2.py; done
My main issue is that I can’t enter the templates
folder, and even when I can, the python command cant find the python files to run.
This is kind of a non-answer but this seems like an over complicated setup. If you have an unstated reason you must or just want (to learn perhaps) the loop then this isn’t going to be your answer but…You can do this sans loop with the find command.
Something like
find $HOME/my/folders -type d -name templates -exec my.py {} ;
Since you are already using find, why not offload the entire task to it? You could try the following:
find . -type f -path "*/templates/render_j2.py" -execdir python render_j2.py ;
This will search for all files render_j2.py
in a directory templates
below your starting point, and in the directory where the file was found, execute your python command.
There’s a number of things wrong with this:
- Neither version is testing if
$file
is a directory - When the first version uses
cd $file
then $file will not be a valid path in the next iteration of the loop, because you changed directories; puttingcd
in a subshell (using parentheses) along with things you want to do in that directory would fix this. - In the second version, the find syntax is wrong to do what you want
- it doesn’t make sense to run find in a loop like this, find does its own loop internally
Something like this might work:
find . -name templates -type d -execdir python {}/render_j2.py ;
This would be equivalent to
(cd all/one && python ./templates/render_j2.py )
(cd all/two && python ./templates/render_j2.py )
...
which still might not be exactly what you want.