Working with directories, need assistance

Hello there,

I have the following issue and I need you assistance.

I have created a script that searches for directories that have spaces, for example:

./assets/en/images/pricing/current offers/SIMPLE GRID
./assets/en/images/pricing/current offers/ADVERTISED PRICE

But now the requirements have been updated and I have to rename the directory with an "_", so the result will be:

./assets/en/images/pricing/current_offers/SIMPLE_GRID
./assets/en/images/pricing/current_offers/ADVERTISED_PRICE

I have tried something like this:

mv ./assets/en/images/pricing/'current offers'/'SIMPLE GRID' ./assets/en/images/pricing/'current_offers'/'SIMPLE_GRID' but is not working.

Could you please give me a suggestion or any other idea to do this?

Thanks for the help.

Best regards

---------- Post updated at 04:27 PM ---------- Previous update was at 04:07 PM ----------

I have tried also these
find . -name '* *' | while read file;
do
target=`echo "$file" | sed 's/ /_/g'`;
echo "Renaming '$file' to '$target'";
mv "$file" "$target";
done;

But is not working

I received an error, since it replace the first found instance for example
assets/en/images/pricing/current_offers but when tries to change the second
assets/en/images/pricing/current offers/SIMPLE GRID it shows "No such file or directory"

thanks

I'm assuming this is a *nix environment. In which case you can't just use spaces. A path with spaces is understood as FILENAME\ WITH\ A\ SPACE.

Each space has to be escaped, and spaces in reg exp are \s.

In your code:

target=`echo "$file" | sed 's/ /_/g'`;

should be

target=`echo "$file" | sed 's/\s/_/g'`;

Hope this points you in the right direction.

This is one solution.

The first matter of business is to reverse the order of the matches, so you are looking at the last matches first, which will be the deepest subdirectories/files in a particular tree. This will prevent you from renaming a parent directory first, and later having an invalid path to a subdirectory. You can use 'tac' to reverse the order of the matches returned by find.

You are getting the error message because you are replacing all spaces in the line with underscores, including those in the path. However, the mv command will only rename the filename (or directory) given after the last slash, not the entire path including a filename.

For example, if I have a directory structure like this (with spaces):

parent dir
\_ sub dir

And I do this to change the spaces into underscores:

mv   ./parent\ dir/sub\ dir   ./parent_dir/sub_dir

mv is going to give me an error because parent_dir (with underscores) does not exist for sub\ dir to be placed there. mv is only operating on sub\ dir, and it is given an invalid path.

To prevent this, separate the filename from the path, so you can operate on the filename separately from the path. The 'dirname' and 'basename' commands help you do this.

Lastly, use sed to replace all spaces in the filename with underscores, then glue the path and filename back together in your mv command.

Changing your code around, it would end up looking something like this:

#!/bin/bash

find . -name "* *" | tac | while read file ; do

        directory=`dirname "$file"`
        target=`basename "$file" | sed "s/ /_/g"`
        echo "Renaming '$file' to '${directory}/${target}'"
        mv "$file" "${directory}/${target}"

done
mv SIMPLE\ GRID SIMPLE_PRICE
mv ADVERTISED\ PRICE ADVERTISED_PRICE

Thanks for all the help guys... It works!!!

Best regards :0)
Pura vida