@berlitz/max-utils
Advanced tools
+11
-0
@@ -6,2 +6,13 @@ # Change Log | ||
| # [4.5.0](https://github.com/berlitz-global/max/compare/@berlitz/max-utils@4.4.0...@berlitz/max-utils@4.5.0) (2023-08-22) | ||
| ### Features | ||
| * added DOMPurify for sanitize html ([1d8a013](https://github.com/berlitz-global/max/commit/1d8a013426e816b7c8f7c7bb277aea2dceaf1a53)) | ||
| # [4.4.0](https://github.com/berlitz-global/max/compare/@berlitz/max-utils@4.3.0...@berlitz/max-utils@4.4.0) (2022-04-05) | ||
@@ -8,0 +19,0 @@ |
+128
-75
@@ -8,3 +8,3 @@ "use strict"; | ||
| var _sanitizeHtml = _interopRequireDefault(require("sanitize-html")); | ||
| var _isomorphicDompurify = _interopRequireDefault(require("isomorphic-dompurify")); | ||
@@ -14,76 +14,127 @@ function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; } | ||
| var sanitizeHtml = function sanitizeHtml(html) { | ||
| return (0, _sanitizeHtml.default)(html, { | ||
| allowedTags: ['a', 'br', 'blockquote', 'del', 'div', 'em', 'h1', 'h2', 'h3', 'h4', 'h5', 'hr', 'iframe', 'img', 'li', 'ol', 'p', 'span', 'strong', 'table', 'td', 'th', 'tr', 'u', 'ul', 'audio', 'source', 'button'], | ||
| allowedAttributes: { | ||
| '*': ['style', 'data-key'], | ||
| a: ['href', 'target', 'rel', 'name', { | ||
| name: 'class', | ||
| multiple: true, | ||
| values: ['btn'] | ||
| }], | ||
| img: ['src', 'alt'], | ||
| iframe: ['width', 'height', 'src', 'frameborder', 'allow', 'allowfullscreen'], | ||
| p: [{ | ||
| name: 'class', | ||
| multiple: true, | ||
| values: ['fine', 'color-brand-primary', 'nmb'] | ||
| }], | ||
| span: [{ | ||
| name: 'class', | ||
| values: ['ww', 'color-brand-primary', 'fine'] | ||
| }], | ||
| div: [{ | ||
| name: 'class', | ||
| multiple: true, | ||
| values: ['video-16x9'] | ||
| }], | ||
| h1: ['id', { | ||
| name: 'class', | ||
| multiple: true, | ||
| values: ['color-brand-primary'] | ||
| }], | ||
| h2: ['id', { | ||
| name: 'class', | ||
| multiple: true, | ||
| values: ['color-brand-primary'] | ||
| }], | ||
| h3: ['id', { | ||
| name: 'class', | ||
| multiple: true, | ||
| values: ['color-brand-primary'] | ||
| }], | ||
| h4: ['id', { | ||
| name: 'class', | ||
| multiple: true, | ||
| values: ['color-brand-primary'] | ||
| }], | ||
| h5: ['id', { | ||
| name: 'class', | ||
| multiple: true, | ||
| values: ['color-brand-primary'] | ||
| }], | ||
| audio: ['controls', 'controlslist'], | ||
| source: ['src', 'type'], | ||
| button: ['id', { | ||
| name: 'class', | ||
| values: ['ot-sdk-show-settings'] | ||
| }], | ||
| tr: ['id', { | ||
| name: 'class', | ||
| multiple: false, | ||
| values: ['color-success', 'color-warning', 'color-danger', 'color-brand', 'color-white', 'color-gray'] | ||
| }], | ||
| td: ['id', { | ||
| name: 'class', | ||
| multiple: false, | ||
| values: ['color-success', 'color-warning', 'color-danger', 'color-brand', 'color-white', 'color-gray'] | ||
| }] | ||
| }, | ||
| allowedStyles: { | ||
| '*': { | ||
| 'text-align': [/^left$/, /^center$/, /^right$/] | ||
| var allowedSchemes = ['http', 'https', 'ftp', 'mailto', 'tel']; | ||
| var pTagClassList = ['fine', 'color-brand-primary', 'nmb']; | ||
| var spanTagClassList = ['ww', 'color-brand-primary', 'fine']; | ||
| var tableTagClassList = ['color-success', 'color-warning', 'color-danger', 'color-brand', 'color-white', 'color-gray']; | ||
| var schemesRegex = RegExp('^(' + allowedSchemes.join('|') + '):', 'gim'); | ||
| _isomorphicDompurify.default.addHook('afterSanitizeAttributes', function (node) { | ||
| // build an anchor to map URLs to | ||
| var anchor = document.createElement('a'); // check all href attributes for validity | ||
| if (node.hasAttribute('href')) { | ||
| anchor.href = node.getAttribute('href'); | ||
| if (anchor.protocol && !anchor.protocol.match(schemesRegex)) { | ||
| node.removeAttribute('href'); | ||
| } | ||
| }, | ||
| allowedSchemes: ['http', 'https', 'ftp', 'mailto', 'tel'] | ||
| } // check all action attributes for validity | ||
| if (node.hasAttribute('action')) { | ||
| anchor.href = node.getAttribute('action'); | ||
| if (anchor.protocol && !anchor.protocol.match(schemesRegex)) { | ||
| node.removeAttribute('action'); | ||
| } | ||
| } // check all xlink:href attributes for validity | ||
| if (node.hasAttribute('xlink:href')) { | ||
| anchor.href = node.getAttribute('xlink:href'); | ||
| if (anchor.protocol && !anchor.protocol.match(schemesRegex)) { | ||
| node.removeAttribute('xlink:href'); | ||
| } | ||
| } // check all class attributes for validity | ||
| if (node.hasAttribute('class')) { | ||
| if (node.nodeName === 'A') { | ||
| filterClass(node, ['btn'], false); | ||
| } | ||
| if (node.nodeName === 'P') { | ||
| filterClass(node, pTagClassList, true); | ||
| } | ||
| if (node.nodeName === 'SPAN') { | ||
| filterClass(node, spanTagClassList, true); | ||
| } | ||
| if (node.nodeName === 'H1' || node.nodeName === 'H2' || node.nodeName === 'H3' || node.nodeName === 'H4' || node.nodeName === 'H5') { | ||
| filterClass(node, ['color-brand-primary'], false); | ||
| } | ||
| if (node.nodeName === 'BUTTON') { | ||
| filterClass(node, ['ot-sdk-show-settings', 'btn'], true); | ||
| } | ||
| if (node.nodeName === 'TR' || node.nodeName === 'TD') { | ||
| filterClass(node, tableTagClassList, false); | ||
| } | ||
| } // check all style attributes for validity | ||
| if (node.hasAttribute('style')) { | ||
| var textStyleFilter = ['left', 'center', 'right']; | ||
| var styleAttr = node.getAttribute('style').split('; '); | ||
| var objectStyle = {}; | ||
| styleAttr.forEach(function (property) { | ||
| var style = property.split(':'); | ||
| objectStyle[style[0]] = style[1].replace(' ', '').replace(';', ''); | ||
| }); | ||
| var filteredStyle = Object.keys(objectStyle).filter(function (key) { | ||
| return key === 'text-align'; | ||
| }).reduce(function (cur, key) { | ||
| var style = textStyleFilter.filter(function (textStyle) { | ||
| return textStyle === objectStyle[key]; | ||
| }); | ||
| if (style.length > 0) return Object.assign(cur, { | ||
| textAlign: style[0] | ||
| }); | ||
| }, {}); | ||
| if (filteredStyle) { | ||
| node.setAttribute('style', "text-align: ".concat(filteredStyle.textAlign)); | ||
| } else { | ||
| node.removeAttribute('style'); | ||
| } | ||
| } // set all img elements to have lazy loading | ||
| if (node.nodeName === 'IMG') { | ||
| node.setAttribute('loading', 'lazy'); | ||
| } | ||
| }); | ||
| var filterClass = function filterClass(node, filterList, multiple) { | ||
| var className = node.className; | ||
| var classList = className.split(/\s+/); | ||
| var filteredClass = []; | ||
| classList.map(function (tagClass) { | ||
| filterList.map(function (filter) { | ||
| if (filter === tagClass) { | ||
| filteredClass.push(tagClass); | ||
| } | ||
| }); | ||
| }); | ||
| if (multiple) { | ||
| return node.setAttribute('class', filteredClass.join(' ')); | ||
| } else if (filteredClass.length > 0) { | ||
| return node.setAttribute('class', filteredClass[0]); | ||
| } else { | ||
| return node.removeAttribute('class'); | ||
| } | ||
| }; | ||
| var configOptions = { | ||
| ALLOWED_TAGS: ['a', 'br', 'blockquote', 'del', 'div', 'em', 'h1', 'h2', 'h3', 'h4', 'h5', 'hr', 'iframe', 'img', 'li', 'ol', 'p', 'span', 'strong', 'table', 'td', 'th', 'tr', 'u', 'ul', 'audio', 'source', 'button'], | ||
| ALLOWED_ATTR: ['style', 'data-key', 'href', 'target', 'rel', 'name', 'src', 'alt', 'id', 'width', 'height', 'frameborder', 'allow', 'allowfullscreen', 'class', 'controls', 'controlslist', 'type', 'loading'] | ||
| }; | ||
| var purified = _isomorphicDompurify.default.sanitize(html, configOptions).replace(/<(hr|br|img)>/g, '<$1 />'); | ||
| return purified; | ||
| }; | ||
@@ -94,5 +145,7 @@ | ||
| var removeAllTags = function removeAllTags(html) { | ||
| return sanitizeHtml(html, { | ||
| allowedTags: [] | ||
| var removedAllTags = _isomorphicDompurify.default.sanitize(html, { | ||
| ALLOWED_TAGS: [] | ||
| }); | ||
| return removedAllTags; | ||
| }; | ||
@@ -99,0 +152,0 @@ |
+3
-2
| { | ||
| "name": "@berlitz/max-utils", | ||
| "description": "Utilities for the Max Design System", | ||
| "version": "4.4.0", | ||
| "version": "4.5.0", | ||
| "main": "lib/index.js", | ||
@@ -30,6 +30,7 @@ "homepage": "https://github.com/berlitz-global/max/blob/master/packages/max-utils/CHANGELOG.md", | ||
| "dependencies": { | ||
| "isomorphic-dompurify": "^0.20.0", | ||
| "sanitize-html": "1.20.1", | ||
| "slugify": "^1.5.0" | ||
| }, | ||
| "gitHead": "a9e349122a44c9da091d8e3f8bb676473799eb03" | ||
| "gitHead": "1ab9fcf5f2d6e7c5cc860f0527058d549bfa8395" | ||
| } |
33778
8.63%474
5.8%5
25%+ Added
+ Added
+ Added
+ Added
+ Added
+ Added
+ Added
+ Added
+ Added
+ Added
+ Added
+ Added
+ Added
+ Added
+ Added
+ Added
+ Added
+ Added
+ Added
+ Added
+ Added
+ Added
+ Added
+ Added
+ Added
+ Added
+ Added
+ Added
+ Added
+ Added
+ Added
+ Added
+ Added
+ Added
+ Added
+ Added
+ Added
+ Added
+ Added
+ Added
+ Added
+ Added
+ Added
+ Added
+ Added
+ Added
+ Added
+ Added
+ Added
+ Added
+ Added
+ Added
+ Added
+ Added
+ Added
+ Added
+ Added
+ Added
+ Added
+ Added
+ Added
+ Added
+ Added
+ Added
+ Added
+ Added
+ Added
+ Added
+ Added
+ Added
+ Added