@schukai/monster 4.23.5 → 4.24.0

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 CHANGED
@@ -2,6 +2,29 @@
2
2
 
3
3
 
4
4
 
5
+ ## [4.24.0] - 2025-06-25
6
+
7
+ ### Add Features
8
+
9
+ - Add email viewer component and HTML sanitizer [#325](https://gitlab.schukai.com/oss/libraries/javascript/monster/issues/325)
10
+ ### Changes
11
+
12
+ - update styles
13
+ - update monster
14
+ - update
15
+ - update webtests
16
+ - update npm
17
+
18
+
19
+
20
+ ## [4.23.6] - 2025-06-24
21
+
22
+ ### Bug Fixes
23
+
24
+ - Clean up event handling by removing preventDefault calls
25
+
26
+
27
+
5
28
  ## [4.23.5] - 2025-06-24
6
29
 
7
30
  ### Bug Fixes
package/package.json CHANGED
@@ -1 +1 @@
1
- {"author":"schukai GmbH","dependencies":{"@floating-ui/dom":"^1.7.1","@popperjs/core":"^2.11.8"},"description":"Monster is a simple library for creating fast, robust and lightweight websites.","homepage":"https://monsterjs.org/","keywords":["framework","web","dom","css","sass","mobile-first","app","front-end","templates","schukai","core","shopcloud","alvine","monster","buildmap","stack","observer","observable","uuid","node","nodelist","css-in-js","logger","log","theme"],"license":"AGPL 3.0","main":"source/monster.mjs","module":"source/monster.mjs","name":"@schukai/monster","repository":{"type":"git","url":"https://gitlab.schukai.com/oss/libraries/javascript/monster.git"},"type":"module","version":"4.23.5"}
1
+ {"author":"schukai GmbH","dependencies":{"@floating-ui/dom":"^1.7.1","@popperjs/core":"^2.11.8"},"description":"Monster is a simple library for creating fast, robust and lightweight websites.","homepage":"https://monsterjs.org/","keywords":["framework","web","dom","css","sass","mobile-first","app","front-end","templates","schukai","core","shopcloud","alvine","monster","buildmap","stack","observer","observable","uuid","node","nodelist","css-in-js","logger","log","theme"],"license":"AGPL 3.0","main":"source/monster.mjs","module":"source/monster.mjs","name":"@schukai/monster","repository":{"type":"git","url":"https://gitlab.schukai.com/oss/libraries/javascript/monster.git"},"type":"module","version":"4.24.0"}
@@ -0,0 +1,171 @@
1
+ /**
2
+ * Copyright © schukai GmbH and all contributing authors, {{copyRightYear}}. All rights reserved.
3
+ * Node module: @schukai/monster
4
+ *
5
+ * This source code is licensed under the GNU Affero General Public License version 3 (AGPLv3).
6
+ * The full text of the license can be found at: https://www.gnu.org/licenses/agpl-3.0.en.html
7
+ *
8
+ * For those who do not wish to adhere to the AGPLv3, a commercial license is available.
9
+ * Acquiring a commercial license allows you to use this software without complying with the AGPLv3 terms.
10
+ * For more information about purchasing a commercial license, please contact schukai GmbH.
11
+ *
12
+ * SPDX-License-Identifier: AGPL-3.0
13
+ */
14
+
15
+ import { instanceSymbol } from "../../../constants.mjs";
16
+ import {
17
+ assembleMethodSymbol,
18
+ CustomElement,
19
+ registerCustomElement,
20
+ updaterTransformerMethodsSymbol,
21
+ } from "../../../dom/customelement.mjs";
22
+ import { HtmlStyleSheet } from "./stylesheet/html.mjs";
23
+ import { sanitizeHtml } from "../../../dom/sanitize-html.mjs";
24
+
25
+ export { HtmlContent };
26
+
27
+ /**
28
+ * @private
29
+ * @type {symbol}
30
+ */
31
+ const htmlContentElementSymbol = Symbol("htmlContentElement");
32
+
33
+ /**
34
+ * The HtmlContent component is used to display arbitrary HTML content within its shadow DOM.
35
+ * It provides options for sanitization to prevent XSS attacks.
36
+ *
37
+ * @copyright schukai GmbH
38
+ * @summary An HTML content component that can display sanitized HTML.
39
+ */
40
+ class HtmlContent extends CustomElement {
41
+ /**
42
+ * This method is called by the `instanceof` operator.
43
+ * @return {symbol}
44
+ */
45
+ static get [instanceSymbol]() {
46
+ return Symbol.for(
47
+ "@schukai/monster/components/content/viewer/html-content@@instance",
48
+ );
49
+ }
50
+
51
+ /**
52
+ * To set the options via the HTML tag, the attribute `data-monster-options` must be used.
53
+ * @see {@link https://monsterjs.org/en/doc/#configurate-a-monster-control}
54
+ *
55
+ * The individual configuration values can be found in the table.
56
+ *
57
+ * @property {Object} templates Template definitions
58
+ * @property {string} templates.main Main template
59
+ * @property {string} content The HTML string to be displayed.
60
+ * @property {Object} features Features to enable or disable specific functionalities.
61
+ * @property {boolean} features.sanitize Whether to sanitize the HTML content (removes scripts, etc.). Defaults to true.
62
+ * @property {object} sanitize Sanitization options.
63
+ * @property {function} sanitize.callback A callback function to sanitize the HTML content. Defaults to a built-in sanitizer. You can use libraries like DOMPurify for this purpose.
64
+ */
65
+ get defaults() {
66
+ return Object.assign({}, super.defaults, {
67
+ templates: {
68
+ main: getTemplate(),
69
+ },
70
+ content: "", // Default content is an empty slot
71
+
72
+ features: {
73
+ sanitize: true,
74
+ },
75
+
76
+ sanitize: {
77
+ callback: sanitizeHtml.bind(this),
78
+ },
79
+ });
80
+ }
81
+
82
+ /**
83
+ * Returns the updater transformer methods for this component.
84
+ * @returns {{sanitizeHtml: ((function(*): (*))|*)}}
85
+ */
86
+ [updaterTransformerMethodsSymbol]() {
87
+ return {
88
+ sanitizeHtml: (value) => {
89
+ if (this.getOption("features.sanitize")) {
90
+ return this.getOption("sanitize.callback")(value);
91
+ }
92
+ return value;
93
+ },
94
+ };
95
+ }
96
+
97
+ /**
98
+ * Sets the content of the HtmlContent component.
99
+ * @param content
100
+ * @returns {HtmlContent}
101
+ */
102
+ setContent(content) {
103
+ this.setOption("content", content);
104
+ return this;
105
+ }
106
+
107
+ /**
108
+ * @return {string}
109
+ */
110
+ static getTag() {
111
+ return "monster-html-content";
112
+ }
113
+
114
+ /**
115
+ * @return {HtmlContent}
116
+ */
117
+ [assembleMethodSymbol]() {
118
+ super[assembleMethodSymbol]();
119
+ initControlReferences.call(this);
120
+ grabChildren.call(this);
121
+ }
122
+
123
+ /**
124
+ * @return {Array}
125
+ */
126
+ static getCSSStyleSheet() {
127
+ return [HtmlStyleSheet];
128
+ }
129
+ }
130
+
131
+ function grabChildren() {
132
+ // If there are children, we grab them and set the content
133
+ if (this.children.length > 0) {
134
+ const content = Array.from(this.children)
135
+ .map((child) => child.outerHTML)
136
+ .join("");
137
+ this.setContent(content);
138
+
139
+ this.innerHTML = "";
140
+ }
141
+ }
142
+
143
+ /**
144
+ * @private
145
+ * @return {HtmlContent}
146
+ */
147
+ function initControlReferences() {
148
+ if (!this.shadowRoot) {
149
+ throw new Error("no shadow-root is defined");
150
+ }
151
+
152
+ this[htmlContentElementSymbol] = this.shadowRoot.querySelector(
153
+ "[data-monster-role=content-container]",
154
+ );
155
+ return this;
156
+ }
157
+
158
+ /**
159
+ * @private
160
+ * @return {string}
161
+ */
162
+ function getTemplate() {
163
+ // language=HTML
164
+ return `
165
+ <div data-monster-role="content-container" part="content-container"
166
+ data-monster-replace="path:content | call:sanitizeHtml | default: "
167
+ ></div>
168
+ `;
169
+ }
170
+
171
+ registerCustomElement(HtmlContent);