Home > Blockchain >  Renaming files with same file name pattern in Unix server using shell script
Renaming files with same file name pattern in Unix server using shell script

Time:04-06

I have a few files with the same file name pattern in the Unix server.

Example: Sample:

ABC DE FGH IJKL 04012022.csv
ABC DE FGH IJKL 04022022.csv

Expected Output:

ABC_DE_FGH_IJKL_04012022.csv
ABC_DE_FGH_IJKL_04022022.csv

This is what I tried. But got an error in the mv command as it was trying to rename both files at once.

for file in ls ABC\ DE\ FGH\ IJKL\ ????????.csv 
do 
    #Extracting date part separately 
    date_part=$(ls ABC\ DE\ FGH\ IJKL\ ????????.csv | cut -c 17-24) 
    #Appending date part to file 
    csv_file_nm="ABC_DE_FGH_IJKL_"$date_part.csv 
    #Renaming file using mv command 
    mv ABC\ DE\ FGH\ IJKL\ ????????.csv $csv_file_nm 
done

CodePudding user response:

The code shown is horribly broken:

for file in ls ABC\ DE\ FGH\ IJKL\ ????????.csv 
do 
    #Extracting date part separately 
    date_part=$(ls ABC\ DE\ FGH\ IJKL\ ????????.csv | cut -c 17-24) 
    #Appending date part to file 
    csv_file_nm="ABC_DE_FGH_IJKL_"$date_part.csv 
    #Renaming file using mv command 
    mv ABC\ DE\ FGH\ IJKL\ ????????.csv $csv_file_nm 
done

To use this idea (which isn't a very good way of proceeding, but…), you'd need to use "$file" in the loop rather than repeated ls operations:

for file in ABC\ DE\ FGH\ IJKL\ ????????.csv 
do 
    #Extracting date part separately 
    date_part=$(echo "$file" | cut -c 17-24) 
    #Appending date part to file 
    csv_file_nm="ABC_DE_FGH_IJKL_$date_part.csv" 
    #Renaming file using mv command 
    mv "$file" "$csv_file_nm"
done

That script uses globbing rather than ls to generate the file names — I've removed a stray ls from the for line. You might have intended to write for file in $(ls …), or maybe for file in `ls …` — but that isn't in the question. Processing the output of ls is not recommended either.

However, since you want to replace the spaces with underscores, a more direct way of operating would be:

for file in ABC\ DE\ FGH\ IJKL\ ????????.csv 
do 
    csv_file_nm=$(echo "$file" | sed 's/ /_/g') 
    mv "$file" "$csv_file_nm" 
done

Or, if your shell is Bash (and new enough), then:

for file in ABC\ DE\ FGH\ IJKL\ ????????.csv 
do 
    mv "$file" "${file// /_}" 
done

Or, if you have the Perl-based rename (sometimes called prename) command on the system, then:

rename 's/ /_/g' "ABC DE FGH IJKL "????????.csv
  • Related