diff --git a/source/components/notify/monitor-attribute-errors.mjs b/source/components/notify/monitor-attribute-errors.mjs new file mode 100644 index 0000000000000000000000000000000000000000..90e1238289ead6aba6eaac086534e84176dc665c --- /dev/null +++ b/source/components/notify/monitor-attribute-errors.mjs @@ -0,0 +1,217 @@ +/** + * Copyright © schukai GmbH and all contributing authors, {{copyRightYear}}. All rights reserved. + * Node module: @schukai/monster + * + * This source code is licensed under the GNU Affero General Public License version 3 (AGPLv3). + * The full text of the license can be found at: https://www.gnu.org/licenses/agpl-3.0.en.html + * + * For those who do not wish to adhere to the AGPLv3, a commercial license is available. + * Acquiring a commercial license allows you to use this software without complying with the AGPLv3 terms. + * For more information about purchasing a commercial license, please contact schukai GmbH. + */ + +import {instanceSymbol} from "../../constants.mjs"; +import {addAttributeToken, hasObjectLink} from "../../dom/attributes.mjs"; +import { + ATTRIBUTE_ERRORMESSAGE, + ATTRIBUTE_ROLE, customElementUpdaterLinkSymbol, +} from "../../dom/constants.mjs"; +import {CustomControl} from "../../dom/customcontrol.mjs"; +import {CustomElement} from "../../dom/customelement.mjs"; +import { + assembleMethodSymbol, + registerCustomElement, +} from "../../dom/customelement.mjs"; +import {findTargetElementFromEvent} from "../../dom/events.mjs"; +import {isFunction} from "../../types/is.mjs"; +import {MonitorAttributeErrorsStyleSheet} from "./stylesheet/monitor-attribute-errors.mjs"; +import {fireCustomEvent} from "../../dom/events.mjs"; +import {getDocument} from "../../dom/util.mjs"; +import {clone} from "../../util/clone.mjs"; + +export {MonitorAttributeErrors}; + +/** + * @private + * @type {symbol} + */ +const mutationObserversSymbol = Symbol("mutationObservers"); + + +/** + * A MonitorAttributeErrors + * + * @fragments /fragments/components/notify/monitor-attribute-errors/ + * + * @example /examples/components/notify/monitor-attribute-errors-simple + * + * @since 3.98.0 + * @copyright schukai GmbH + * @summary A beautiful MonitorAttributeErrors that can make your life easier and also looks good. + */ +class MonitorAttributeErrors extends CustomElement { + /** + * This method is called by the `instanceof` operator. + * @returns {symbol} + */ + static get [instanceSymbol]() { + return Symbol.for("@schukai/monster/components/notify/monitor-attribute-errors@@instance"); + } + + /** + * + * @return {Components.Notify.MonitorAttributeErrors + */ + [assembleMethodSymbol]() { + super[assembleMethodSymbol](); + return this; + } + + /** + * @return {void} + */ + connectedCallback() { + super.connectedCallback() + setupMutationObserver.call(this, getDocument()); + } + + + /** + * @return {void} + */ + disconnectedCallback() { + super.disconnectedCallback(); + deactivateAllObservers.call(this); + } + + /** + * To set the options via the HTML Tag, the attribute `data-monster-options` must be used. + * @see {@link https://monsterjs.org/en/doc/#configurate-a-monster-control} + * + * The individual configuration values can be found in the table. + * + * @property {Object} templates Template definitions + * @property {string} templates.main Main template + * @property {Object} labels Label definitions + * @property {Object} actions Callbacks + * @property {string} actions.click="throw Error" Callback when clicked + * @property {Object} features Features + * @property {Object} classes CSS classes + * @property {boolean} disabled=false Disabled state + */ + get defaults() { + return Object.assign({}, super.defaults, { + templates: { + main: getTemplate(), + }, + labels: {}, + classes: {}, + disabled: false, + features: {}, + actions: { + click: () => { + throw new Error("the click action is not defined"); + }, + } + }); + } + + /** + * @return {string} + */ + static getTag() { + return "monster-monitor-attribute-errors"; + } + + /** + * @return {CSSStyleSheet[]} + */ + static getCSSStyleSheet() { + return [MonitorAttributeErrorsStyleSheet]; + } + + +} + +/** + * @private + * @param root + */ +function setupMutationObserver(root) { + const self = this; + + if (!this?.[mutationObserversSymbol]) { + this[mutationObserversSymbol] = []; + } + + const config = { + childList: true, + subtree: true, + attributes: true, + attributeFilter: ['data-monster-error'] + }; + + const callback = (mutationsList, observer) => { + for (const mutation of mutationsList) { + if (mutation.type === 'childList') { + mutation.addedNodes.forEach(node => { + checkNodeForErrors(node); + observeShadowRoots(node); + }); + } + if (mutation.type === 'attributes' && mutation.attributeName === 'data-monster-error') { + const node = mutation.target; + + console.group(); + console.log(node); + console.log(node.getAttribute('data-monster-error')); + console.groupEnd(); + + getDocument().querySelector('monster-notify').push(node.getAttribute('data-monster-error')); + + } + } + }; + + const observer = new MutationObserver(callback); + observer.observe(root, config); + this[mutationObserversSymbol].push(observer); // Speichert den Observer + + root.querySelectorAll('*').forEach(node => { + checkNodeForErrors(node); + observeShadowRoots(node); + }); + + function checkNodeForErrors(node) { + if (node.nodeType === 1 && node.hasAttribute('data-monster-error')) { + console.log('Fehler gefunden:', node, node.getAttribute('data-monster-error')); + } + } + + function observeShadowRoots(node) { + if (node.nodeType === 1 && node.shadowRoot && node.shadowRoot.mode === 'open') { + console.log('Beobachte Shadow Root:', node); + setupMutationObserver.call(self, node.shadowRoot); + } + } +} + +function deactivateAllObservers() { + this[mutationObserversSymbol].forEach(observer => { + observer.disconnect(); + }); + this[mutationObserversSymbol] = []; + +} + +/** + * @private + * @return {string} + */ +function getTemplate() { + // language=HTML + return ``; +} + + +registerCustomElement(MonitorAttributeErrors); diff --git a/source/components/notify/style/monitor-attribute-errors.pcss b/source/components/notify/style/monitor-attribute-errors.pcss new file mode 100644 index 0000000000000000000000000000000000000000..e69de29bb2d1d6434b8b29ae775ad8c2e48c5391 diff --git a/source/components/notify/stylesheet/monitor-attribute-errors.mjs b/source/components/notify/stylesheet/monitor-attribute-errors.mjs new file mode 100644 index 0000000000000000000000000000000000000000..81ed587fa42e99ca5169b51d49797eb42d55d811 --- /dev/null +++ b/source/components/notify/stylesheet/monitor-attribute-errors.mjs @@ -0,0 +1,31 @@ +/** + * Copyright © schukai GmbH and all contributing authors, 2025. All rights reserved. + * Node module: @schukai/monster + * + * This source code is licensed under the GNU Affero General Public License version 3 (AGPLv3). + * The full text of the license can be found at: https://www.gnu.org/licenses/agpl-3.0.en.html + * + * For those who do not wish to adhere to the AGPLv3, a commercial license is available. + * Acquiring a commercial license allows you to use this software without complying with the AGPLv3 terms. + * For more information about purchasing a commercial license, please contact schukai GmbH. + */ + +import {addAttributeToken} from "../../../dom/attributes.mjs"; +import {ATTRIBUTE_ERRORMESSAGE} from "../../../dom/constants.mjs"; + +export {MonitorAttributeErrorsStyleSheet} + +/** + * @private + * @type {CSSStyleSheet} + */ +const MonitorAttributeErrorsStyleSheet = new CSSStyleSheet(); + +try { + MonitorAttributeErrorsStyleSheet.insertRule(` +@layer monitorattributeerrors { + +}`, 0); +} catch (e) { + addAttributeToken(document.getRootNode().querySelector('html'), ATTRIBUTE_ERRORMESSAGE, e + ""); +}