Skip to content

Instantly share code, notes, and snippets.

@ivangeorgiev
Last active May 30, 2019 07:28
Show Gist options
  • Save ivangeorgiev/5f9a4e5d0ec8fea71105fc5f9e8963c2 to your computer and use it in GitHub Desktop.
Save ivangeorgiev/5f9a4e5d0ec8fea71105fc5f9e8963c2 to your computer and use it in GitHub Desktop.
Optimize image files for web site.
# Docker image with ImageMagick installed
#
# To build a docker image, execute:
# docker build -t imagick .
#
# To create a docker container, execute:
# docker run -it --rm --name imagick -v ${PWD}:/mydata -w /mydata imagick
FROM ubuntu:19.04
RUN apt-get update \
&& apt-get -y install imagemagick
#! /bin/bash
# Optimize image files:
# - Source is specified in ARG[1], default "upload"
# - Target is specified in ARG[2], default "output"
# - Process recursively
# - Preserve (mirror) directory structure and file names
# - Process JPG files (METHOD_JPG=<optimize-method>)
# - Process PNG files (METHOD_PNG=<optimize-method>)
# - Process OTHER files (METHOD_OTHER=<optimize-method>)
# - Optimize method "copy"
# - Optimize method "jpg"
# - Optimize method "skip"
# - Copy (preserve) files with optimization error
# - (jpg) For files not exceeding JPG_SMALL_LIMIT bytes apply "copy" optimization
# - (jpg) apply quality JPG_QUALITY
# - (jpg) resize to MAX_WIDTH and/or MAX_HEIGHT
#
#
# Usage: optimize-images.sh [<input-directory> [<output-directory>]]
#
# GitHub: https://gist.github.com/ivangeorgiev/5f9a4e5d0ec8fea71105fc5f9e8963c2
#
################################################################
# BEGIN CONFIGURATION #
################################################################
# Directories
IN_DIR=${1:-upload}
OUT_DIR=${2:-output}
# Optimization methods per file type
METHOD_PNG=jpg
METHOD_JPG=jpg
METHOD_OTHER=copy
# Optimization settings
MAX_WIDTH=800
MAX_HEIGHT=600
JPG_QUALITY=82
JPG_SMALL_LIMIT=30000
################################################################
# END CONFIGURATION #
################################################################
################################################################
# BEGIN OPTIMIZATION METHODS #
################################################################
function optimize_copy() {
local message=${1:-(copy) $f}
echo $message
cp $f $OUT_DIR/$f
}
function optimize_skip() {
local message=${1:-(skip) $f}
echo $message
}
function optimize_jpg() {
echo -n "(jpg)"
if (( $fsize > $JPG_SMALL_LIMIT )); then
echo " $f"
if ! convert $f -quality ${JPG_QUALITY} -resize "${MAX_WIDTH}>" -resize "x${MAX_HEIGHT}>" jpeg:$OUT_DIR/$f; then
echo -n " --- JPEG Error: "
optimize_copy
fi
else
echo -n "[small: $fsize B]"
optimize_copy
fi
}
################################################################
# END OPTIMIZATION METHODS #
################################################################
################################################################
# BEGIN FILE TYPE HANDLERS #
################################################################
function handle_other() {
echo -n "OTHER: "
optimize_$METHOD_OTHER
}
function handle_jpg() {
echo -n "JPG: "
optimize_$METHOD_JPG
}
function handle_png() {
echo -n "PNG: "
optimize_$METHOD_PNG
}
################################################################
# END FILE TYPE HANDLERS #
################################################################
################################################################
# BEGIN MAIN #
################################################################
echo Processing $IN_DIR
for f in $(find $IN_DIR -type f | sort); do
fname=$(basename $f)
dname=$(dirname $f)
fext=${fname##*.}
fsize=$(stat -c%s "$f")
mkdir -p ${OUT_DIR}/$dname
case $fext in
jpg | jpeg | JPG | JPEG)
handle_jpg
;;
png|PNG)
handle_jpg
;;
*)
handle_other
;;
esac
done
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment