Register
It is currently Mon Jul 28, 2014 12:15 am

renaming file prefixes and extensions


All times are UTC - 6 hours


Post new topic Reply to topic  [ 14 posts ] 
Author Message
 PostPosted: Sun Sep 10, 2006 9:29 am   

Joined: Mon May 16, 2005 6:29 pm
Posts: 94
Location: Upstate NY
i ran into a situation at work were i had to change the prefix on a bunch of images. this would normally be an relatively simple to do but people keep insiting on putting spaces in the file names, no matter how many times i keep telling them to only use alpha, numeric, "-" and "_" only. so the trick here was to figure out what had to be quoted and what didn't so the script wouldn't choke when it saw spaces in filenames.

note: this will also work for fixing file extensions.

Code:
#!/bin/bash

for i in *.jpg
do
MATCH="<current prefix/extension>";
REPLACE="<new prefix/extension>";
TARGET=$(echo "$i" | sed -e "s/$MATCH/$REPLACE/")

# this allows you to visually see what files are being modified.
# comment this line out if running from a cronjob
echo "$i";

mv "$i" "$TARGET"
done

exit 0


Top
 Profile WWW  
 PostPosted: Sun Sep 10, 2006 1:27 pm   
User avatar

Joined: Tue May 17, 2005 12:55 am
Posts: 86
Location: Big Easy, Louisiana
looks good man 8) are we gonna try to incorporate this into bbips :?


Top
 Profile YIM  
 PostPosted: Sun Sep 10, 2006 1:43 pm   

Joined: Mon May 16, 2005 6:29 pm
Posts: 94
Location: Upstate NY
never thought about it but crouse is more than welcome to. he already has most of it there there i think.


Top
 Profile WWW  
 PostPosted: Sun Sep 10, 2006 8:10 pm   
Site Admin
User avatar

Joined: Sun May 15, 2005 9:36 pm
Posts: 662
Location: Des Moines, Iowa
I've thought of writing a renaming utility that renames files to........

$VARIABLENAME-0001.jpg
$VARIABLENAME-0002.jpg

and so on....recursively throught the file.....

so you could type something like

bbrename summer_06

and your images would come out named

summer_06-0001.jpg
summer_06-0002.jpg

etc etc...... but don't know if it would be used much......


Top
 Profile WWW  
 PostPosted: Sun Sep 10, 2006 8:59 pm   

Joined: Mon May 16, 2005 6:29 pm
Posts: 94
Location: Upstate NY
i'm doing some work combining my rename scripts and updating with the changes made last night to handle the whitespace. if i get it done in the next few days i will post it.

i normally am dealing with renaming extensions. this is the first time i've had to do a prefix but won't be the last. so i'm hoping to have some way to define the prefix or extension as a variable like $1 or $2 so it can be run easily from cli and cron. depending on how that works out i might add a function using read to interact from the cli.


Top
 Profile WWW  
 PostPosted: Mon Sep 11, 2006 7:26 pm   

Joined: Mon May 16, 2005 6:29 pm
Posts: 94
Location: Upstate NY
well it looks like it's going to take more work that i had planned. the script works on files in the same directory that the script is in. but when it needs to search for files to match a specific string and the folders have a space in them the whole thing pretty much breaks.

right now i have the script generating a list of offending files and trying to parse the files from the list is causing some issues. there has to be a better way to "wrap" the variable. quotes are not working.

since it seems that the script has issues when running the file list through a "for" loop but it works fine as part of a "find" command. i'm going to look into using xargs or something to see if there is a better way to do this.

when i have a better clue as to what i am doing i will post a little more information and script samples


Top
 Profile WWW  
 PostPosted: Mon Sep 11, 2006 8:24 pm   
User avatar

Joined: Mon Jul 03, 2006 8:58 pm
Posts: 52
Location: Rochester, NY
It seems to me you need to use something like perl or sed to substitute a set of "naughty" characters with their escaped version. For example:
Code:
sed 's/\([ $"\]\)/\\\1/g'

This will replace all spaces, dollar signs, double quotes and backslashes with the escaped version of the same.

So a file named
Code:
Uncle $all\ys "brother".txt
will be replaced with
Code:
Uncle\ \$all\\ys\ \"brother\".txt


Top
 Profile WWW  
 PostPosted: Tue Sep 12, 2006 11:38 am   
Site Admin

Joined: Tue May 17, 2005 7:31 pm
Posts: 251
Location: Georgia
for extensions i would just do this...
Code:
ext=jpg
new_ext=jpeg

for filename in *.$ext
do
    mv "$filename" "${filename:0:${#filename}-${#ext}}${new_ext}"
done


Top
 Profile  
 PostPosted: Tue Sep 12, 2006 6:44 pm   

Joined: Mon May 16, 2005 6:29 pm
Posts: 94
Location: Upstate NY
jbsnake
is there any way you could explain what the second part (destination) of the "mv" line does? i've never really seen syntaxing like that. also does all that bracketing take into account that there are whitespaces in the filename and filepath?

brions
will your sed command "escape" the white space just for that function or is it a permant part of the rename? i unfortunately don't have the luxury to correct the errors of the others in the office beyond the extension correction. in the future as part of the network clean up i will be doing i might be able to clean up all that whitespace permantly


Top
 Profile WWW  
 PostPosted: Tue Sep 12, 2006 7:57 pm   
Site Admin
User avatar

Joined: Sun May 15, 2005 9:36 pm
Posts: 662
Location: Des Moines, Iowa
lets say filename is thecoolestfile.jpeg
and the new extention is .jpg

Code:
mv "$filename" "${filename:0:${#filename}-${#ext}}${new_ext}"


Basically, it moves $filename toooo

the quotes enclose the next name.....

#filename means number of characters of the filename thecoolestfile.jpeg which is 20 then SUBTRACT the lenght of the current extention which is 4 so, this means the NEW filename uses the characters from 0 to 16 (which in essence now removes the OLD extention) and the ${new_ext} adds on the new extention

pretty cool if ya ask me ;)


Top
 Profile WWW  
 PostPosted: Tue Sep 12, 2006 10:59 pm   
Site Admin

Joined: Tue May 17, 2005 7:31 pm
Posts: 251
Location: Georgia
fear not the whitespace... for it is handled by the great and powerful ""

Code:
"${filename:0:${#filename}-${#ext}}${new_ext}"


