From aa8fa395a6d1d460f0b1a4813e0ecf5be82da746 Mon Sep 17 00:00:00 2001 From: George Mamadashvili Date: Tue, 27 Dec 2022 11:07:43 +0400 Subject: [PATCH 1/2] Try: Improve caching for getBlockContext --- .../inner-blocks/get-block-context.js | 17 +++++++++-------- 1 file changed, 9 insertions(+), 8 deletions(-) diff --git a/packages/block-editor/src/components/inner-blocks/get-block-context.js b/packages/block-editor/src/components/inner-blocks/get-block-context.js index 295ef380d3808d..23399949452dc0 100644 --- a/packages/block-editor/src/components/inner-blocks/get-block-context.js +++ b/packages/block-editor/src/components/inner-blocks/get-block-context.js @@ -22,18 +22,19 @@ const BLOCK_CONTEXT_CACHE = new WeakMap(); */ export default function getBlockContext( attributes, blockType ) { if ( ! BLOCK_CONTEXT_CACHE.has( blockType ) ) { - BLOCK_CONTEXT_CACHE.set( blockType, new WeakMap() ); + BLOCK_CONTEXT_CACHE.set( blockType, new Map() ); } const blockTypeCache = BLOCK_CONTEXT_CACHE.get( blockType ); - if ( ! blockTypeCache.has( attributes ) ) { - const context = mapValues( - blockType.providesContext, - ( attributeName ) => attributes[ attributeName ] - ); + const context = mapValues( + blockType.providesContext, + ( attributeName ) => attributes[ attributeName ] + ); - blockTypeCache.set( attributes, context ); + const cacheKey = JSON.stringify( context ); + if ( ! blockTypeCache.has( cacheKey ) ) { + blockTypeCache.set( cacheKey, context ); } - return blockTypeCache.get( attributes ); + return blockTypeCache.get( cacheKey ); } From dc289450cebe32b95868c83f90e01e37579fee36 Mon Sep 17 00:00:00 2001 From: George Mamadashvili Date: Tue, 27 Dec 2022 14:55:23 +0400 Subject: [PATCH 2/2] Add unit tests --- .../inner-blocks/test/get-block-context.js | 59 +++++++++++++++++++ 1 file changed, 59 insertions(+) create mode 100644 packages/block-editor/src/components/inner-blocks/test/get-block-context.js diff --git a/packages/block-editor/src/components/inner-blocks/test/get-block-context.js b/packages/block-editor/src/components/inner-blocks/test/get-block-context.js new file mode 100644 index 00000000000000..915e7017a40513 --- /dev/null +++ b/packages/block-editor/src/components/inner-blocks/test/get-block-context.js @@ -0,0 +1,59 @@ +/** + * WordPress dependencies + */ +import { + getBlockType, + getBlockTypes, + registerBlockType, + unregisterBlockType, +} from '@wordpress/blocks'; + +/** + * Internal dependencies + */ +import getBlockContext from '../get-block-context'; + +describe( 'getBlockContext', () => { + beforeAll( () => { + registerBlockType( 'core/fruit-basket', { + category: 'text', + title: 'Fruit Basket', + attributes: { + id: { + type: 'number', + }, + name: { + type: 'string', + }, + }, + providesContext: { basketId: 'id' }, + } ); + } ); + afterAll( () => { + getBlockTypes().forEach( ( block ) => { + unregisterBlockType( block.name ); + } ); + } ); + + it( 'should return cached value when attributes are the same', () => { + const attributes = { id: 1, name: '' }; + const blockType = getBlockType( 'core/fruit-basket' ); + + const prevContext = getBlockContext( attributes, blockType ); + const nextContext = getBlockContext( attributes, blockType ); + + expect( prevContext ).toBe( nextContext ); + } ); + + it( 'should return cached value if attributes used in context are the same', () => { + const blockType = getBlockType( 'core/fruit-basket' ); + + const prevContext = getBlockContext( { id: 1, name: '' }, blockType ); + const nextContext = getBlockContext( + { id: 1, name: 'Apples' }, + blockType + ); + + expect( prevContext ).toBe( nextContext ); + } ); +} );