fxa-content-server/grunttasks/sriify.js

88 строки
2.7 KiB
JavaScript

/* This Source Code Form is subject to the terms of the Mozilla Public
* License, v. 2.0. If a copy of the MPL was not distributed with this
* file, You can obtain one at http://mozilla.org/MPL/2.0/. */
var url = require('url');
module.exports = function (grunt) {
function normalizeSriDirectives(sriDirectives) {
var normalized = {};
Object.keys(sriDirectives).forEach(function (key) {
var cleanedKey = key.replace(/@?dist/, '');
normalized[cleanedKey] = sriDirectives[key];
});
return normalized;
}
function addSriAttributesToResourceElements(directives, html) {
return html.replace(/(?:src|href)="([^"]*)"/gi, function (match, resourceUrl) {
var parsedUrl = url.parse(resourceUrl);
var directive = directives[parsedUrl.pathname];
if (directive) {
return match + ' integrity="' + directive.integrity + '" crossorigin="anonymous"' ;
}
return match;
});
}
function updateHtmlWithSriAttributes(directives, src) {
var html = grunt.file.read(src);
var htmlWithIntegrity = addSriAttributesToResourceElements(directives, html);
if (html !== htmlWithIntegrity) {
grunt.log.writeln('Adding SRI directives to', src);
grunt.file.write(src, htmlWithIntegrity);
}
}
grunt.registerMultiTask('sri-update-html', 'Update HTML with SRI attributes', function () {
// open each HTML file
// look for src, href
// look up url in sri table
// if url in sri table, insert integrity tag
// write HTML file if any changes to file
var options = this.options({});
var sriDirectives = normalizeSriDirectives(grunt.file.readJSON(options.directives));
this.filesSrc.forEach(
updateHtmlWithSriAttributes.bind(null, sriDirectives));
});
grunt.config('sri-update-html', {
options: {
directives: '<%= yeoman.tmp %>/sri-directives.json'
},
dist: { //eslint-disable-line sorting/sort-object-props
src: [
'<%= yeoman.page_template_dist %>/**/*.html'
]
}
});
grunt.config('sri', {
options: {
algorithms: [ 'sha512' ],
dest: '<%= yeoman.tmp %>/sri-directives.json'
},
dist: { //eslint-disable-line sorting/sort-object-props
src: [
'<%= yeoman.dist %>/**/*.css',
'<%= yeoman.dist %>/**/*.js',
]
}
});
grunt.registerTask('sriify', 'Add SRI integrity attributes to static resources', function (subtaskName) {
// sri is run twice. The first time to find the sri hashes for
// the resources embedded in main.js. This will modify main.js
// so sri must be called again to find the final sri value for
// main.js in the html.
grunt.task.run('sri', 'sri-update-html');
});
};