WordPress/gutenberg

has_block doesn't return true when a block is inside a reusable block

Opened this issue · 6 comments

If a block is inside a reusable block, has_block doesn't return true.

Steps to reproduce the behavior:

  1. Add a block inside a reusable block. (Let's say prfx/myblock)

  2. Add action in plugins php file to wp_enqueue_scripts

    if (has_block('prfx/myblock')) {
    
    wp_register_script('my-script', plugins_url( 'dist/assets/myscript.min.js', dirname( __FILE__ )), array(), null, true );
    
    wp_enqueue_script('my-script');
    
    }
    
  3. At this point the script is not loaded to site, but the block is in the page.

  4. Add the block to the page separate/outside to reusable block

  5. Now the script loads.

Could has_block function also validate with blocks inside reusable blocks?

Desktop:

  • Windows 10
  • Firefox 70.0.1
  • Gutenberg Version 6.8.0

In the meantime, this function will do the job:

function has_reusable_block( $block_name, $id = false ){
    $id = (!$id) ? get_the_ID() : $id;
    if( $id ){
        if ( has_block( 'block', $id ) ){
            // Check reusable blocks
            $content = get_post_field( 'post_content', $id );
            $blocks = parse_blocks( $content );

            if ( ! is_array( $blocks ) || empty( $blocks ) ) {
                return false;
            }

            foreach ( $blocks as $block ) {
                if ( $block['blockName'] === 'core/block' && ! empty( $block['attrs']['ref'] ) ) {
                    if( has_block( $block_name, $block['attrs']['ref'] ) ){
                       return true;
                    }
                }
            }
        }
    }

    return false;
}

Maybe the name of the function should be sth like has_block_in_reusable instead of has_reusable_block, anyway...

Possible duplicate of #17048.

Chiming in to ask if a reusable block check function can be added to core if possible. Many themes use reusable blocks for the sake of speed.

I would also like to know if there is a plan to provide a solution for this problem? As @outdoorsdev rightly pointed out, reusable blocks are widely used and I would expect has_block to take them into account.

Hi folks - I'd love to know if this issue is resolved by the change to synced/unsynced patterns? Are you able to try it out and see if it makes a difference?

I expect it's still a bug, has_block is very basic, and doesn't know to recurse into patterns or template parts (or any other kind of block that loads content from another post).

My own feeling is that I don't think it'd be a good idea to try improving has_block for this purpose either - it'd suddenly become a very expensive function, which existing users of the function might not expect.

Maybe some other API would be a way to solve it, but it's not an easy problem to fix, hence why this issue remains open. 😞