3 Feb '24
I was inspired to create this tutorial while updating my personal website, which is this site that you are looking at. I had logged into my web-hosting administrator's page and out of curiosity, decided to explore host-provider's inbuilt web performance monitoring tool. It was a tool which could analyse how optimised my website was. When the report was generated, I was surprised to find out that the website was running sub-optimally. The report provided a list of suggestions on how my website can be optimised, one of which was to use '.webp' images instead of the usual '.png' and '.jpeg' images.
On doing a search, I found out that WebP, which has a file extension of '.webp', is an image format developed by Google that provides both lossy and lossless compression for images on the web. It aims to create smaller file sizes without compromising image quality, thus helping web pages load faster. The conversion from other image formats to WebP can be done using the 'cwebp' command line tool by Google.
cwebp input.jpg -o output.webp
I tried it out on a jpeg file and it worked nicely. But a bigger problem loomed ahead. All the images used in the website were of .png or .jpeg formats. Converting each image manually to .webp would be a painstaking task. So, being the software engineer that I am, the idea of automation instantly came to mind. Having taken a few courses on Linux which covered shell scripting, I thought it would be a good idea to experiment with automating the image conversion. So, the process of creating a Bash script began. Click here for the Github repository.
Script requirements
The first step was to decide on the requirements. Besides converting an image to WebP format, it should work down from a root directory. In other words, it should recursively convert images which are inside a child directory.
Coding
#!/bin/bash convert_jpeg_to_webp() { }
#!/bin/bash convert_jpeg_to_webp() { local dir="$1" local file # to implement } convert_jpeg_to_webp "$(pwd)"
#!/bin/bash convert_jpeg_to_webp() { local dir="$1" local file # Loop through files and directories in the current directory for file in "$dir"/*; do if [ -d "$file" ]; then # If the item is a directory, call the function recursively convert_jpeg_to_webp "$file" fi done } convert_jpeg_to_webp "$(pwd)"
#!/bin/bash convert_jpeg_to_webp() { local dir="$1" local file # Loop through files and directories in the current directory for file in "$dir"/*; do if [ -d "$file" ]; then # If the item is a directory, call the function recursively convert_jpeg_to_webp "$file" elif [ -f "$file" ] && { [[ "$file" == *.jpg ]] || [[ "$file" == *.jpeg ]]; }; then # If the item is a JPEG file, convert it to WebP format filename=$(basename "$file") cwebp "$file" -o "${file%.*}.webp" fi done } convert_jpeg_to_webp "$(pwd)"
Running the script
chmod +x convert_jpeg_to_webp.sh
./convert_jpeg_to_webp.sh
find . -type f \( -name "*.jpeg" -o -name "*.jpg" -o -name "*.png" \) -delete
Improvements
From here, we can think of various ways to modify and extend the functionality of the script, such as converting png to webp, or from any format to another format.
In fact, as the file types are currently hardcoded, we can consider the use of variables, thus making the script more robust. Refer to my Github repo for variants of the above script. Finally, we can also implement the removal of the original file images using the script, instead of manually keying it into the terminal, as done earlier.
Conclusion
This is all for the tutorial. We have seen how we can create a bash script to automate the conversion of file images from one format to another, thus saving a lot of time. This is one of the advantages of using Linux instead of other operating systems. I experienced firsthand the practical advantages of the command line through this mini-project. I have shown a basic implementation of the script, while exploring possible implementations to improve on the existing code. Hope that you have found the tutorial useful. 😊