let's break that down :wink:
strings are just arrays of characters... right? (waits for nods)
the bracketting allows for specific "parts" of the string
if you just do ${filename} you get whatever is in the variable 'filename'
it's basically broken down like ${variable_name:start_position:length}
so it's
Code:
${filename:0:

that's take the filename variable and start at the 0 position... or first character
as crouse pointed out... ${#variable_name} returns the length of the variable
so then
Code:
${filename:0:${#filename}-${#ext}}

is:
the variable 'filename' starting at position 0 with a length of the full length of the variable 'filename' minus the length of the variable ext
since we designated ext to equal jpg in my example script...${#ext} would equal 3
so let's say we take a filename...
thecoolestfile.jpeg
so the mv line would be like this (all variables exposed)
Code:
filename="thecoolestfile.jpeg"
ext=jpeg
new_ext=jpg
mv "$filename" "${filename:0:19-4}${new_ext}"
# or mv "thecoolestfile.jpeg" "thecoolestfile.jpg"


hope that helps to shed some light on string manipulation... bash style 8)


Top
 Profile  
 PostPosted: Wed Sep 13, 2006 4:01 am   
User avatar

Joined: Mon Jul 03, 2006 8:58 pm
Posts: 52
Location: Rochester, NY
But does that get around the problem of a special character in the file name such as a dollar sign or quote character?

I thought part of isacklow's problem was nightmarish filenames created by other people that he didn't want to change? I can see this working for spaces, but not for other "special" characters. Granted, I haven't tried it.yet.

Edit: I have tried now and even without jbsnake's cool substring function or my sed string I got the rename to work just fine. Here's the code, the input, and the ouput:

Code:
#!/bin/bash

MATCH=".txt";
REPLACE=".bar.txt";

for i in *${MATCH}
do
TARGET=$(echo "$i" | sed -e "s/$MATCH/$REPLACE/")

# this allows you to visually see what files are being modified.
# comment this line out if running from a cronjob
echo "$i";

mv "$i" "$TARGET"
done

exit 0


Input:
Code:
> touch Uncle\ \$ally\\s\ \"brother\".txt


Output:
Code:
> ./testscript.sh
Uncle $ally\s "brother".txt
> ls *.bar.txt
Uncle $ally\s "brother".bar.txt


I've got bash 3.1.17 if it makes a difference.and sed 4.1.4.


Top
 Profile WWW  
 PostPosted: Wed Sep 13, 2006 5:34 am   

Joined: Wed Sep 06, 2006 12:19 pm
Posts: 54
Location: Covington, WA
isacklow wrote:
i ran into a situation at work were i had to change the prefix on a bunch of images. this would normally be an relatively simple to do but people keep insiting on putting spaces in the file names, no matter how many times i keep telling them to only use alpha, numeric, "-" and "_" only. so the trick here was to figure out what had to be quoted and what didn't so the script wouldn't choke when it saw spaces in filenames.

note: this will also work for fixing file extensions.

Code:
#!/bin/bash

for i in *.jpg
do
MATCH="<current prefix/extension>";
REPLACE="<new prefix/extension>";
TARGET=$(echo "$i" | sed -e "s/$MATCH/$REPLACE/")

# this allows you to visually see what files are being modified.
# comment this line out if running from a cronjob
echo "$i";

mv "$i" "$TARGET"
done

exit 0

Hi all, forum noob here ;-)
It seems you can just replace ALL offending characters with an underscore...........This might get some of them a bit mad, but just telling them to do something won't work.........Once they see that there beautiful names get mangled, they might get the hint :D

So try something along the lines of what BrionS suggested, but convert them all to underscores.......Something like this should do the trick
Code:
# Create test file:
:>'Uncle $all\ys "brother".ext'

for file in *.ext; do
    mv "$file" $(sed 's|[^[:alnum:]_/.-]|_|g' <<<"$file")
done

The output will be someting like
Code:
Uncle $all\ys "brother".ext  ---renamed to--->  Uncle__all_ys__brother_.ext

Of course, this might be a bit harsh if you're a soft touch :lol: .........But you can always tone it down by including the characters you want to ALLOW in the regexp part of the sed command........Just make sure the hyphen is the last character before the closing bracket (-]), other wise you might allow a whole range of characters you didn't expect. :o

Anyway, the idea here is to exclude the characters you don't want to mangle, which is a whole lot easier than trying to figure out what you forgot to include as no-no's... :roll:

HTH :)
---thegeekster


Top
 Profile  
 PostPosted: Wed Sep 13, 2006 5:42 am   

Joined: Wed Sep 06, 2006 12:19 pm
Posts: 54
Location: Covington, WA
Oh yeah, make sure the carat symbol is the first one right after the opening bracket ([^)..............For those who might not be quite familiar with regular expressions :wink:


Top
 Profile  
Display posts from previous:  Sort by  
Post new topic Reply to topic  [ 14 posts ] 

All times are UTC - 6 hours


Who is online

Users browsing this forum: No registered users and 4 guests


You cannot post new topics in this forum
You cannot reply to topics in this forum
You cannot edit your posts in this forum
You cannot delete your posts in this forum
You cannot post attachments in this forum

Jump to:  
cron


BashScripts | Promote Your Page Too
Powered by phpBB © 2011 phpBB Group
© 2003 - 2011 USA LINUX USERS GROUP