From 5a5564b4d5cd6fe271ccb02e3f85f4141d7f21b5 Mon Sep 17 00:00:00 2001 From: Glen Davies Date: Fri, 14 Feb 2020 07:53:08 +1300 Subject: [PATCH] Fix sandbox html refresh bug (#20176) * Force rerender of Sandbox component when html prop changes --- packages/components/src/sandbox/index.js | 13 +++- packages/components/src/sandbox/test/index.js | 75 +++++++++++++++++++ 2 files changed, 84 insertions(+), 4 deletions(-) create mode 100644 packages/components/src/sandbox/test/index.js diff --git a/packages/components/src/sandbox/index.js b/packages/components/src/sandbox/index.js index fcd2508c22cf7c..c52bce90880fa5 100644 --- a/packages/components/src/sandbox/index.js +++ b/packages/components/src/sandbox/index.js @@ -28,8 +28,10 @@ class Sandbox extends Component { this.trySandbox(); } - componentDidUpdate() { - this.trySandbox(); + componentDidUpdate( prevProps ) { + const forceRerender = prevProps.html !== this.props.html; + + this.trySandbox( forceRerender ); } isFrameAccessible() { @@ -69,13 +71,16 @@ class Sandbox extends Component { } } - trySandbox() { + trySandbox( forceRerender = false ) { if ( ! this.isFrameAccessible() ) { return; } const body = this.iframe.current.contentDocument.body; - if ( null !== body.getAttribute( 'data-resizable-iframe-connected' ) ) { + if ( + ! forceRerender && + null !== body.getAttribute( 'data-resizable-iframe-connected' ) + ) { return; } diff --git a/packages/components/src/sandbox/test/index.js b/packages/components/src/sandbox/test/index.js new file mode 100644 index 00000000000000..7888082f49459a --- /dev/null +++ b/packages/components/src/sandbox/test/index.js @@ -0,0 +1,75 @@ +/** + * External dependencies + */ +import ReactDOM from 'react-dom'; +import { act } from 'react-dom/test-utils'; + +/** + * WordPress dependencies + */ +import { useState } from '@wordpress/element'; + +/** + * Internal dependencies + */ +import Sandbox from '../'; + +let container; + +const TestWrapper = () => { + const [ html, setHtml ] = useState( + '' + ); + + const updateHtml = () => { + setHtml( + '' + ); + }; + + return ( +
+ + +
+ ); +}; + +beforeEach( () => { + container = document.createElement( 'div' ); + document.body.appendChild( container ); +} ); + +afterEach( () => { + document.body.removeChild( container ); + container = null; +} ); + +it( 'should rerender with new emdeded content if html prop changes', () => { + act( () => { + ReactDOM.render( , container ); + } ); + + const button = container.querySelector( '.mock-button' ); + const iframe = container.querySelector( '.components-sandbox' ); + + let sandboxedIframe = iframe.contentWindow.document.body.querySelector( + '.mock-iframe' + ); + + expect( sandboxedIframe.src ).toEqual( 'https://super.embed/' ); + + act( () => { + button.dispatchEvent( + new window.MouseEvent( 'click', { bubbles: true } ) + ); + } ); + + sandboxedIframe = iframe.contentWindow.document.body.querySelector( + '.mock-iframe' + ); + + expect( sandboxedIframe.src ).toEqual( 'https://another.super.embed/' ); +} );