I’m slowly uploading my digital photo archives to Picasa albums. I bought the extra space recently, I want to make sure my pictures are ok for a longer time.
I’m using google command line for this. It’s going slowly, so I mostly start the upload process remotely when I’m at a work (because google-cl kills bandwidth, so I can’t reliably use net when I’m home and when google-cl is working).
Well, to get to the point. One of the albums had file names in the form of ‘more1 1.jpg’, ‘more1 2.jpg’… and I wanted to change this. Being a linux geek that I am, I knew the shell was the fastest way to go. But I didn’t know how.
It’s easy, of course, I googled it in few seconds. I’m posting it here for my future referrence.
So here is the resulting line:
ls * | sed ‘s/more1\ \(.*\)/mv “&” “\1″/’ | sh
Now step-by-step explanation:
1. ls * - this is clear (there were only files in the folder). This could have been something like find . -type f, or find /somewhere -name ‘<name pattern>’.
2. sed ‘s/more1\ \(.*\)/mv “&” “\1″/’
This is the fun part. sed can filter text, do regex searches, matches, transformations, whatever.
Regex term s/<ORIGINAL>/<NEW>/ means that I want to change the ORIGINAL for NEW.
3. ORIGINAL
In my case, orignal was more1\ \(.*\) : more1 is the first part of the name. Then there is this space (escaped with a backslash). Then there is a “match whatever, zero or more characters: (.*) – of course the () had to be escaped too.
This could also have been something like file123.jpeg – I can match it with /file\(.*\)\.jpeg/ – translated it means match anything that begins with file and ends with .jpeg. So, now we have ORIGINAL.
4. NEW
What I wanted is lose the “more1\ ” part. I had to move (hence mv) the file (“&” – the quotes are because of the spaces in the filename) to just the first group (\1).
5. What is first group?
In regexes, when you match something, it’s called a group. When you match two things, you have two groups. Ie file.extension is matched by /(.+)\.(.+)/ (1 or more anything, dot, 1 or more anything – the dot if not escaped means “any character”).
So my matched group was \1 (the number and extension). In my example where I matched file<NUM>.jpeg, I could move this to holliday\1.JPG – to capitalize the ending or whatever.
6. The last part, sh.
What did sed produce? It took a string like ‘more1 120.jpg’ and turned it into a string like ‘mv “more1 120.jpg” “120.jpg”‘. But this is a string, it is not a command.
So we piped that string to the ‘sh’ command. It would be the same as I’ve written:
sh mv “more1 120.jpg” “120.jpg” – which is what I wanted in the first place.
Hope I remember this post when I need a mass-rename next time