/** * Copyright (c) Meta Platforms, Inc. and affiliates. * * This source code is licensed under the MIT license found in the * LICENSE file in the root directory of this source tree. * * @flow */ /* globals MSApp */ import {SVG_NAMESPACE} from './DOMNamespaces'; import {enableTrustedTypesIntegration} from 'shared/ReactFeatureFlags'; // SVG temp container for IE lacking innerHTML let reusableSVGContainer: HTMLElement; function setInnerHTMLImpl( node: Element, html: {valueOf(): {toString(): string, ...}, ...}, ): void { if (node.namespaceURI === SVG_NAMESPACE) { if (__DEV__) { if (enableTrustedTypesIntegration) { // TODO: reconsider the text of this warning and when it should show // before enabling the feature flag. if (typeof trustedTypes !== 'undefined') { console.error( "Using 'dangerouslySetInnerHTML' in an svg element with " + 'Trusted Types enabled in an Internet Explorer will cause ' + 'the trusted value to be converted to string. Assigning string ' + "to 'innerHTML' will throw an error if Trusted Types are enforced. " + "You can try to wrap your svg element inside a div and use 'dangerouslySetInnerHTML' " + 'on the enclosing div instead.', ); } } } if (!('innerHTML' in node)) { // IE does not have innerHTML for SVG nodes, so instead we inject the // new markup in a temp node and then move the child nodes across into // the target node reusableSVGContainer = reusableSVGContainer || document.createElement('div'); reusableSVGContainer.innerHTML = '' + html.valueOf().toString() + ''; const svgNode = reusableSVGContainer.firstChild; while (node.firstChild) { node.removeChild(node.firstChild); } // $FlowFixMe[incompatible-use] // $FlowFixMe[incompatible-type] while (svgNode.firstChild) { node.appendChild(svgNode.firstChild); } return; } } node.innerHTML = (html: any); } let setInnerHTML: ( node: Element, html: {valueOf(): {toString(): string, ...}, ...}, ) => void = setInnerHTMLImpl; // $FlowFixMe[cannot-resolve-name] if (typeof MSApp !== 'undefined' && MSApp.execUnsafeLocalFunction) { /** * Create a function which has 'unsafe' privileges (required by windows8 apps) */ setInnerHTML = function ( node: Element, html: {valueOf(): {toString(): string, ...}, ...}, ): void { // $FlowFixMe[cannot-resolve-name] return MSApp.execUnsafeLocalFunction(function () { return setInnerHTMLImpl(node, html); }); }; } export default setInnerHTML;