htmlnano 2.1.1 → 2.1.2
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/CHANGELOG.md +12 -1
- package/docs/docs/050-modules.md +2 -2
- package/docs/package-lock.json +632 -798
- package/index.d.ts +2 -1
- package/lib/htmlnano.cjs +4 -2
- package/lib/htmlnano.mjs +3 -1
- package/lib/modules/minifyConditionalComments.cjs +1 -1
- package/lib/modules/sortAttributes.cjs +1 -2
- package/lib/modules/sortAttributes.mjs +1 -3
- package/lib/modules/sortAttributesWithLists.cjs +1 -2
- package/lib/modules/sortAttributesWithLists.mjs +1 -2
- package/lib/presets/ampSafe.cjs +1 -1
- package/lib/presets/max.cjs +1 -1
- package/package.json +10 -8
- package/test.js +8 -33
package/index.d.ts
CHANGED
|
@@ -5,6 +5,7 @@ import type { Config as SvgoOptimizeOptions } from "svgo";
|
|
|
5
5
|
|
|
6
6
|
export interface HtmlnanoOptions {
|
|
7
7
|
skipConfigLoading?: boolean;
|
|
8
|
+
skipInternalWarnings?: boolean;
|
|
8
9
|
collapseAttributeWhitespace?: boolean;
|
|
9
10
|
collapseBooleanAttributes?: {
|
|
10
11
|
amphtml?: boolean;
|
|
@@ -22,7 +23,7 @@ export interface HtmlnanoOptions {
|
|
|
22
23
|
minifySvg?: SvgoOptimizeOptions | boolean;
|
|
23
24
|
normalizeAttributeValues?: boolean;
|
|
24
25
|
removeAttributeQuotes?: boolean;
|
|
25
|
-
removeComments?: boolean | "safe" | "all" | RegExp | (() => boolean);
|
|
26
|
+
removeComments?: boolean | "safe" | "all" | RegExp | ((comment: string) => boolean);
|
|
26
27
|
removeEmptyAttributes?: boolean;
|
|
27
28
|
removeRedundantAttributes?: boolean;
|
|
28
29
|
removeOptionalTags?: boolean;
|
package/lib/htmlnano.cjs
CHANGED
|
@@ -10,7 +10,7 @@ var _cosmiconfig = require("cosmiconfig");
|
|
|
10
10
|
var _safe = _interopRequireDefault(require("./presets/safe.cjs"));
|
|
11
11
|
var _ampSafe = _interopRequireDefault(require("./presets/ampSafe.cjs"));
|
|
12
12
|
var _max = _interopRequireDefault(require("./presets/max.cjs"));
|
|
13
|
-
function _interopRequireDefault(
|
|
13
|
+
function _interopRequireDefault(e) { return e && e.__esModule ? e : { default: e }; }
|
|
14
14
|
function __transformExtension(filepath, extMapping) {
|
|
15
15
|
if (!filepath.startsWith('./') && !filepath.startsWith('../')) {
|
|
16
16
|
// Package import
|
|
@@ -121,7 +121,9 @@ function htmlnano(optionsRun, presetRun) {
|
|
|
121
121
|
}));
|
|
122
122
|
} catch (e) {
|
|
123
123
|
if (e.code === 'MODULE_NOT_FOUND' || e.code === 'ERR_MODULE_NOT_FOUND') {
|
|
124
|
-
|
|
124
|
+
if (!options.skipInternalWarnings) {
|
|
125
|
+
console.warn(`You have to install "${dependency}" in order to use htmlnano's "${moduleName}" module`);
|
|
126
|
+
}
|
|
125
127
|
} else {
|
|
126
128
|
throw e;
|
|
127
129
|
}
|
package/lib/htmlnano.mjs
CHANGED
|
@@ -98,7 +98,9 @@ function htmlnano(optionsRun, presetRun) {
|
|
|
98
98
|
await import(dependency);
|
|
99
99
|
} catch (e) {
|
|
100
100
|
if (e.code === 'MODULE_NOT_FOUND' || e.code === 'ERR_MODULE_NOT_FOUND') {
|
|
101
|
-
|
|
101
|
+
if (!options.skipInternalWarnings){
|
|
102
|
+
console.warn(`You have to install "${dependency}" in order to use htmlnano's "${moduleName}" module`);
|
|
103
|
+
}
|
|
102
104
|
} else {
|
|
103
105
|
throw e;
|
|
104
106
|
}
|
|
@@ -6,7 +6,7 @@ Object.defineProperty(exports, "__esModule", {
|
|
|
6
6
|
exports.default = minifyConditionalComments;
|
|
7
7
|
var _htmlnano = _interopRequireDefault(require("../htmlnano.cjs"));
|
|
8
8
|
var _helpers = require("../helpers.cjs");
|
|
9
|
-
function _interopRequireDefault(
|
|
9
|
+
function _interopRequireDefault(e) { return e && e.__esModule ? e : { default: e }; }
|
|
10
10
|
// Spec: https://docs.microsoft.com/en-us/previous-versions/windows/internet-explorer/ie-developer/compatibility/ms537512(v=vs.85)
|
|
11
11
|
const CONDITIONAL_COMMENT_REGEXP = /(<!--\[if\s+?[^<>[\]]+?]>)([\s\S]+?)(<!\[endif\]-->)/gm;
|
|
12
12
|
|
|
@@ -4,7 +4,6 @@ Object.defineProperty(exports, "__esModule", {
|
|
|
4
4
|
value: true
|
|
5
5
|
});
|
|
6
6
|
exports.default = sortAttributes;
|
|
7
|
-
var _timsort = require("timsort");
|
|
8
7
|
const validOptions = new Set(['frequency', 'alphabetical']);
|
|
9
8
|
const processModuleOptions = options => {
|
|
10
9
|
if (options === true) return 'alphabetical';
|
|
@@ -26,7 +25,7 @@ class AttributeTokenChain {
|
|
|
26
25
|
}
|
|
27
26
|
createSortOrder() {
|
|
28
27
|
let _sortOrder = [...this.freqData.entries()];
|
|
29
|
-
|
|
28
|
+
_sortOrder.sort((a, b) => b[1] - a[1]);
|
|
30
29
|
this.sortOrder = _sortOrder.map(i => i[0]);
|
|
31
30
|
}
|
|
32
31
|
sortFromNodeAttrs(nodeAttrs) {
|
|
@@ -1,5 +1,3 @@
|
|
|
1
|
-
import { sort as timSort } from 'timsort';
|
|
2
|
-
|
|
3
1
|
const validOptions = new Set(['frequency', 'alphabetical']);
|
|
4
2
|
|
|
5
3
|
const processModuleOptions = options => {
|
|
@@ -27,7 +25,7 @@ class AttributeTokenChain {
|
|
|
27
25
|
|
|
28
26
|
createSortOrder() {
|
|
29
27
|
let _sortOrder = [...this.freqData.entries()];
|
|
30
|
-
|
|
28
|
+
_sortOrder.sort((a, b) => b[1] - a[1]);
|
|
31
29
|
|
|
32
30
|
this.sortOrder = _sortOrder.map(i => i[0]);
|
|
33
31
|
}
|
|
@@ -4,7 +4,6 @@ Object.defineProperty(exports, "__esModule", {
|
|
|
4
4
|
value: true
|
|
5
5
|
});
|
|
6
6
|
exports.default = collapseAttributeWhitespace;
|
|
7
|
-
var _timsort = require("timsort");
|
|
8
7
|
var _collapseAttributeWhitespace = require("./collapseAttributeWhitespace.cjs");
|
|
9
8
|
// class, rel, ping
|
|
10
9
|
|
|
@@ -28,7 +27,7 @@ class AttributeTokenChain {
|
|
|
28
27
|
}
|
|
29
28
|
createSortOrder() {
|
|
30
29
|
let _sortOrder = [...this.freqData.entries()];
|
|
31
|
-
|
|
30
|
+
_sortOrder.sort((a, b) => b[1] - a[1]);
|
|
32
31
|
this.sortOrder = _sortOrder.map(i => i[0]);
|
|
33
32
|
}
|
|
34
33
|
sortFromNodeAttrsArray(attrValuesArray) {
|
|
@@ -1,5 +1,4 @@
|
|
|
1
1
|
// class, rel, ping
|
|
2
|
-
import { sort as timSort } from 'timsort';
|
|
3
2
|
import { attributesWithLists } from './collapseAttributeWhitespace.mjs';
|
|
4
3
|
|
|
5
4
|
const validOptions = new Set(['frequency', 'alphabetical']);
|
|
@@ -26,7 +25,7 @@ class AttributeTokenChain {
|
|
|
26
25
|
|
|
27
26
|
createSortOrder() {
|
|
28
27
|
let _sortOrder = [...this.freqData.entries()];
|
|
29
|
-
|
|
28
|
+
_sortOrder.sort((a, b) => b[1] - a[1]);
|
|
30
29
|
|
|
31
30
|
this.sortOrder = _sortOrder.map(i => i[0]);
|
|
32
31
|
}
|
package/lib/presets/ampSafe.cjs
CHANGED
|
@@ -5,7 +5,7 @@ Object.defineProperty(exports, "__esModule", {
|
|
|
5
5
|
});
|
|
6
6
|
exports.default = void 0;
|
|
7
7
|
var _safe = _interopRequireDefault(require("./safe.cjs"));
|
|
8
|
-
function _interopRequireDefault(
|
|
8
|
+
function _interopRequireDefault(e) { return e && e.__esModule ? e : { default: e }; }
|
|
9
9
|
/**
|
|
10
10
|
* A safe preset for AMP pages (https://www.ampproject.org)
|
|
11
11
|
*/
|
package/lib/presets/max.cjs
CHANGED
|
@@ -5,7 +5,7 @@ Object.defineProperty(exports, "__esModule", {
|
|
|
5
5
|
});
|
|
6
6
|
exports.default = void 0;
|
|
7
7
|
var _safe = _interopRequireDefault(require("./safe.cjs"));
|
|
8
|
-
function _interopRequireDefault(
|
|
8
|
+
function _interopRequireDefault(e) { return e && e.__esModule ? e : { default: e }; }
|
|
9
9
|
/**
|
|
10
10
|
* Maximal minification (might break some pages)
|
|
11
11
|
*/
|
package/package.json
CHANGED
|
@@ -1,19 +1,22 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "htmlnano",
|
|
3
|
-
"version": "2.1.
|
|
3
|
+
"version": "2.1.2",
|
|
4
4
|
"description": "Modular HTML minifier, built on top of the PostHTML",
|
|
5
5
|
"main": "index.cjs",
|
|
6
6
|
"module": "index.mjs",
|
|
7
7
|
"source": "index.mjs",
|
|
8
8
|
"exports": {
|
|
9
9
|
".": {
|
|
10
|
+
"types": "./index.d.ts",
|
|
10
11
|
"require": "./index.cjs",
|
|
11
12
|
"import": "./index.mjs"
|
|
12
13
|
},
|
|
13
14
|
"./index.mjs": {
|
|
15
|
+
"types": "./index.d.mts",
|
|
14
16
|
"import": "./index.mjs"
|
|
15
17
|
},
|
|
16
18
|
"./index.cjs": {
|
|
19
|
+
"types": "./index.d.cts",
|
|
17
20
|
"require": "./index.cjs"
|
|
18
21
|
}
|
|
19
22
|
},
|
|
@@ -60,26 +63,25 @@
|
|
|
60
63
|
},
|
|
61
64
|
"dependencies": {
|
|
62
65
|
"cosmiconfig": "^9.0.0",
|
|
63
|
-
"posthtml": "^0.16.5"
|
|
64
|
-
"timsort": "^0.3.0"
|
|
66
|
+
"posthtml": "^0.16.5"
|
|
65
67
|
},
|
|
66
68
|
"devDependencies": {
|
|
69
|
+
"@aminya/babel-plugin-replace-import-extension": "1.2.0",
|
|
67
70
|
"@babel/cli": "^7.15.7",
|
|
68
71
|
"@babel/core": "^7.15.5",
|
|
69
72
|
"@babel/eslint-parser": "^7.17.0",
|
|
70
73
|
"@babel/preset-env": "^7.15.6",
|
|
71
74
|
"@babel/register": "^7.15.3",
|
|
72
|
-
"@aminya/babel-plugin-replace-import-extension": "1.2.0",
|
|
73
75
|
"cssnano": "^7.0.0",
|
|
74
76
|
"eslint": "^8.12.0",
|
|
75
77
|
"eslint-plugin-import": "^2.28.1",
|
|
76
78
|
"eslint-plugin-path-import-extension": "^0.9.0",
|
|
77
79
|
"expect": "^29.0.0",
|
|
78
|
-
"mocha": "^
|
|
80
|
+
"mocha": "^11.0.1",
|
|
79
81
|
"postcss": "^8.3.11",
|
|
80
|
-
"purgecss": "^
|
|
82
|
+
"purgecss": "^7.0.2",
|
|
81
83
|
"relateurl": "^0.2.7",
|
|
82
|
-
"rimraf": "^
|
|
84
|
+
"rimraf": "^6.0.0",
|
|
83
85
|
"srcset": "5.0.1",
|
|
84
86
|
"svgo": "^3.0.2",
|
|
85
87
|
"terser": "^5.21.0",
|
|
@@ -88,7 +90,7 @@
|
|
|
88
90
|
"peerDependencies": {
|
|
89
91
|
"cssnano": "^7.0.0",
|
|
90
92
|
"postcss": "^8.3.11",
|
|
91
|
-
"purgecss": "^
|
|
93
|
+
"purgecss": "^7.0.2",
|
|
92
94
|
"relateurl": "^0.2.7",
|
|
93
95
|
"srcset": "5.0.1",
|
|
94
96
|
"svgo": "^3.0.2",
|
package/test.js
CHANGED
|
@@ -1,39 +1,13 @@
|
|
|
1
|
+
const fs = require('fs');
|
|
2
|
+
|
|
1
3
|
const htmlnano = require('.');
|
|
2
4
|
// const posthtml = require('posthtml');
|
|
3
|
-
const
|
|
4
|
-
|
|
5
|
-
// minifySvg: false,
|
|
6
|
-
// minifyJs: false,
|
|
7
|
-
// };
|
|
8
|
-
// // posthtml, posthtml-render, and posthtml-parse options
|
|
9
|
-
// const postHtmlOptions = {
|
|
10
|
-
// sync: true, // https://github.com/posthtml/posthtml#usage
|
|
11
|
-
// lowerCaseTags: true, // https://github.com/posthtml/posthtml-parser#options
|
|
12
|
-
// quoteAllAttributes: false, // https://github.com/posthtml/posthtml-render#options
|
|
13
|
-
// };
|
|
5
|
+
const preset = require('./lib/presets/max.cjs');
|
|
6
|
+
|
|
14
7
|
|
|
15
|
-
|
|
16
|
-
// <!doctype html>
|
|
17
|
-
// <html lang="en">
|
|
18
|
-
// <head>
|
|
19
|
-
// <meta charset="utf-8">
|
|
20
|
-
// <title></title>
|
|
21
|
-
// <script class="fob">alert(1)</script>
|
|
22
|
-
// <script>alert(2)</script>
|
|
23
|
-
// </head>
|
|
24
|
-
// <body>
|
|
25
|
-
// <script>alert(3)</script>
|
|
26
|
-
// <script>alert(4)</script>
|
|
27
|
-
// </body>
|
|
28
|
-
// </html>
|
|
29
|
-
// `;
|
|
8
|
+
const html = fs.readFileSync('./test.html', 'utf8');
|
|
30
9
|
|
|
31
|
-
const
|
|
32
|
-
minifySvg: safePreset.minifySvg,
|
|
33
|
-
};
|
|
34
|
-
const html = `
|
|
35
|
-
<input type="text" class="form-control" name="testInput" autofocus="" autocomplete="off" id="testId"><a id="testId" href="#" class="testClass"></a><img width="20" src="../images/image.png" height="40" alt="image" class="cls" id="id2">
|
|
36
|
-
`;
|
|
10
|
+
const startTime = Date.now();
|
|
37
11
|
|
|
38
12
|
htmlnano
|
|
39
13
|
// "preset" arg might be skipped (see "Presets" section below for more info)
|
|
@@ -41,7 +15,8 @@ htmlnano
|
|
|
41
15
|
.process(html)
|
|
42
16
|
.then(function (result) {
|
|
43
17
|
// result.html is minified
|
|
44
|
-
console.log(result.html);
|
|
18
|
+
// console.log(result.html);
|
|
19
|
+
console.log(`Time taken: ${Date.now() - startTime}ms`);
|
|
45
20
|
})
|
|
46
21
|
.catch(function (err) {
|
|
47
22
|
console.error(err);
|