I’m working on a project that uses Node.js and Pug, formerly Jade, to generate a static website and I couldn’t be more happy about how this works.
Still, one thing was bothering me for some time, and namely how to efficiently include a minified, production-ready SVG icon system, using symbol
s within the Pug pages.
TL;DR
I had to find a better way to include an SVG icon system, both inline and minified, using symbol
s within the Pug generated files.
- I minified the
symbols.svg
output withimagemin
- I read the resulted content and passed it to Pug using the
locals
object. - I inlined the already now minified SVG result in the source files using a Pug dot block.
The struggle
The system that helps to generate the static files consists of gulp
, pug
, sass
, imagemin
, uglify
and all the front-end buzzwords you can think of. Lots of buzzwords, I told you I know how to make websites.
Leaving the joke aside, Pug, formerly Jade, has a simple mechanism to include non-Pug files as raw text and it works just fine.
All good except the fact that if you choose to minify the Pug files output, e.g. when in production
, if your included non-Pug files aren’t minified/uglified already, you’ll end up with some mixed output in your final HTML source file.
Mixed HTML code output, both minified and non-minified
In the beginning, I have to admit I started by having two files to maintain: symbols.svg
and symbols.min.svg
and whenever a new symbol was added to symbols.svg
, had to update the symbols.min.svg
file too. I’m not so proud of this, but it worked, and I knew I had to find a better way to handle this situation.
My take on this
New year, new ideas.
It’s not new year’s resolution or something like that, but the first thing I made when got back to work in 2019, besides updating the footers to © 2019 :), was to handle this SVG inline include in my Pug files.
Here’s how the symbols.svg
icon system looks like:
Quick tip
The display
attribute lets you control the rendering of graphical or container elements. No need to add any CSS class helper to visually hide the SVG content. More on MDN.
The following gulp task excerpt will move and optimize the symbols.svg
. Note the SVGO options that we’re passing on for our SVG, they are useful and mandatory in this case otherwise lots of stuff will get removed from the optimized output.
Within the pugTask
, I’m passing the already minified SVG file as a property of the locals
object, which is part of the Pug API. Also, I always make sure the above gulp imagesTask
runs before the pugTask
, in order to have the locals.svg
available. As I just switched everything to gulp 4, I use series() to execute tasks one after another.
Finally, I’ll be able to include the minified result in a partial Pug file using a dot block of plain text and unescaped string interpolation:
From Pug docs:
That’s it!
Better, beautiful & minified HTML output
I’m pretty happy I managed to find a way to improve this piece within my build process and will dig even further to see how to improve things. Let me know if you know a better way to do it, would love to hear it!