Detect non WOFF2 fonts and estimate gain

This commit is contained in:
Gaël Métais
2020-12-21 01:18:56 +01:00
parent dd0c17a9d4
commit d93af3d6e4
7 changed files with 170 additions and 13 deletions
+12 -6
View File
@@ -15,9 +15,6 @@ var ContentTypeChecker = function() {
function checkContentType(entry) {
var deferred = Q.defer();
debug('Entering contentTypeChecker');
debug(entry);
// Setting isSomething values:
switch(entry.type) {
@@ -59,9 +56,15 @@ var ContentTypeChecker = function() {
try {
foundType = findContentType(entry.weightCheck.bodyBuffer);
if (foundType !== null && foundType.type !== entry.type) {
debug('Content type %s is wrong for %s. It should be %s.', entry.type, entry.ulr, foundType.type);
rewriteContentType(entry, foundType);
if (foundType !== null) {
if (foundType.type === 'webfont') {
// Always rewrite fonts for woff2 checking
rewriteContentType(entry, foundType);
} else if (foundType.type !== entry.type) {
// For other kind of files, just rewrite if needed
debug('Content type %s is wrong for %s. It should be %s.', entry.type, entry.ulr, foundType.type);
rewriteContentType(entry, foundType);
}
}
} catch(err) {
@@ -188,6 +191,7 @@ var ContentTypeChecker = function() {
updateFn: function(entry) {
entry.type = 'webfont';
entry.isWebFont = true;
entry.isWoff = true;
}
},
woff2: {
@@ -196,6 +200,7 @@ var ContentTypeChecker = function() {
updateFn: function(entry) {
entry.type = 'webfont';
entry.isWebFont = true;
entry.isWoff2 = true;
}
},
otf: {
@@ -212,6 +217,7 @@ var ContentTypeChecker = function() {
updateFn: function(entry) {
entry.type = 'webfont';
entry.isWebFont = true;
entry.isTTF = true;
}
},
eot: {
+82 -5
View File
@@ -2,6 +2,8 @@ var debug = require('debug')('ylt:fontAnalyzer');
var Q = require('q');
var fontkit = require('fontkit');
var woffTools = require('woff-tools');
var ttf2woff2 = require('ttf2woff2');
var FontAnalyzer = function() {
@@ -19,25 +21,100 @@ var FontAnalyzer = function() {
if (entry.isWebFont) {
debug('File %s is a font. Let\'s have a look inside!', entry.url);
getMetricsFromFont(entry, charsListOnPage)
convertToWoff2(entry)
.then(function(entry) {
return getMetricsFromFont(entry, charsListOnPage);
})
.then(function(fontMetrics) {
entry.fontMetrics = fontMetrics;
deferred.resolve(entry);
})
.fail(function(error) {
debug('Could not open the font: %s', error);
deferred.resolve(entry);
});
} else {
deferred.resolve(entry);
}
deferred.resolve(entry);
return deferred.promise;
}
function convertToWoff2(entry) {
var deferred = Q.defer();
debug('Entering font format converter...');
if (entry.isWoff2) {
debug('File is already a woff2.');
deferred.resolve(entry);
} else if (entry.isWoff) {
debug('File is a woff. Let\'s convert to woff2');
try {
var fileSize = entry.weightCheck.bodySize;
debug('Current file size is %d', fileSize);
var ttf = woffTools.toSfnt(entry.weightCheck.bodyBuffer);
var woff2 = ttf2woff2(ttf);
var newFileSize = woff2.length;
debug('New image size is %d', newFileSize);
debug('Filesize is %d bytes smaller (-%d%)', fileSize - newFileSize, Math.round((fileSize - newFileSize) * 100 / fileSize));
entry.weightCheck.sizeAsWoff2 = newFileSize;
deferred.resolve(entry);
} catch(error) {
deferred.reject(error);
}
} else if (entry.isTtf) {
debug('File is a TTF. Let\'s convert to woff2');
try {
var fileSize = entry.weightCheck.bodySize;
debug('Current file size is %d', fileSize);
var woff2 = ttf2woff2(entry.weightCheck.bodyBuffer);
var newFileSize = woff2.length;
debug('New image size is %d', newFileSize);
debug('Filesize is %d bytes smaller (-%d%)', fileSize - newFileSize, Math.round((fileSize - newFileSize) * 100 / fileSize));
entry.weightCheck.sizeAsWoff2 = newFileSize;
deferred.resolve(entry);
} catch(error) {
deferred.reject(error);
}
} else {
// Other font formats are not handled
deferred.resolve(entry);
}
return deferred.promise;
}
// The gain is estimated of enough value if it's over 1KB or over 20%,
// but it's ignored if is below 100 bytes
function gainIsEnough(oldWeight, newWeight) {
var gain = oldWeight - newWeight;
var ratio = gain / oldWeight;
return (gain > 2048 || (ratio > 0.2 && gain > 100));
}
function getMetricsFromFont(entry, charsListOnPage) {
var deferred = Q.defer();
+40
View File
@@ -167,6 +167,10 @@ var Redownload = function() {
offenders.fontsCount = listFonts(results);
metrics.fontsCount = offenders.fontsCount.count;
// Conversion to woff2
offenders.nonWoff2Fonts = listNonWoff2Fonts(results);
metrics.nonWoff2Fonts = offenders.nonWoff2Fonts.totalGain;
// Heavy fonts
offenders.heavyFonts = listHeavyFonts(results);
metrics.heavyFonts = offenders.heavyFonts.totalGain;
@@ -551,6 +555,42 @@ var Redownload = function() {
};
}
function listNonWoff2Fonts(requests) {
var results = {
totalGain: 0,
fonts: []
};
requests.forEach(function(req) {
if (!req.isWoff2 && req.weightCheck.sizeAsWoff2) {
var before = req.weightCheck.bodySize;
var after = req.weightCheck.sizeAsWoff2;
var gain = before - after;
var type = null;
if (req.isWoff) {
type = 'woff';
} else if (req.isTtf) {
type = 'ttf';
}
if (gain > 200) {
results.totalGain += gain;
results.fonts.push({
url: req.url,
originalSize: before,
type: type,
woff2Size: after,
gain: gain
});
}
}
});
return results;
}
function listHeavyFonts(requests) {
var list = [];
var totalGain = 0;