Recovering front-end developer, now I just write JavaScript

Multiple Folders to Multiple Zips

How to create multiple zips from multiple folders

Multiple Folders to Multiple Zips
Photo by Garmin B / Unsplash

If you have a bunch of folders and want to individually zip them up, the simplest method is to right click and compress the folder. But, if you have many folders it can get tiresome.

I searched around and found a way to to run a small bash script that will loop through the top-level folders in a directory and create a zip from it.

For example, say you have:

Main folder:
  - MyFolder
  - Another Folder
  - Yet more folder

cd into the main folder, cd Main\ folder and then run one of the below:

# Loud mode
for i in */; do zip -r "${i%/}.zip" "$i"; done

# Quiet mode
for i in */; do zip -q -r "${i%/}.zip" "$i"; done

The result of the above is:

Main folder:
  - MyFolder
  - Another Folder
  - Another
  - Yet more folder
  - Yet more

I was using this to backup a load of working files and it worked a charm.

Happy archiving!

Download Images From a Text File

How to download images from a text file, and maybe retain the folder structure

Let's say you have a list of images that another tool has created. Let's say you need to download each of those images and then do something with them. Instead of manually pasting each URL into a browser and saving the image, this trick will do them all in one go.

Create a text file like, such as images.txt. Enter all the URLs into it like so:

Assuming you have wget installed, cd into the folder with the text file in, and run this:

wget -i images.txt

It'll download the image in the same folder, and you'll end up with a folder structure like this:


And that's it! You now have all the images listed in the text file, saved locally.

Update: Jan 17th 2022

If you add -x after the file name, it will replicate the remote file structure. Taking our earlier example of:

With the updated command:

wget -i images.txt -x

Will yield the following:

Update: Nov 21st 2023

Sometimes, you might need to set a header. Here's how to do that.

header='--header=User-Agent: Mozilla/5.0 (Windows NT 6.0) AppleWebKit/537.11 (KHTML, like Gecko) Chrome/23.0.1271.97 Safari/537.11'
wget "$header" -i images.txt -x

Staging & Production Shopify Themes with Theme Kit

How I manage Shopify theme development

Staging & Production Shopify Themes with Theme Kit
Photo by Mohammad Rahmani / Unsplash

Shopify has a library called Theme Kit, which lets you use your local environment to build theme that then deploy to Shopify and lat yo preview on their infrastructure. Most tutorials will guide you in setting this up akin to mid 2000's development where you FTP every change to the server and view the changes on the live site.

The trouble with this comes when you want to work on something that will take more than 2 minutes, and don't want to interrupt the live site and potentially cause issues with people trying to purchase stuff. You wouldn't change the wheel on a moving car.

Thankfully, Theme Kit is configurable and there's a few ways to drastically improve this process.

There's a little bit of legwork to get started, but once done, it's simple.

On Shopify

  • Navigate to the Themes section and create a duplicate of the current live theme
  • Rename the live theme to Your Theme - Production
  • Rename the new duplicate to Your Theme - Development (To help differentiate)
  • Hit [Customise] on the Production theme, and copy the numbers in the URL. This is the theme ID.
  • And do the same for the Development theme.

At this point you should have 2 copies of the same theme, and an ID for each version of that theme.

  • Your Theme - Production123456789123
  • Your Theme - Development123456789456

Local development changes

In config.yml, set development and production environments.

  password: a1b2c3d4
  theme_id: "1234"
  - themekit_ignores # Ignores files in ./.themeignore
  password: a1b2c3d4
  theme_id: "1234"
  - themekit_ignores # Ignores files in ./.themeignore

Of the Commands section below, one deploys all files whether they have changed or not, so we need to make sure that any files we don't want synced are ignored. For example, config/settings_data.json caused me some headaches (it wiped all custom settings fields), so that's definitely important to ignore.

Your .themeignore file should look something like this, depending how your theme's built:



The day-to-day work involves running gulp and the below command in another shell tab.

# Upload changes to the development theme
theme watch --env=development

When I'm ready to deploy all changes, I run gulp build, and the below:

# Deploy changes to production theme
theme deploy --allow-live --env=production

Previewing things

All fo this is great, but if there's no way to preview the changes, what's the point?

Shopify lets you preview any theme installed on your site. By knowing the theme ID, you san skip the step of needing to go into Shopify and opening the preview every time you need it.

