Search code examples
csscompressiongoogle-webfonts

Why doesn't Google compress their webfont CSS?


I was looking through how Google's Webfonts work, and found out that when one places something like

@include url('https://fonts.googleapis.com/css?family=Archivo+Narrow:400,400italic,700,700italic');

in one's stylesheet, the CSS interpreter then GETs what's at the given URL:

/* latin-ext */
@font-face {
  font-family: 'Archivo Narrow';
  font-style: normal;
  font-weight: 400;
  src: local('Archivo Narrow Regular'), local('ArchivoNarrow-Regular'), url(https://fonts.gstatic.com/s/archivonarrow/v5/DsLzC9scoPnrGiwYYMQXpj3sPXe5Q4a3bCZMR7ryN4o.woff2) format('woff2');
  unicode-range: U+0100-024F, U+1E00-1EFF, U+20A0-20AB, U+20AD-20CF, U+2C60-2C7F, U+A720-A7FF;
}
/* latin */
@font-face {
  font-family: 'Archivo Narrow';
  font-style: normal;
  font-weight: 400;
  src: local('Archivo Narrow Regular'), local('ArchivoNarrow-Regular'), url(https://fonts.gstatic.com/s/archivonarrow/v5/DsLzC9scoPnrGiwYYMQXpkU-p1xzoRgkupcXIqgYFBc.woff2) format('woff2');
  unicode-range: U+0000-00FF, U+0131, U+0152-0153, U+02C6, U+02DA, U+02DC, U+2000-206F, U+2074, U+20AC, U+2212, U+2215, U+E0FF, U+EFFD, U+F000;
}
/* latin-ext */
@font-face {
  font-family: 'Archivo Narrow';
  font-style: normal;
  font-weight: 700;
  src: local('Archivo Narrow Bold'), local('ArchivoNarrow-Bold'), url(https://fonts.gstatic.com/s/archivonarrow/v5/M__Wu4PAmHf4YZvQM8tWsGwfvudCZ8RknLCBmdpmlzc.woff2) format('woff2');
  unicode-range: U+0100-024F, U+1E00-1EFF, U+20A0-20AB, U+20AD-20CF, U+2C60-2C7F, U+A720-A7FF;
}
/* latin */
@font-face {
  font-family: 'Archivo Narrow';
  font-style: normal;
  font-weight: 700;
  src: local('Archivo Narrow Bold'), local('ArchivoNarrow-Bold'), url(https://fonts.gstatic.com/s/archivonarrow/v5/M__Wu4PAmHf4YZvQM8tWsBKUK2vxztsQZZBkxIuj92o.woff2) format('woff2');
  unicode-range: U+0000-00FF, U+0131, U+0152-0153, U+02C6, U+02DA, U+02DC, U+2000-206F, U+2074, U+20AC, U+2212, U+2215, U+E0FF, U+EFFD, U+F000;
}
/* latin-ext */
@font-face {
  font-family: 'Archivo Narrow';
  font-style: italic;
  font-weight: 400;
  src: local('Archivo Narrow Italic'), local('ArchivoNarrow-Italic'), url(https://fonts.gstatic.com/s/archivonarrow/v5/vqsrtPCpTU3tJlKfuXP5zY_xx5DQT9YeiXYckfzGhA8.woff2) format('woff2');
  unicode-range: U+0100-024F, U+1E00-1EFF, U+20A0-20AB, U+20AD-20CF, U+2C60-2C7F, U+A720-A7FF;
}
/* latin */
@font-face {
  font-family: 'Archivo Narrow';
  font-style: italic;
  font-weight: 400;
  src: local('Archivo Narrow Italic'), local('ArchivoNarrow-Italic'), url(https://fonts.gstatic.com/s/archivonarrow/v5/vqsrtPCpTU3tJlKfuXP5zeEHrUcvG35DlvKNjpX7jU4.woff2) format('woff2');
  unicode-range: U+0000-00FF, U+0131, U+0152-0153, U+02C6, U+02DA, U+02DC, U+2000-206F, U+2074, U+20AC, U+2212, U+2215, U+E0FF, U+EFFD, U+F000;
}
/* latin-ext */
@font-face {
  font-family: 'Archivo Narrow';
  font-style: italic;
  font-weight: 700;
  src: local('Archivo Narrow Bold Italic'), local('ArchivoNarrow-BoldItalic'), url(https://fonts.gstatic.com/s/archivonarrow/v5/wG6O733y5zHl4EKCOh8rSR5iW2BxMHezLzQnpy1d6Fo.woff2) format('woff2');
  unicode-range: U+0100-024F, U+1E00-1EFF, U+20A0-20AB, U+20AD-20CF, U+2C60-2C7F, U+A720-A7FF;
}
/* latin */
@font-face {
  font-family: 'Archivo Narrow';
  font-style: italic;
  font-weight: 700;
  src: local('Archivo Narrow Bold Italic'), local('ArchivoNarrow-BoldItalic'), url(https://fonts.gstatic.com/s/archivonarrow/v5/wG6O733y5zHl4EKCOh8rSflEgKdwIoor_PG0pLo4YVU.woff2) format('woff2');
  unicode-range: U+0000-00FF, U+0131, U+0152-0153, U+02C6, U+02DA, U+02DC, U+2000-206F, U+2074, U+20AC, U+2212, U+2215, U+E0FF, U+EFFD, U+F000;
}

Now, knowing Google, they like to get as much information to their user in as few bytes as possible. This is easily seen in the source code of google.com, where every image, stylesheet, and script is embedded in the HTML without any extraneous whitespace. This means it's all gotten in one go without another request as fast as possible. Now, knowing Google likes to do all this, why isn't the above GET something like:

@font-face{font-family:'Archivo Narrow';font-style:normal;font-weight:400;src:local('Archivo Narrow Regular'),local('ArchivoNarrow-Regular'),url(https://fonts.gstatic.com/s/archivonarrow/v5/DsLzC9scoPnrGiwYYMQXpj3sPXe5Q4a3bCZMR7ryN4o.woff2)format('woff2');unicode-range:U+0100-024F,U+1E00-1EFF,U+20A0-20AB,U+20AD-20CF,U+2C60-2C7F,U+A720-A7FF;}@font-face{font-family:'Archivo Narrow';font-style:normal;font-weight:400;src:local('Archivo Narrow Regular'),local('ArchivoNarrow-Regular'),url(https://fonts.gstatic.com/s/archivonarrow/v5/DsLzC9scoPnrGiwYYMQXpkU-p1xzoRgkupcXIqgYFBc.woff2)format('woff2');unicode-range: U+0000-00FF,U+0131,U+0152-0153,U+02C6,U+02DA,U+02DC,U+2000-206F,U+2074,U+20AC,U+2212,U+2215,U+E0FF,U+EFFD,U+F000;}@font-face{font-family:'Archivo Narrow';font-style:normal;font-weight:700;src:local('Archivo Narrow Bold'),local('ArchivoNarrow-Bold'),url(https://fonts.gstatic.com/s/archivonarrow/v5/M__Wu4PAmHf4YZvQM8tWsGwfvudCZ8RknLCBmdpmlzc.woff2)format('woff2');unicode-range:U+0100-024F,U+1E00-1EFF,U+20A0-20AB,U+20AD-20CF,U+2C60-2C7F,U+A720-A7FF;}@font-face{font-family:'Archivo Narrow';font-style:normal;font-weight:700;src:local('Archivo Narrow Bold'),local('ArchivoNarrow-Bold'),url(https://fonts.gstatic.com/s/archivonarrow/v5/M__Wu4PAmHf4YZvQM8tWsBKUK2vxztsQZZBkxIuj92o.woff2)format('woff2');unicode-range:U+0000-00FF,U+0131,U+0152-0153,U+02C6,U+02DA,U+02DC,U+2000-206F,U+2074,U+20AC,U+2212,U+2215,U+E0FF,U+EFFD,U+F000;}@font-face{font-family:'Archivo Narrow';font-style:italic;font-weight:400;src:local('Archivo Narrow Italic'),local('ArchivoNarrow-Italic'),url(https://fonts.gstatic.com/s/archivonarrow/v5/vqsrtPCpTU3tJlKfuXP5zY_xx5DQT9YeiXYckfzGhA8.woff2)format('woff2');unicode-range:U+0100-024F,U+1E00-1EFF,U+20A0-20AB,U+20AD-20CF,U+2C60-2C7F,U+A720-A7FF;}@font-face{font-family:'Archivo Narrow';font-style:italic;font-weight:400;src:local('Archivo Narrow Italic'),local('ArchivoNarrow-Italic'),url(https://fonts.gstatic.com/s/archivonarrow/v5/vqsrtPCpTU3tJlKfuXP5zeEHrUcvG35DlvKNjpX7jU4.woff2)format('woff2');unicode-range:U+0000-00FF,U+0131,U+0152-0153,U+02C6,U+02DA,U+02DC,U+2000-206F,U+2074,U+20AC,U+2212,U+2215,U+E0FF,U+EFFD,U+F000;}@font-face{font-family:'Archivo Narrow';font-style:italic;font-weight:700;src:local('Archivo Narrow Bold Italic'),local('ArchivoNarrow-BoldItalic'),url(https://fonts.gstatic.com/s/archivonarrow/v5/wG6O733y5zHl4EKCOh8rSR5iW2BxMHezLzQnpy1d6Fo.woff2)format('woff2');unicode-range:U+0100-024F,U+1E00-1EFF,U+20A0-20AB,U+20AD-20CF,U+2C60-2C7F,U+A720-A7FF;}@font-face{font-family:'Archivo Narrow';font-style:italic;font-weight:700;src:local('Archivo Narrow Bold Italic'),local('ArchivoNarrow-BoldItalic'),url(https://fonts.gstatic.com/s/archivonarrow/v5/wG6O733y5zHl4EKCOh8rSflEgKdwIoor_PG0pLo4YVU.woff2)format('woff2');unicode-range:U+0000-00FF,U+0131,U+0152-0153,U+02C6,U+02DA,U+02DC,U+2000-206F,U+2074,U+20AC,U+2212,U+2215,U+E0FF,U+EFFD,U+F000;}

which would shave off 399 bytes in this example (easily more if shorter URLs are made for the fonts, maybe something like http://f.g.co/A6ofNp), which can easily add up to gigabytes on their end given how much traffic there is to Google's webfonts.

Why would they do this? It seems strange that Google would let something like transmission efficiency slip, so I feel there must be a reason. My first reasoning is that maybe some browsers or some standard somewhere requires the whitespace, or something to that effect.


Solution

  • @Blazemonger's point about compression algorithms costing more than transmitting the whitespace is not very accurate because, knowing Google, they've probably hard-coded that whitespace anyway (i.e., it's not generated by humans or even a specific generator for CSS, just a fixed string).

    Now, there's a few things to consider:

    1. It's easier to developers to understand what Google Fonts is doing if they can read the generated code.
    2. Those "developers" may be just designers that can scratch some code together, not enough to know that you can pretty-print CSS. It's easier for them if the code's readable to begin with.
    3. Google probably GZips that. In Huffman coding, it doesn't matter if a fixed string is always a ; or twenty spaces, it's going to occupy roughly the same lenght overall. GZip will perform especially well on evenly-spaced stuff like this sort of generated code.
    4. You mention a saving of 107 bytes. Did you consider that the HTTP headers alone may be larger than that? (They are). Also, if Google hosts Youtube videos in 1080p for free (4K to come soon), 107 bytes is likely laughing matter to them.