commit f8369f3bc05351017b5d9e749968326f84130295 Author: Alexandre Gigliotti Date: Wed Jul 22 15:51:14 2015 -0700 Initial commit. diff --git a/.gitignore b/.gitignore new file mode 100644 index 0000000..78ed38d --- /dev/null +++ b/.gitignore @@ -0,0 +1,2 @@ +node_modules +test/test.html \ No newline at end of file diff --git a/lib/index.js b/lib/index.js new file mode 100644 index 0000000..514aeea --- /dev/null +++ b/lib/index.js @@ -0,0 +1,68 @@ +var co = require('co'); +var inlineLess = require('inline-less'); +var inlineCssUrl = require('inline-css-url'); +var cheerio = require('cheerio'); +var string = require('string'); +var fs = require('mz/fs'); + +// TODO refactor into separate module +// inline html images +var localPath = require('local-path'); +var datauri = require('datauri'); +var path = require('path'); +var inlineImg = function (html, filePath) { + var basedir = path.dirname(filePath); + var $ = cheerio.load(html); + var images = $('img').filter(function (index, element) { + return localPath($(element).attr('src')); + }); + images.each(function (index, element) { + var src = $(element).attr('src'); + var filePath = path.resolve(basedir, src); + src = datauri(filePath); + $(element).attr('src', src); + }); + return $.html(); +}; + +// TODO refactor into separate module +// inline html url css data types +var inlineUrl = function (html, filePath) { + var $ = cheerio.load(html); + // style elements + var styles = $('style'); + styles.each(function (index, element) { + var css = $(element).html(); + css = inlineCssUrl(css, filePath); + $(element).html(css); + }); + // style attributes + var attributes = $('body *').filter('[style]'); + attributes.each(function (index, element) { + var css = $(element).attr('style'); + var prefix = 'element {'; + var suffix = '}'; + css = prefix + css + suffix; + css = inlineCssUrl(css, filePath); + css = string(css).collapseWhitespace().toString(); + css = css.replace(new RegExp('^' + prefix + '\\s*(.*)\\s+' + suffix + '$'), '$1'); + $(element).attr('style', css); + }); + return $.html(); +}; + +var inline = co.wrap(function * (filePath, options) { + var html = yield fs.readFile(filePath, 'utf8'); + // inline links: less + html = yield inlineLess(html, filePath, options); + // TODO inline links: css + // TODO inline scripts (js + browserify? = scriptify) + + // Inline local assets (path -> datauri) + html = inlineUrl(html, filePath); + html = inlineImg(html, filePath); + // svg? + + return html; +}); +module.exports = inline; diff --git a/package.json b/package.json new file mode 100644 index 0000000..f92653c --- /dev/null +++ b/package.json @@ -0,0 +1,21 @@ +{ + "name": "inline-html", + "version": "0.0.0", + "description": "", + "main": "lib/index.js", + "scripts": { + "test": "echo \"Error: no test specified\" && exit 1" + }, + "author": "", + "license": "ISC", + "dependencies": { + "cheerio": "^0.19.0", + "co": "^4.6.0", + "datauri": "^0.7.1", + "inline-css-url": "file:../inline-css-url", + "inline-less": "file:../inline-less", + "local-path": "file:../local-path", + "mz": "^2.0.0", + "string": "^3.3.0" + } +} diff --git a/test/assets/imported.css b/test/assets/imported.css new file mode 100644 index 0000000..e9ad805 --- /dev/null +++ b/test/assets/imported.css @@ -0,0 +1,8 @@ +body { + border: solid 4px green; +} +#import { + background-image: url('./person.png'); + background-size: contain; + background-repeat: no-repeat; +} \ No newline at end of file diff --git a/test/assets/person.png b/test/assets/person.png new file mode 100644 index 0000000..ad607a9 Binary files /dev/null and b/test/assets/person.png differ diff --git a/test/index.html b/test/index.html new file mode 100644 index 0000000..225a74b --- /dev/null +++ b/test/index.html @@ -0,0 +1,25 @@ + + + + + + + + + +
Import
+
Style
+
Attribute
+ Image + + \ No newline at end of file diff --git a/test/index.js b/test/index.js new file mode 100644 index 0000000..e73e404 --- /dev/null +++ b/test/index.js @@ -0,0 +1,15 @@ +var inline = require('../lib'); +var path = require('path'); +var fs = require('fs'); + +var filepath = path.resolve(__dirname, './index.html'); +var options = {}; +/** + * html -> async -> inlined html + */ +inline(filepath, options) + .then(function (html) { + console.log(html); + fs.writeFileSync('./test.html', html); + }) + .catch(console.error); diff --git a/test/main.less b/test/main.less new file mode 100644 index 0000000..aead599 --- /dev/null +++ b/test/main.less @@ -0,0 +1,7 @@ +@import (less) './assets/imported.css'; + +#link { + background-image: url('assets/person.png'); + background-size: contain; + background-repeat: no-repeat; +} \ No newline at end of file