A simple problem:
Rename files with extension
xyz
which names ends withfile
. They need to start withdocument-
and have extensiontxt
For example if a file is1-file.xyz
it should be renamed todocument-1.txt
From this:
> ls -al
total 0
drwxr-xr-x 12 owner staff 384 Jan 1 19:26 .
drwxr-xr-x 7 owner staff 224 Oct 23 11:32 ..
-rw-r--r-- 1 owner staff 0 Jan 1 19:26 1-file.xyz
-rw-r--r-- 1 owner staff 0 Jan 1 19:26 10-file.xyz
-rw-r--r-- 1 owner staff 0 Jan 1 19:26 2-file.xyz
-rw-r--r-- 1 owner staff 0 Jan 1 19:26 3-file.xyz
-rw-r--r-- 1 owner staff 0 Jan 1 19:26 4-file.xyz
-rw-r--r-- 1 owner staff 0 Jan 1 19:26 5-file.xyz
-rw-r--r-- 1 owner staff 0 Jan 1 19:26 6-file.xyz
-rw-r--r-- 1 owner staff 0 Jan 1 19:26 7-file.xyz
-rw-r--r-- 1 owner staff 0 Jan 1 19:26 8-file.xyz
-rw-r--r-- 1 owner staff 0 Jan 1 19:26 9-file.xyz
to this:
> ls -al
total 0
drwxr-xr-x 12 owner staff 384 Jan 12 22:39 .
drwxr-xr-x 7 owner staff 224 Oct 23 11:32 ..
-rw-r--r-- 1 owner staff 0 Jan 12 22:39 document-1.txt
-rw-r--r-- 1 owner staff 0 Jan 12 22:39 document-10.txt
-rw-r--r-- 1 owner staff 0 Jan 12 22:39 document-2.txt
-rw-r--r-- 1 owner staff 0 Jan 12 22:39 document-3.txt
-rw-r--r-- 1 owner staff 0 Jan 12 22:39 document-4.txt
-rw-r--r-- 1 owner staff 0 Jan 12 22:39 document-5.txt
-rw-r--r-- 1 owner staff 0 Jan 12 22:39 document-6.txt
-rw-r--r-- 1 owner staff 0 Jan 12 22:39 document-7.txt
-rw-r--r-- 1 owner staff 0 Jan 12 22:39 document-8.txt
-rw-r--r-- 1 owner staff 0 Jan 12 22:39 document-9.txt
Solution
I could grab any commander and go one by one. But that is one time solution. Plus, I know there will be more files like these.
To rename one from cli:
> mv 1-file.xyz document-1.txt
To do it on each file inside current directory:
for f in *.xyz; do mv $f "document-${f%-file.xyz}.txt";done
What is does?
For each file that ends with .xyz
, remove its ending -file.xyz
and insert it in template document-<file_name>.txt
. Then rename current file.
Part "document-${f%-file.xyz}.txt"
is made of two parts replacing -file.xyz
then using result in the new filename. This part ${f%-file.xyz}
is substring removal. Here it is how works:
Expression | Description |
---|---|
${PARAMETER#PATTERN} | Replacing pattern from the begging the shortest match |
${PARAMETER##PATTERN} | Replacing pattern from the begging the longest match |
${PARAMETER%PATTERN} | Replacing pattern from the end the shortest match |
${PARAMETER%%PATTERN} | Replacing pattern from the end the longest match |
Looking into this algorithm there are several steps:
- locate target files by pattern
- delete pattern from filename
- add suffix and postfix on result from above
- rename file
From all this I can write a simple script:
#!/bin/sh
PATTERN=$1
SUFIX=$2
POSTFIX=$3
cnt=0
for f in $(eval echo "*$PATTERN"); do
mv "$f" "$SUFIX${f%$PATTERN}$POSTFIX"
cnt=$((cnt + 1))
done;
echo "renamed $cnt files."
And to use this script, like this:
$rf.sh -file.xyz document- .txt
Code available at toolz