Now you have a staging version of your Shopify theme, and a single command to deploy that to production.

Happy theming!

Detailing a New Car

Detailing a New Car

It’s been a while, hasn’t it. Since my last post, the new car has: been assembled from a pile of aluminum, steel, plastic, and several dead cows; been shipped from South Carolina USA to Southampton UK; passed through customs; and finally transported to Berry BMW at Heathrow.

It was there for all of 48 hours before I arrived to collect it, in all its unwashed glory, per my request.

View this post on Instagram

Look! Worlds tallest man buys X3 M40i. Shock. ☝️☝️☝️🤔 he really is taller than @joeachilles and it was Joes channel that had brought @pauladamdavis all the way down to Heathrow to order up this amazing spec X3 M40i. And before anyone says that we forgot to valet it... that’s because Paul has got @themattfinish working on it all of next week. More clean pics to follow. Enjoy the car buddy. 🔥🔥🔥 ———————————————— 💻: 🖥: 📺: @joeachilles (YouTube) ———————————————— #TRLDeals #BimmerDeals #MINIDeals #BMW #BMWM #MPower #MINI #JCW #JohnCooperWorks #S #Cooper #Performance #Competition #BMWGram #BMWPost #BMWLife #BMWWorld #BimmerPost #BimmerNation #UltimateDrivingMachine #bmwrepost #bmwx3 #bmwx3m40i #bmwx3m #carsofinstagram #instacars #bestsuvever

A post shared by Tony Lewis - TRLDeals (@trldeals) on

When I ordered the new car back in January, one of the first things I wanted to do (if budget allowed) was get it detailed by someone with considerable more skill than me. I’d say I’m a competent weekend-worrier, but as soon as it comes to paint correction and ceramic coatings, I get nervous. I’d rather pay someone to do it right once, than pay even more to correct my mistakes.

So, when I got a better idea of delivery dates, I contact Matt at The Matt Finish to get it booked in for a ‘new car detail’. That means that pretty much every surface visible for protection. The engine bay was dressed; wheels, suspension components and breaks ceramic coated, paint corrected and coated. I had the black plastic surrounding the windows and rear windows covers, and even the mirror caps covered in matte PPF, as they have a matte finish from factory.

Look that that gloss!

The paint is coated with Siramik SC Altum, Ultima and Diamas, the wheels and plastics in CarPro Dlux, and Gtechniq G1 on all glass, Dr Leather Dye Block on leather, Gtechniq I1 on fabrics, and finally Aerospace 303 on the engine bay.

I’d say that’s pretty comprehensive, and I’m chuffed to bits with it. All of that effort means that I (right so) need to take proper care of it. What’s the point of it being absolutely perfect if I then wash it with a sponge with Fairy liquid on a hot day, and let it dry in the sun?

With Matt’s help and recommendations, I purchased about £400 worth of new detailing equipment. I had some, but wanted to refresh any older things I had. So, 3 buckets, shampoo, wheel cleaners, various brushes, new wash mitt, microfiber clothes, spray bottles, tyre dressing, and pressure washer, and a multitude of other bits & pieces.

I've ordered a BMW X3 M40i

I've ordered a BMW X3 M40i

Let me explain.

I’ve grown tired of the hot hatch market. I currently own (owned?) a Ford Focus ST-3. It was a fun car, and I specced it relatively well, but it had issues from the start. The 19″ wheels I specced left little in the way of comfort, and the infotainment system definitely shows its age. Trying to zoom and pan around the sat nav map was infuriatingly slow. It also made my wife queasy on long journeys, and after a long journey on my own, my ears felt hot and pained.

The qualities that led to those issues, where the same qualities that made it fun to drive on dry, country roads. The car, assuming you understood its purpose, fulfilled its role in life. I have no real complaints about the car itself, but I feel i’ve outgrown that market.

