Useful Shell Oneliners
Monday, November 12th, 2007From time to time you come upon some useful oneliner in the shell. Either because you see it somewhere, see someone doing it, or because you need it and produce one yourself. And most of the time, it’s not enough to put into a shell-script, so you find yourself hunting for it in your .bash_history. Well, here are some:
Do something to a lot of files
for i in *; do command $i; done
You’ll need this a lot. Does not work with files containing spaces
Convert a load of images
for i in *.tif; do convert -quality 75 $i `basename $i .tif`.jpeg;
Make pdf out of a several images
convert -limit memory 32 -limit map 32 *.png target.pdf
You really want to set the limits, unless you have more RAM than the whole images converted to pbm.
With Graphicsmagick, you need to set a compression for jpg, otherwise the resulting PDF will be huge.
gm convert -compress JPEG *.jpg target.pdf
The resources you want to give those programs can be set using environment-variables:
export MAGICK_MEMORY_LIMIT="640mb"
export MAGICK_MAP_LIMIT="320mb"
export MAGICK_AREA_LIMIT="640mb"
Make pdf out of a lot of images
But the whole idea of using ImageMagick or GraphicsMagick to create pdf-files is very much flawed, since both first convert the jpeg-files into an raw, uncompressed intermediate format which tends to eat up all available memory, and then crash. And which is completely nonsensical too, since jpeg-files can be embedded into pdf as they are. Luckily, pdfjoin will help us, tough it accepts only files with the extension ‘.pdf’ as input as of yet:
mmv '*.jpg' '#1.pdf'; pdfjoin --outfile target.pdf *.pdf
Change resolution (DPI) of an image
convert -density 600 -units PixelsPerInch source.png target.png
split/crop pictures
convert -crop 1230x880 source.png target
Note that this does not really crop the image, but splits it into as many parts as necessary, using “target” as prefix, adding a number as suffix.
fix offset
convert +repage source.png target
Lately, “crop” seems to behave differently, it leaves all but the first part with an offset. This makes the picture disappear in gimp, and stretched if you make a pdf out of it. That’s why you may need to repage.
rotate
convert -rotate 90 source.png target
rotates 90 degrees clockwise.
Attach pictures to each other, one below the other
montage +frame +shadow +label -tile 1x2 -geometry "widthxheight+0+0" source1.png source2.png target.png
Important is that width and height are the dimensions of each of the sources. For putting them next to each other, just use 2×1 as tile.
Rename files according a textfile-list
for i in `cat list` ; do mv `echo $i | awk -F"-" '{print $1".ext"}'` $i.ext ; done
Delete empty directories
find . -type d -empty -depth -exec rmdir {} \;
Remove first page of a PDF
pdftk A=source.pdf cat A2-end output target.pdf
Yes, pdftks syntax is a bit alien.
Merge PDFs
pdftk sources*.pdf cat output target.pdf
Unpack lots of packed files into different directories
for i in *.rar; do mkdir `basename $i .rar`; mv $i `basename $i .rar`; cd `basename $i .rar`; rar x $i; cd ..; done
If you have a load of packed files, in this case rar, and you want to unpack each into a different subdirectory, according to the name of the rar-file.
Get rid of magnatune-advertisements in mp3s
for i in *.mp3; do mp3splt -s -p min=2 -d `basename $i .mp3` $i ; done
Merge AVI-movies
mencoder -forceidx -oac copy -ovc copy -o outputfile.avi parts*.avi
That’s the basic way. If you want to process a whole directory with avi-files whose filenames have a distinct part (like “cd≶num>” or “-Part≶num>” as in my example) you can do something this:
for i in *-Part1.avi; do mencoder -forceidx -ovc copy -oac copy -o `basename $i -Part1.avi`.avi `basename $i -Part1.avi`-Part*.avi; done
To be continued. You might also want to check out my Program-section for small useful scripts.