A simple loop in the shell (which avoids the fact that there are several conflicting variants of the rename
utility):
for name in test??-*.txt; do
mv "$name" "${name%%-*}.txt"
done
The loop iterates over all names in the current directory matching the given pattern. For each such name, the end of the string is trimmed from the first -
using a standard parameter substitution. The substitution ${variable%%pattern}
removes the longest suffix string matching pattern
from the value of the variable
variable. We then add the .txt
suffix back onto the result of the substitution.
In the bash
shell, you may want to set the nullglob
shell option before running the loop, so that it does not run a single iteration if there is no matching filename.
With mv
on a GNU system (or any system with mv
from GNU coreutils), you may use -b
or --backup
to back up the destination file if it happens to already exist. Without -b
, the above loop would handle name conflicts by simply overwriting the existing file.
rename
command takes a Perl expression, for example a substitution command (s/regular-expression/replacement/
), not shell globbing patterns. With it, you could uses/-.*/.txt/
as the expression. Since I don't know whatreplace
you are using, I opted for not mentioning that command at all and instead use a loop that is guaranteed to work the same regardless of shell and Linux distribution. – Kusalananda Jan 12 '22 at 21:28