Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Subset fontawesome fonts #194

Open
wants to merge 12 commits into
base: master
Choose a base branch
from

Conversation

Munter
Copy link
Contributor

@Munter Munter commented Aug 7, 2018

This PR adds a script that will grep the source code for occurrences of font-awesome class names, then filter out unused selectors from the font-awesome stylesheet. With the remaining selectors it will figure out which codepoints from the font files are used and create an optimal subset of the font with only these glyphs. The whole thing gets written out to a stylesheet of about 2544 bytes, which gets appended to main.css.

So it's trading 7kb of CSS and 75kb of fonts, plus extra roundtrip latency with 2544 bytes that include the font as well.

The script requires the fontawesome files to have been downloaded, like the result of running npm run build:vendor, and fits best in between npm run build:jekyll and npm run build:site.

In order to use this optimization fully there are still some changes needed, like the original fontawesome files not being included in _config.yml so they don't end up in all sorts of places. But I'm not sure how this impacts local development. I'll need some feedback to figure out how to correctly slot this into the existing workflow

Example output:

@font-face{font-family:FontAwesome;font-weight:400;font-style:normal;src:url(data:font/woff;base64,d09GRgABAAAAAAXQAAwAAAAACAgABAAHAAAAAAAAAAAAAAAAAAAAAAAAAABHREVGAAAFuAAAABYAAAAWABEACE9TLzIAAAScAAAAPgAAAGB4FHbWY21hcAAABNwAAABEAAAAZNI5wxdnYXNwAAAFsAAAAAgAAAAI//8AA2dseWYAAAEcAAAC0gAABKIeN/h3aGVhZAAABCQAAAA2AAAANhCJ5SxoaGVhAAAEfAAAAB0AAAAkDwMIB2htdHgAAARcAAAAHgAAAB4pgACAbG9jYQAABBAAAAASAAAAEgULA8RtYXhwAAAD8AAAAB0AAAAgAHECHG5hbWUAAAUgAAAAhAAAAOIN0CgEcG9zdAAABaQAAAAMAAAAIAADAAB42oxTtWPzRhR/T1g2s8yyrC8cGcOqs5SZmWEpMyrlJTyVuxQ8lbai/4HQXOaO2cKX78kOs+Duwe/xHXAA6yBZogUyJAHACQn7R6+UTmWRFlXjnO6imhD8bp9XRr9gsSU2wpZQxsd4+ZJ8UWXVr38eZSvfP/zw9yhiDMXvH34Br89wBEC5AWZW/hINr3thC0FYtjL689esmgFAgHVLBtECBUCgsG1CIV/MGTEu0M/nDL8dl38n714bOyt9SW87+71/6OErVPWKh4f6f2f/rI1bbu6mM9Tb7xkZ/Hmx+UJTVc0Lmxd//uWftc/IHdAjWRJQfQ7IQB+AmtdSktdvbO4eFxWbTGkFFwVNBvzGACYNP/pllCgXrURCW0MynytpiKDlNS2P9NP3SVlfNvVyWce5N7vf634LZ/Uy+9YVZ6a76GZm3OVqQtDCCGENoekTMtn8MMFqdUMyf6tMH+c6FWWmx4O16Kks1sKaFmYm8OBcH5MeEechCYPwIADm21FLp+SY4LNn1MZnJZ83jv4cpV3cUDpwU1babCUfKILXgWRBiEK+lG1Q+QEkLUGpx4E6JX6hzCp6U4xPnO2Ry7ojFD4nzieV6cgpXZlU1s5XphU9G51UlNnIqb0o/uVrJ69+5tmrp6++4Ybrnnvmmtlr9vBULHlP8PFzwiGHXpY9ZxPdpCszkfCEwv1PhBKZULIEisR3g9b+mL964uprZ65+5vnrbriBPO9mgQd6JBCBphyHdoCMrzHVPmzMznUML9GYli276yKth9G1OmUv+O9BZCMPke7TZh64J47HldeIl3wur5/44u7TZ9D9cp+3WjvP7T6PN89zW7dVVmuV226r8GblNqv69Grt6Wr1ad58usr9btoge2GGrd1A8q9sYmiFHfmkIQeDm/lQ0Ga0g25lRuF70D7iJ8yRfVQPzj6ys8A76gyeXgIhF2OqB5mEzwcAYXYYAQAAeNpjYGRgYOBgkmRQZwABJiBmBIs5MIABAAk3AJAAAAAAAAAAAEIAcADQAWQBqAHwAlEAAAABAAAABAHLbQwIrV8PPPUACwcAAAAAANQzzTIAAAAA1DPNMv///wAJAQYAAAAACAACAAAAAAAAA4AAcAaAAAAHAAAABoAAAAaAABAGAAAABYAAAAAAAAB42mNgZGBgY/jPwMDAyfAfCDgZgSKogB0AelgFHgAAAHjaY2Bmy2ScwMDKwMDSw2LMwMDQBqGZihkYGLsY8ICCyqJiBocPTB+nsTH8B/LZGBiBJJBAAAUGRgD7rwnSAAB42mNgYGACYmYgFgGSjGCahSEASAsAIVD8A9MHlg+SHw5+OPnR/eO0//8xRfj/8//jf8XvzG/Dt5+vEGgGGgAA7xcb03jaTIu1FQJAEEQ/DlWgKS4xTgW4u7tHtM7gvLvdHQVs1DBhMDuAFryxAbPYCxv1ei+sDYM3Nv9lLPi+uhXlybBmw5UdU8ZMOOAiS5cTQ6GC0IoBV+EIIcIkCAinWOi5/lp7xBjqDnXVZkBA76ZXQhp7ZdeslIvdBxQ3B2IDhKkAy/4Z8XjaY2BmwAsAAH0ABAAAAAH//wACAAEAAAAMAAAAAAAAAAIAAQABAAcAAQAA) format("woff")}.fa{display:inline-block;font:normal normal normal 14px/1 FontAwesome;font-size:inherit;text-rendering:auto;-webkit-font-smoothing:antialiased;-moz-osx-font-smoothing:grayscale}.fa-search:before{content:"\f002"}.fa-heart:before{content:"\f004"}.fa-download:before{content:"\f019"}.fa-chain:before,.fa-link:before{content:"\f0c1"}.fa-bars:before{content:"\f0c9"}.fa-minus-square-o:before{content:"\f147"}.fa-plus-square-o:before{content:"\f196"}

@Munter
Copy link
Contributor Author

Munter commented Aug 7, 2018

This PR closes #191

@jdalton
Copy link
Member

jdalton commented Aug 7, 2018

🤯! Thank you!

const getTemporaryFilePath = require('gettemporaryfilepath');

require('promise.prototype.finally').shim();

const allowedFormats = ['woff', 'woff2'];

const readFile = util.promisify(fs.readFile);
const execFile = util.promisify(childProcess.execFile);
const execFile = pify(childProcess.execFile);
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

^ can you use execa?

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Done

@jdalton
Copy link
Member

jdalton commented Aug 8, 2018

Rock! Thank you again @Munter!

@Munter
Copy link
Contributor Author

Munter commented Aug 9, 2018

In my mesurements I saw some problems on the individual versions of the docs, which didn't preload anything other than lodash itself. Netlify apparently clobbers the link: headers when there are multiple definitions. I added the docs client hints to all the specific versions as well

@Munter
Copy link
Contributor Author

Munter commented Aug 9, 2018

It looks to me like all the preloads of the javascript is actually hurting the first paint performance. Is there a way those scripts could be moved out of the client hints? Is the javascript really so important as to override the browsers prioritization?

@Munter
Copy link
Contributor Author

Munter commented Aug 9, 2018

Here's a performance comparison of the docs page before and after things branch: https://www.webpagetest.org/video/compare.php?tests=180809_Z9_7b995e5da2efc33ee296854297a5c8ab%2C180809_Q9_087f0a76614e24ca3e994c8b3552d38d&thumbSize=200&ival=1000&end=visual

I can't explain what's happening with the extremely late font rendering. I even added font-display: swap; to trigger an immediate render as soon as the stylesheet comes down.

https://twitter.com/_munter_/status/1027358579534249984

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Development

Successfully merging this pull request may close these issues.

None yet

2 participants