From 22bc2e772480bcad40e5bbc7a5d484d2149ee81c Mon Sep 17 00:00:00 2001 From: Daniel Richards Date: Thu, 13 Jun 2024 08:58:34 +0800 Subject: [PATCH] Block Bindings / Pattern Overrides: Try preventing normal attribute updates when a __default binding exists (#62471) * Try preventing normal attribute updates when a __default binding exists * Add an e2e test * Only skip normal attribute updates for pattern overrides ---- Co-authored-by: talldan Co-authored-by: SantosGuillamot --- .../src/hooks/use-bindings-attributes.js | 12 ++++- .../editor/various/pattern-overrides.spec.js | 53 +++++++++++++++++++ 2 files changed, 64 insertions(+), 1 deletion(-) diff --git a/packages/block-editor/src/hooks/use-bindings-attributes.js b/packages/block-editor/src/hooks/use-bindings-attributes.js index 334c751bc01b0..7bd5df05d31eb 100644 --- a/packages/block-editor/src/hooks/use-bindings-attributes.js +++ b/packages/block-editor/src/hooks/use-bindings-attributes.js @@ -97,6 +97,9 @@ export const withBlockBindingSupport = createHigherOrderComponent( unlock( select( blocksStore ) ).getAllBlockBindingsSources() ); const { name, clientId, context } = props; + const hasPatternOverridesDefaultBinding = + props.attributes.metadata?.bindings?.[ DEFAULT_ATTRIBUTE ] + ?.source === 'core/pattern-overrides'; const bindings = useMemo( () => replacePatternOverrideDefaultBindings( @@ -213,7 +216,13 @@ export const withBlockBindingSupport = createHigherOrderComponent( } } - if ( Object.keys( keptAttributes ).length ) { + // Only apply normal attribute updates to blocks + // that have partial bindings. Currently this is + // only skipped for pattern overrides sources. + if ( + ! hasPatternOverridesDefaultBinding && + Object.keys( keptAttributes ).length + ) { setAttributes( keptAttributes ); } } ); @@ -226,6 +235,7 @@ export const withBlockBindingSupport = createHigherOrderComponent( context, setAttributes, sources, + hasPatternOverridesDefaultBinding, ] ); diff --git a/test/e2e/specs/editor/various/pattern-overrides.spec.js b/test/e2e/specs/editor/various/pattern-overrides.spec.js index f4648a03efe95..3587296a6b2a0 100644 --- a/test/e2e/specs/editor/various/pattern-overrides.spec.js +++ b/test/e2e/specs/editor/various/pattern-overrides.spec.js @@ -742,6 +742,59 @@ test.describe( 'Pattern Overrides', () => { ).toBeHidden(); } ); + test( 'overridden images should not have unsupported attributes set', async ( { + admin, + requestUtils, + editor, + } ) => { + const imageName = 'Editable image'; + const TEST_IMAGE_FILE_PATH = path.resolve( + __dirname, + '../../../assets/10x10_e2e_test_image_z9T8jK.png' + ); + const { id } = await requestUtils.createBlock( { + title: 'Pattern', + content: ` +
+`, + status: 'publish', + } ); + + await admin.createNewPost(); + + await editor.insertBlock( { + name: 'core/block', + attributes: { ref: id }, + } ); + + const imageBlock = editor.canvas.getByRole( 'document', { + name: 'Block: Image', + } ); + await editor.selectBlocks( imageBlock ); + await imageBlock + .getByTestId( 'form-file-upload-input' ) + .setInputFiles( TEST_IMAGE_FILE_PATH ); + await expect( imageBlock.getByRole( 'img' ) ).toHaveCount( 1 ); + await expect( imageBlock.getByRole( 'img' ) ).toHaveAttribute( + 'src', + /\/wp-content\/uploads\// + ); + + // Because the image is an inner block of a controlled pattern block, + // `getBlocks` has to be called using the pattern block's client id. + const patternBlock = editor.canvas.getByRole( 'document', { + name: 'Block: Pattern', + } ); + const patternClientId = await patternBlock.getAttribute( 'data-block' ); + const patternInnerBlocks = await editor.getBlocks( { + clientId: patternClientId, + } ); + + // Link is an unsupported attribute, so should be undefined, even though + // the image block tries to set its attribute. + expect( patternInnerBlocks[ 0 ].attributes.link ).toBe( undefined ); + } ); + test( 'blocks with the same name should be synced', async ( { page, admin,