I’m 28 years old now. I’m beyond trying to show off with wheels, badges, and exhausts. But, I still want some fun.


  • Phytonic Blue
    • All of my previous cars have either been black, or silver, with the exception of a dark blue Audi A3 for a brief period. I’m bored of cars that look no different with a B&W filter, and that blend in to the typically miserable British weather. The Phytonic Blue is different enough to be interesting, but not overly bright – I don’t want to stand out too much.
  • Black with grey contrast stitching Vernasca leather.
    • As much as I’d like a lighter interior, black is classic, ages relatively well, and effectively eliminates dye transfer.
  • 20″ 669M Wheels, with fun flats
    • I prefer the look of the 21″ 718M wheels, but I’m happy to have a smaller wheel if it means a slightly taller side-wall, and more stealthy look. 20″ it is.
    • The 20’s have 12mm more sidewall that the 21’s, and the 20’s have 28mm more sidewall than the 19’s on my Focus ST.
  • “Technology package”, which includes:
    • This consists of the Display Key. A largely useless key (apparently) with some occasionally useful features.
    • Head-up Display. I’m not sure yet how good BMW’s sat nav is. If it’s pants, I’ll use Google Maps via CarPlay, and only use the head-up for media stuff. If it’s good, I’ll use it for directions too.
    • “Enhanced Bluetooth with wireless charging” – wireless charging for my phone (and that Display Key)!
    • BMW Gesture Control“. A fun ‘look at this’ feature, but not one I’ll use often I’m sure.
    • WiFI Hot Spot Preparation – Everyone I know has data on their phones. Not useful to me at all.
  • “Comfort package”, which includes:
    • “Comfort Access” because I haven’t used a fob button to open a car door in about 6 years.
    • “Acoustic glazing” – Hopefully this kills some noise on long motorways journeys. I know the car itself is going to be quieter anyway, may as tick this box to help it a bit more.
    • “Exterior Mirrors – folding with anti-dazzle” – Why this is an option and not a standard is beyond me. The ‘anti-dazzle’ bit nice nice. You know the little switch (?) under the rear view mirror in most cars to stop you being blinded? This, but automatically, but on all mirrors.
    • “Rear Seat Backrest Adjustment” – I’m sure the few people who’ll ever sit in the back for any significant time will appreciate this
    • “Extended storage” – This adds a gas strut to the boot floor to keep it up when lifted. Given I’ll store some cleaning chemicals and microfibres under there, this is welcome.
  • “Steering wheel heating” – It’s £170. Nobody likes a cold steering wheel art 7am on a February morning.
  • “Adaptive M Sport suspension”, because it’s such a cheap option at £530 (comparatively) it’d be silly not to. I hope this gives the car duel personalities. Sport for me, comfort for everyone else.
  • “Panoramic glass sunroof” because the black leather interior will need all the brightening up it can get. And, it helps the interior – whatever the colour – feel more open.
  • “Sun protection glass” which, if you’ve read about the leather colour and pano roof, seems counterintuitive. It is, but it helps the outside look cleaner. The open glass roof counteract the slight loss of light from the side.
  • “Lumbar support, driver and front pass” – I had this on my BMW 335i coupé a few years back, and it’s the thing I miss most about that car. Essentially, it’s some inflatable air bags in the seats which I can set to push into my lower back. Amazing.
  • “Galvanic embellisher for controls” – A purely aesthetic option that changes a majority of the switchgear from black plastic to a metallic plastic (not real metal, I think), to lighten small parts of the interior and make controls stand out a bit.
  • “Driving Assistant Plus” – Ah, this one is kind of experimental. It encompasses:
    • “Active Cruise Control with Stop&Go”. I want this as a safer cruise control, as it’ll slow when it gets close to the car ahead of me. And in heavy traffic, it’ll even come to a standstill, and then continue on. Is this what dreams are made of?
    • Lane assistance, because driving home from the airport after a 3am landing isn’t fun.
    • A slew of tangentially related safety systems to help prevent me crash, and prepare the car fir being crashed into.
  • “Parking Assistant Plus” – So, this one is mostly marketed as the “it’ll park for you” thing, but I want it for the 360° camera, which will be all sorts of run, and wheel-saving.
  • “harman/kardon surround sound” (BMW don’t capitalise it, weirdly) – I listen to music through studio monitors all day. I know any car audio system is inherently compromised, but I wanted to give it the best shot.
  • “Apple CarPlay preparation” – Duhh

So there’s my spec, with an explanation for all of it. I intend to keep this car for years after the 4-year PCP deal is up, so I wanted to make sure it has everything I want now, and what I may want in the future.

Delivery is expected mid April 2019. As I get some more interesting information, I’ll share it here.

Hi! I'm Paul 👋 I write code for a living. Specifically, I work at Ghost where I build & maintain the tooling that enables migrations from other platforms to Ghost.

On this blog, I mostly share random things I find interesting or useful. There is no pattern, there is no plan.