diff --git a/src/wp-includes/blocks.php b/src/wp-includes/blocks.php index 98d8f10d5c..ed0c4d2dbf 100644 --- a/src/wp-includes/blocks.php +++ b/src/wp-includes/blocks.php @@ -113,6 +113,44 @@ function get_dynamic_block_names() { return $dynamic_block_names; } +/** + * Remove all dynamic blocks from the given content. + * + * @since 5.0.0 + * + * @param string $content Content of the current post. + * @return string + */ +function strip_dynamic_blocks( $content ) { + return _recurse_strip_dynamic_blocks( parse_blocks( $content ) ); +} + +/** + * Helper function for strip_dynamic_blocks(), to recurse through the block tree. + * + * @since 5.0.0 + * @access private + * + * @param array $blocks Array of blocks from parse_blocks(). + * @return string HTML from the non-dynamic blocks. + */ +function _recurse_strip_dynamic_blocks( $blocks ) { + $clean_content = ''; + $dynamic_blocks = get_dynamic_block_names(); + + foreach ( $blocks as $block ) { + if ( ! in_array( $block['blockName'], $dynamic_blocks ) ) { + if ( $block['innerBlocks'] ) { + $clean_content .= _recurse_strip_dynamic_blocks( $block['innerBlocks'] ); + } else { + $clean_content .= $block['innerHTML']; + } + } + } + + return $clean_content; +} + /** * Parses blocks out of a content string. * @@ -142,10 +180,85 @@ function parse_blocks( $content ) { * * @since 5.0.0 * - * @param string $parser_class Name of block parser class + * @param string $parser_class Name of block parser class. */ $parser_class = apply_filters( 'block_parser_class', 'WP_Block_Parser' ); $parser = new $parser_class(); return $parser->parse( $content ); } + +/** + * Parses dynamic blocks out of `post_content` and re-renders them. + * + * @since 5.0.0 + * @global WP_Post $post The post to edit. + * + * @param string $content Post content. + * @return string Updated post content. + */ +function do_blocks( $content ) { + $blocks = parse_blocks( $content ); + return _recurse_do_blocks( $blocks, $blocks ); +} + +/** + * Helper function for do_blocks(), to recurse through the block tree. + * + * @since 5.0.0 + * @access private + * + * @param array $blocks Array of blocks from parse_blocks(). + * @param array $all_blocks The top level array of blocks. + * @return string The block HTML. + */ +function _recurse_do_blocks( $blocks, $all_blocks ) { + global $post; + + /* + * Back up global post, to restore after render callback. + * Allows callbacks to run new WP_Query instances without breaking the global post. + */ + $global_post = $post; + + $rendered_content = ''; + $dynamic_blocks = get_dynamic_block_names(); + + foreach ( $blocks as $block ) { + $block = (array) $block; + if ( in_array( $block['blockName'], $dynamic_blocks ) ) { + // Find registered block type. We can assume it exists since we use the + // `get_dynamic_block_names` function as a source for pattern matching. + $block_type = WP_Block_Type_Registry::get_instance()->get_registered( $block['blockName'] ); + + // Replace dynamic block with server-rendered output. + $block_content = $block_type->render( (array) $block['attrs'], $block['innerHTML'] ); + } elseif ( $block['innerBlocks'] ) { + $block_content = _recurse_do_blocks( $block['innerBlocks'], $blocks ); + } else { + $block_content = $block['innerHTML']; + } + + /** + * Filters the content of a single block. + * + * During the_content, each block is parsed and added to the output individually. This filter allows + * that content to be altered immediately before it's appended. + * + * @since 5.0.0 + * + * @param string $block_content The block content about to be appended. + * @param array $block The full block, including name and attributes. + * @param array $all_blocks The array of all blocks being processed. + */ + $rendered_content .= apply_filters( 'do_block', $block_content, $block, $all_blocks ); + + // Restore global $post. + $post = $global_post; + } + + // Strip remaining block comment demarcations. + $rendered_content = preg_replace( '//m', '', $rendered_content ); + + return $rendered_content; +} diff --git a/src/wp-includes/blocks/archives.php b/src/wp-includes/blocks/archives.php new file mode 100644 index 0000000000..adcc61c233 --- /dev/null +++ b/src/wp-includes/blocks/archives.php @@ -0,0 +1,143 @@ + 'monthly', + 'format' => 'option', + 'show_post_count' => $show_post_count, + ) + ); + + $dropdown_args['echo'] = 0; + + $archives = wp_get_archives( $dropdown_args ); + + switch ( $dropdown_args['type'] ) { + case 'yearly': + $label = __( 'Select Year', 'gutenberg' ); + break; + case 'monthly': + $label = __( 'Select Month', 'gutenberg' ); + break; + case 'daily': + $label = __( 'Select Day', 'gutenberg' ); + break; + case 'weekly': + $label = __( 'Select Week', 'gutenberg' ); + break; + default: + $label = __( 'Select Post', 'gutenberg' ); + break; + } + + $label = esc_attr( $label ); + + $block_content = ' + '; + + $block_content = sprintf( + '
%2$s
', + esc_attr( $class ), + $block_content + ); + } else { + + /** This filter is documented in wp-includes/widgets/class-wp-widget-archives.php */ + $archives_args = apply_filters( + 'widget_archives_args', + array( + 'type' => 'monthly', + 'show_post_count' => $show_post_count, + ) + ); + + $archives_args['echo'] = 0; + + $archives = wp_get_archives( $archives_args ); + + $classnames = esc_attr( $class ); + + if ( empty( $archives ) ) { + + $block_content = sprintf( + '
%2$s
', + $classnames, + __( 'No archives to show.', 'gutenberg' ) + ); + } else { + + $block_content = sprintf( + '', + $classnames, + $archives + ); + } + } + + return $block_content; +} + +/** + * Register archives block. + */ +function register_block_core_archives() { + register_block_type( + 'core/archives', + array( + 'attributes' => array( + 'align' => array( + 'type' => 'string', + ), + 'className' => array( + 'type' => 'string', + ), + 'displayAsDropdown' => array( + 'type' => 'boolean', + 'default' => false, + ), + 'showPostCounts' => array( + 'type' => 'boolean', + 'default' => false, + ), + ), + 'render_callback' => 'render_block_core_archives', + ) + ); +} + +add_action( 'init', 'register_block_core_archives' ); diff --git a/src/wp-includes/blocks/block.php b/src/wp-includes/blocks/block.php new file mode 100644 index 0000000000..bc33929ac5 --- /dev/null +++ b/src/wp-includes/blocks/block.php @@ -0,0 +1,39 @@ +post_type ) { + return ''; + } + + return do_blocks( $reusable_block->post_content ); +} + +register_block_type( + 'core/block', + array( + 'attributes' => array( + 'ref' => array( + 'type' => 'number', + ), + ), + + 'render_callback' => 'render_block_core_block', + ) +); diff --git a/src/wp-includes/blocks/categories.php b/src/wp-includes/blocks/categories.php new file mode 100644 index 0000000000..bd1175733b --- /dev/null +++ b/src/wp-includes/blocks/categories.php @@ -0,0 +1,103 @@ + false, + 'hierarchical' => ! empty( $attributes['showHierarchy'] ), + 'orderby' => 'name', + 'show_count' => ! empty( $attributes['showPostCounts'] ), + 'title_li' => '', + ); + + if ( ! empty( $attributes['displayAsDropdown'] ) ) { + $id = 'wp-block-categories-' . $block_id; + $args['id'] = $id; + $args['show_option_none'] = __( 'Select Category', 'gutenberg' ); + $wrapper_markup = '
%2$s
'; + $items_markup = wp_dropdown_categories( $args ); + $type = 'dropdown'; + + if ( ! is_admin() ) { + $wrapper_markup .= build_dropdown_script_block_core_categories( $id ); + } + } else { + $wrapper_markup = ''; + $items_markup = wp_list_categories( $args ); + $type = 'list'; + } + + $class = "wp-block-categories wp-block-categories-{$type} align{$align}"; + + if ( isset( $attributes['className'] ) ) { + $class .= ' ' . $attributes['className']; + } + + $block_content = sprintf( + $wrapper_markup, + esc_attr( $class ), + $items_markup + ); + + return $block_content; +} + +/** + * Generates the inline script for a categories dropdown field. + * + * @param string $dropdown_id ID of the dropdown field. + * + * @return string Returns the dropdown onChange redirection script. + */ +function build_dropdown_script_block_core_categories( $dropdown_id ) { + ob_start(); + ?> + + 'render_block_core_categories', + ) + ); +} + +add_action( 'init', 'register_block_core_categories' ); diff --git a/src/wp-includes/blocks/latest-comments.php b/src/wp-includes/blocks/latest-comments.php new file mode 100644 index 0000000000..dd310028ce --- /dev/null +++ b/src/wp-includes/blocks/latest-comments.php @@ -0,0 +1,182 @@ + $attributes['commentsToShow'], + 'status' => 'approve', + 'post_status' => 'publish', + ) + ) + ); + + $list_items_markup = ''; + if ( ! empty( $comments ) ) { + // Prime the cache for associated posts. This is copied from \WP_Widget_Recent_Comments::widget(). + $post_ids = array_unique( wp_list_pluck( $comments, 'comment_post_ID' ) ); + _prime_post_caches( $post_ids, strpos( get_option( 'permalink_structure' ), '%category%' ), false ); + + foreach ( $comments as $comment ) { + $list_items_markup .= '
  • '; + if ( $attributes['displayAvatar'] ) { + $avatar = get_avatar( + $comment, + 48, + '', + '', + array( + 'class' => 'wp-block-latest-comments__comment-avatar', + ) + ); + if ( $avatar ) { + $list_items_markup .= $avatar; + } + } + + $list_items_markup .= '
    '; + $list_items_markup .= ''; + if ( $attributes['displayExcerpt'] ) { + $list_items_markup .= '
    ' . wpautop( get_comment_excerpt( $comment ) ) . '
    '; + } + $list_items_markup .= '
  • '; + } + } + + $class = 'wp-block-latest-comments'; + if ( $attributes['align'] ) { + $class .= " align{$attributes['align']}"; + } + if ( $attributes['displayAvatar'] ) { + $class .= ' has-avatars'; + } + if ( $attributes['displayDate'] ) { + $class .= ' has-dates'; + } + if ( $attributes['displayExcerpt'] ) { + $class .= ' has-excerpts'; + } + if ( empty( $comments ) ) { + $class .= ' no-comments'; + } + $classnames = esc_attr( $class ); + + $block_content = ! empty( $comments ) ? sprintf( + '
      %2$s
    ', + $classnames, + $list_items_markup + ) : sprintf( + '
    %2$s
    ', + $classnames, + __( 'No comments to show.', 'gutenberg' ) + ); + + return $block_content; +} + +register_block_type( + 'core/latest-comments', + array( + 'attributes' => array( + 'className' => array( + 'type' => 'string', + ), + 'commentsToShow' => array( + 'type' => 'number', + 'default' => 5, + 'minimum' => 1, + 'maximum' => 100, + ), + 'displayAvatar' => array( + 'type' => 'boolean', + 'default' => true, + ), + 'displayDate' => array( + 'type' => 'boolean', + 'default' => true, + ), + 'displayExcerpt' => array( + 'type' => 'boolean', + 'default' => true, + ), + 'align' => array( + 'type' => 'string', + 'enum' => array( 'center', 'left', 'right', 'wide', 'full', '' ), + ), + ), + 'render_callback' => 'gutenberg_render_block_core_latest_comments', + ) +); diff --git a/src/wp-includes/blocks/latest-posts.php b/src/wp-includes/blocks/latest-posts.php new file mode 100644 index 0000000000..070abafeb4 --- /dev/null +++ b/src/wp-includes/blocks/latest-posts.php @@ -0,0 +1,125 @@ + $attributes['postsToShow'], + 'post_status' => 'publish', + 'order' => $attributes['order'], + 'orderby' => $attributes['orderBy'], + 'category' => $attributes['categories'], + ) + ); + + $list_items_markup = ''; + + foreach ( $recent_posts as $post ) { + $post_id = $post['ID']; + + $title = get_the_title( $post_id ); + if ( ! $title ) { + $title = __( '(Untitled)', 'gutenberg' ); + } + $list_items_markup .= sprintf( + '
  • %2$s', + esc_url( get_permalink( $post_id ) ), + esc_html( $title ) + ); + + if ( isset( $attributes['displayPostDate'] ) && $attributes['displayPostDate'] ) { + $list_items_markup .= sprintf( + '', + esc_attr( get_the_date( 'c', $post_id ) ), + esc_html( get_the_date( '', $post_id ) ) + ); + } + + $list_items_markup .= "
  • \n"; + } + + $class = 'wp-block-latest-posts'; + if ( isset( $attributes['align'] ) ) { + $class .= ' align' . $attributes['align']; + } + + if ( isset( $attributes['postLayout'] ) && 'grid' === $attributes['postLayout'] ) { + $class .= ' is-grid'; + } + + if ( isset( $attributes['columns'] ) && 'grid' === $attributes['postLayout'] ) { + $class .= ' columns-' . $attributes['columns']; + } + + if ( isset( $attributes['className'] ) ) { + $class .= ' ' . $attributes['className']; + } + + $block_content = sprintf( + '', + esc_attr( $class ), + $list_items_markup + ); + + return $block_content; +} + +/** + * Registers the `core/latest-posts` block on server. + */ +function register_block_core_latest_posts() { + register_block_type( + 'core/latest-posts', + array( + 'attributes' => array( + 'categories' => array( + 'type' => 'string', + ), + 'className' => array( + 'type' => 'string', + ), + 'postsToShow' => array( + 'type' => 'number', + 'default' => 5, + ), + 'displayPostDate' => array( + 'type' => 'boolean', + 'default' => false, + ), + 'postLayout' => array( + 'type' => 'string', + 'default' => 'list', + ), + 'columns' => array( + 'type' => 'number', + 'default' => 3, + ), + 'align' => array( + 'type' => 'string', + ), + 'order' => array( + 'type' => 'string', + 'default' => 'desc', + ), + 'orderBy' => array( + 'type' => 'string', + 'default' => 'date', + ), + ), + 'render_callback' => 'render_block_core_latest_posts', + ) + ); +} + +add_action( 'init', 'register_block_core_latest_posts' ); diff --git a/src/wp-includes/blocks/shortcode.php b/src/wp-includes/blocks/shortcode.php new file mode 100644 index 0000000000..d18dd4f582 --- /dev/null +++ b/src/wp-includes/blocks/shortcode.php @@ -0,0 +1,32 @@ + 'render_block_core_shortcode', + ) + ); +} + +add_action( 'init', 'register_block_core_shortcode' ); diff --git a/src/wp-includes/class-wp-block-parser.php b/src/wp-includes/class-wp-block-parser.php index 64823d768e..15c9d9556b 100644 --- a/src/wp-includes/class-wp-block-parser.php +++ b/src/wp-includes/class-wp-block-parser.php @@ -310,9 +310,16 @@ class WP_Block_Parser { * otherwise we're nested and we have to close out the current * block and add it as a new innerBlock to the parent */ - $stack_top = array_pop( $this->stack ); - $stack_top->block->innerHTML .= substr( $this->document, $stack_top->prev_offset, $start_offset - $stack_top->prev_offset ); - $stack_top->prev_offset = $start_offset + $token_length; + $stack_top = array_pop( $this->stack ); + + $html = substr( $this->document, $stack_top->prev_offset, $start_offset - $stack_top->prev_offset ); + if ( $stack_top->block->innerBlocks ) { + $stack_top->block->innerBlocks[] = (array) $this->freeform( $html ); + } else { + $stack_top->block->innerHTML = $html; + } + + $stack_top->prev_offset = $start_offset + $token_length; $this->add_inner_block( $stack_top->block, @@ -445,8 +452,8 @@ class WP_Block_Parser { */ function add_inner_block( WP_Block_Parser_Block $block, $token_start, $token_length, $last_offset = null ) { $parent = $this->stack[ count( $this->stack ) - 1 ]; - $parent->block->innerBlocks[] = $block; - $parent->block->innerHTML .= substr( $this->document, $parent->prev_offset, $token_start - $parent->prev_offset ); + $parent->block->innerBlocks[] = (array) $this->freeform( substr( $this->document, $parent->prev_offset, $token_start - $parent->prev_offset ) ); + $parent->block->innerBlocks[] = (array) $block; $parent->prev_offset = $last_offset ? $last_offset : $token_start + $token_length; } @@ -461,10 +468,16 @@ class WP_Block_Parser { $stack_top = array_pop( $this->stack ); $prev_offset = $stack_top->prev_offset; - $stack_top->block->innerHTML .= isset( $end_offset ) + $html = isset( $end_offset ) ? substr( $this->document, $prev_offset, $end_offset - $prev_offset ) : substr( $this->document, $prev_offset ); + if ( $stack_top->block->innerBlocks ) { + $stack_top->block->innerBlocks[] = (array) $this->freeform( $html ); + } else { + $stack_top->block->innerHTML = $html; + } + if ( isset( $stack_top->leading_html_start ) ) { $this->output[] = (array) self::freeform( substr( diff --git a/src/wp-includes/default-filters.php b/src/wp-includes/default-filters.php index c36ba799cf..cddc762c86 100644 --- a/src/wp-includes/default-filters.php +++ b/src/wp-includes/default-filters.php @@ -181,6 +181,7 @@ add_filter( 'the_title', 'wptexturize' ); add_filter( 'the_title', 'convert_chars' ); add_filter( 'the_title', 'trim' ); +add_filter( 'the_content', 'do_blocks', 9 ); add_filter( 'the_content', 'wptexturize' ); add_filter( 'the_content', 'convert_smilies', 20 ); add_filter( 'the_content', 'wpautop' ); diff --git a/src/wp-includes/formatting.php b/src/wp-includes/formatting.php index a0438e9c53..f408b1bfd0 100644 --- a/src/wp-includes/formatting.php +++ b/src/wp-includes/formatting.php @@ -458,6 +458,11 @@ function wpautop( $pee, $br = true ) { return ''; } + // We don't need to autop posts with blocks in them. + if ( has_blocks( $pee ) ) { + return $pee; + } + // Just to make things a little easier, pad the end. $pee = $pee . "\n"; @@ -3635,6 +3640,7 @@ function wp_trim_excerpt( $text = '' ) { $text = get_the_content( '' ); $text = strip_shortcodes( $text ); + $text = strip_dynamic_blocks( $text ); /** This filter is documented in wp-includes/post-template.php */ $text = apply_filters( 'the_content', $text ); diff --git a/src/wp-settings.php b/src/wp-settings.php index fbd231d45a..87ca2d9e94 100644 --- a/src/wp-settings.php +++ b/src/wp-settings.php @@ -248,6 +248,12 @@ require( ABSPATH . WPINC . '/class-wp-block-type.php' ); require( ABSPATH . WPINC . '/class-wp-block-type-registry.php' ); require( ABSPATH . WPINC . '/class-wp-block-parser.php' ); require( ABSPATH . WPINC . '/blocks.php' ); +require( ABSPATH . WPINC . '/blocks/archives.php' ); +require( ABSPATH . WPINC . '/blocks/block.php' ); +require( ABSPATH . WPINC . '/blocks/categories.php' ); +require( ABSPATH . WPINC . '/blocks/latest-comments.php' ); +require( ABSPATH . WPINC . '/blocks/latest-posts.php' ); +require( ABSPATH . WPINC . '/blocks/shortcode.php' ); $GLOBALS['wp_embed'] = new WP_Embed(); diff --git a/tests/phpunit/data/blocks/do-blocks-expected.html b/tests/phpunit/data/blocks/do-blocks-expected.html index 4a3dc379ef..f413182051 100644 --- a/tests/phpunit/data/blocks/do-blocks-expected.html +++ b/tests/phpunit/data/blocks/do-blocks-expected.html @@ -2,13 +2,18 @@ +

    First Gutenberg Paragraph

    +

    Second Auto Paragraph

    + +

    Third Gutenberg Paragraph

    +

    Third Auto Paragraph

    [someshortcode]

    diff --git a/tests/phpunit/data/blocks/fixtures/core__4-invalid-starting-letter.server.html b/tests/phpunit/data/blocks/fixtures/core__4-invalid-starting-letter.server.html new file mode 100644 index 0000000000..8b13789179 --- /dev/null +++ b/tests/phpunit/data/blocks/fixtures/core__4-invalid-starting-letter.server.html @@ -0,0 +1 @@ + diff --git a/tests/phpunit/data/blocks/fixtures/core__archives.server.html b/tests/phpunit/data/blocks/fixtures/core__archives.server.html new file mode 100644 index 0000000000..fc1fd58758 --- /dev/null +++ b/tests/phpunit/data/blocks/fixtures/core__archives.server.html @@ -0,0 +1 @@ +
    No archives to show.
    \ No newline at end of file diff --git a/tests/phpunit/data/blocks/fixtures/core__archives__showPostCounts.server.html b/tests/phpunit/data/blocks/fixtures/core__archives__showPostCounts.server.html new file mode 100644 index 0000000000..fc1fd58758 --- /dev/null +++ b/tests/phpunit/data/blocks/fixtures/core__archives__showPostCounts.server.html @@ -0,0 +1 @@ +
    No archives to show.
    \ No newline at end of file diff --git a/tests/phpunit/data/blocks/fixtures/core__audio.server.html b/tests/phpunit/data/blocks/fixtures/core__audio.server.html new file mode 100644 index 0000000000..35d42b09c2 --- /dev/null +++ b/tests/phpunit/data/blocks/fixtures/core__audio.server.html @@ -0,0 +1,5 @@ + +
    + +
    + diff --git a/tests/phpunit/data/blocks/fixtures/core__block.server.html b/tests/phpunit/data/blocks/fixtures/core__block.server.html new file mode 100644 index 0000000000..8b13789179 --- /dev/null +++ b/tests/phpunit/data/blocks/fixtures/core__block.server.html @@ -0,0 +1 @@ + diff --git a/tests/phpunit/data/blocks/fixtures/core__button__center.server.html b/tests/phpunit/data/blocks/fixtures/core__button__center.server.html new file mode 100644 index 0000000000..bbeb7ee0a1 --- /dev/null +++ b/tests/phpunit/data/blocks/fixtures/core__button__center.server.html @@ -0,0 +1,3 @@ + +
    Help build Gutenberg
    + diff --git a/tests/phpunit/data/blocks/fixtures/core__categories.server.html b/tests/phpunit/data/blocks/fixtures/core__categories.server.html new file mode 100644 index 0000000000..b6684f132a --- /dev/null +++ b/tests/phpunit/data/blocks/fixtures/core__categories.server.html @@ -0,0 +1 @@ + diff --git a/tests/phpunit/data/blocks/fixtures/core__code.server.html b/tests/phpunit/data/blocks/fixtures/core__code.server.html new file mode 100644 index 0000000000..3f7d5f3791 --- /dev/null +++ b/tests/phpunit/data/blocks/fixtures/core__code.server.html @@ -0,0 +1,5 @@ + +
    export default function MyButton() {
    +	return <Button>Click Me!</Button>;
    +}
    + diff --git a/tests/phpunit/data/blocks/fixtures/core__column.parsed.json b/tests/phpunit/data/blocks/fixtures/core__column.parsed.json index 74b53bdf6a..53f60ddbae 100644 --- a/tests/phpunit/data/blocks/fixtures/core__column.parsed.json +++ b/tests/phpunit/data/blocks/fixtures/core__column.parsed.json @@ -3,20 +3,38 @@ "blockName": "core/column", "attrs": {}, "innerBlocks": [ + { + "blockName": null, + "attrs": {}, + "innerBlocks": [], + "innerHTML": "\n
    \n\t" + }, { "blockName": "core/paragraph", "attrs": {}, "innerBlocks": [], "innerHTML": "\n\t

    Column One, Paragraph One

    \n\t" }, + { + "blockName": null, + "attrs": {}, + "innerBlocks": [], + "innerHTML": "\n\t" + }, { "blockName": "core/paragraph", "attrs": {}, "innerBlocks": [], "innerHTML": "\n\t

    Column One, Paragraph Two

    \n\t" - } - ], - "innerHTML": "\n
    \n\t\n\t\n
    \n" + }, + { + "blockName": null, + "attrs": {}, + "innerBlocks": [], + "innerHTML": "\n
    \n" + } + ], + "innerHTML": "" }, { "blockName": null, diff --git a/tests/phpunit/data/blocks/fixtures/core__column.server.html b/tests/phpunit/data/blocks/fixtures/core__column.server.html new file mode 100644 index 0000000000..b40bed22d1 --- /dev/null +++ b/tests/phpunit/data/blocks/fixtures/core__column.server.html @@ -0,0 +1,10 @@ + +
    + +

    Column One, Paragraph One

    + + +

    Column One, Paragraph Two

    + +
    + diff --git a/tests/phpunit/data/blocks/fixtures/core__columns.parsed.json b/tests/phpunit/data/blocks/fixtures/core__columns.parsed.json index 9ec5cef66a..111a378aa5 100644 --- a/tests/phpunit/data/blocks/fixtures/core__columns.parsed.json +++ b/tests/phpunit/data/blocks/fixtures/core__columns.parsed.json @@ -5,46 +5,100 @@ "columns": 3 }, "innerBlocks": [ + { + "blockName": null, + "attrs": {}, + "innerBlocks": [], + "innerHTML": "\n
    \n\t" + }, { "blockName": "core/column", "attrs": {}, "innerBlocks": [ - { + { + "blockName": null, + "attrs": {}, + "innerBlocks": [], + "innerHTML": "\n\t
    \n\t\t" + }, + { "blockName": "core/paragraph", "attrs": {}, "innerBlocks": [], "innerHTML": "\n\t\t

    Column One, Paragraph One

    \n\t\t" }, - { + { + "blockName": null, + "attrs": {}, + "innerBlocks": [], + "innerHTML": "\n\t\t" + }, + { "blockName": "core/paragraph", "attrs": {}, "innerBlocks": [], "innerHTML": "\n\t\t

    Column One, Paragraph Two

    \n\t\t" - } + }, + { + "blockName": null, + "attrs": {}, + "innerBlocks": [], + "innerHTML": "\n\t
    \n\t" + } ], - "innerHTML": "\n\t
    \n\t\t\n\t\t\n\t
    \n\t" + "innerHTML": "" }, + { + "blockName": null, + "attrs": {}, + "innerBlocks": [], + "innerHTML": "\n\t" + }, { "blockName": "core/column", "attrs": {}, - "innerBlocks": [ - { + "innerBlocks": [ + { + "blockName": null, + "attrs": {}, + "innerBlocks": [], + "innerHTML": "\n\t
    \n\t\t" + }, + { "blockName": "core/paragraph", "attrs": {}, "innerBlocks": [], "innerHTML": "\n\t\t

    Column Two, Paragraph One

    \n\t\t" }, - { + { + "blockName": null, + "attrs": {}, + "innerBlocks": [], + "innerHTML": "\n\t\t" + }, + { "blockName": "core/paragraph", "attrs": {}, "innerBlocks": [], "innerHTML": "\n\t\t

    Column Three, Paragraph One

    \n\t\t" - } + }, + { + "blockName": null, + "attrs": {}, + "innerBlocks": [], + "innerHTML": "\n\t
    \n\t" + } ], - "innerHTML": "\n\t
    \n\t\t\n\t\t\n\t
    \n\t" - } + "innerHTML": "" + }, + { + "blockName": null, + "attrs": {}, + "innerBlocks": [], + "innerHTML": "\n
    \n" + } ], - "innerHTML": "\n
    \n\t\n\t\n
    \n" + "innerHTML": "" }, { "blockName": null, diff --git a/tests/phpunit/data/blocks/fixtures/core__columns.server.html b/tests/phpunit/data/blocks/fixtures/core__columns.server.html new file mode 100644 index 0000000000..a3d2fd1438 --- /dev/null +++ b/tests/phpunit/data/blocks/fixtures/core__columns.server.html @@ -0,0 +1,24 @@ + +
    + +
    + +

    Column One, Paragraph One

    + + +

    Column One, Paragraph Two

    + +
    + + +
    + +

    Column Two, Paragraph One

    + + +

    Column Three, Paragraph One

    + +
    + +
    + diff --git a/tests/phpunit/data/blocks/fixtures/core__cover-image.server.html b/tests/phpunit/data/blocks/fixtures/core__cover-image.server.html new file mode 100644 index 0000000000..e9d6aca013 --- /dev/null +++ b/tests/phpunit/data/blocks/fixtures/core__cover-image.server.html @@ -0,0 +1,5 @@ + +
    +

    Guten Berg!

    +
    + diff --git a/tests/phpunit/data/blocks/fixtures/core__embed.server.html b/tests/phpunit/data/blocks/fixtures/core__embed.server.html new file mode 100644 index 0000000000..6210367e78 --- /dev/null +++ b/tests/phpunit/data/blocks/fixtures/core__embed.server.html @@ -0,0 +1,8 @@ + +
    +
    + https://example.com/ +
    +
    Embedded content from an example URL
    +
    + diff --git a/tests/phpunit/data/blocks/fixtures/core__file__new-window.server.html b/tests/phpunit/data/blocks/fixtures/core__file__new-window.server.html new file mode 100644 index 0000000000..b948a1d8c2 --- /dev/null +++ b/tests/phpunit/data/blocks/fixtures/core__file__new-window.server.html @@ -0,0 +1,3 @@ + +
    6546Download
    + diff --git a/tests/phpunit/data/blocks/fixtures/core__file__no-download-button.server.html b/tests/phpunit/data/blocks/fixtures/core__file__no-download-button.server.html new file mode 100644 index 0000000000..ceaf094b39 --- /dev/null +++ b/tests/phpunit/data/blocks/fixtures/core__file__no-download-button.server.html @@ -0,0 +1,3 @@ + +
    lkjfijwef
    + diff --git a/tests/phpunit/data/blocks/fixtures/core__file__no-text-link.server.html b/tests/phpunit/data/blocks/fixtures/core__file__no-text-link.server.html new file mode 100644 index 0000000000..0110c1ac8b --- /dev/null +++ b/tests/phpunit/data/blocks/fixtures/core__file__no-text-link.server.html @@ -0,0 +1,3 @@ + +
    Download
    + diff --git a/tests/phpunit/data/blocks/fixtures/core__freeform.server.html b/tests/phpunit/data/blocks/fixtures/core__freeform.server.html new file mode 100644 index 0000000000..384bea05af --- /dev/null +++ b/tests/phpunit/data/blocks/fixtures/core__freeform.server.html @@ -0,0 +1,6 @@ + +Testing freeform block with some +
    + HTML content +
    + diff --git a/tests/phpunit/data/blocks/fixtures/core__freeform__undelimited.server.html b/tests/phpunit/data/blocks/fixtures/core__freeform__undelimited.server.html new file mode 100644 index 0000000000..2c349303c5 --- /dev/null +++ b/tests/phpunit/data/blocks/fixtures/core__freeform__undelimited.server.html @@ -0,0 +1,4 @@ +Testing freeform block with some +
    + HTML content +
    diff --git a/tests/phpunit/data/blocks/fixtures/core__gallery.server.html b/tests/phpunit/data/blocks/fixtures/core__gallery.server.html new file mode 100644 index 0000000000..da1d17deab --- /dev/null +++ b/tests/phpunit/data/blocks/fixtures/core__gallery.server.html @@ -0,0 +1,14 @@ + + + diff --git a/tests/phpunit/data/blocks/fixtures/core__gallery__columns.server.html b/tests/phpunit/data/blocks/fixtures/core__gallery__columns.server.html new file mode 100644 index 0000000000..f801a97371 --- /dev/null +++ b/tests/phpunit/data/blocks/fixtures/core__gallery__columns.server.html @@ -0,0 +1,14 @@ + + + diff --git a/tests/phpunit/data/blocks/fixtures/core__heading__h2-em.server.html b/tests/phpunit/data/blocks/fixtures/core__heading__h2-em.server.html new file mode 100644 index 0000000000..b67b8225a5 --- /dev/null +++ b/tests/phpunit/data/blocks/fixtures/core__heading__h2-em.server.html @@ -0,0 +1,3 @@ + +

    The Inserter Tool

    + diff --git a/tests/phpunit/data/blocks/fixtures/core__heading__h2.server.html b/tests/phpunit/data/blocks/fixtures/core__heading__h2.server.html new file mode 100644 index 0000000000..d0ea06ef06 --- /dev/null +++ b/tests/phpunit/data/blocks/fixtures/core__heading__h2.server.html @@ -0,0 +1,3 @@ + +

    A picture is worth a thousand words, or so the saying goes

    + diff --git a/tests/phpunit/data/blocks/fixtures/core__html.server.html b/tests/phpunit/data/blocks/fixtures/core__html.server.html new file mode 100644 index 0000000000..819264ffec --- /dev/null +++ b/tests/phpunit/data/blocks/fixtures/core__html.server.html @@ -0,0 +1,4 @@ + +

    Some HTML code

    +This text will scroll from right to left + diff --git a/tests/phpunit/data/blocks/fixtures/core__image.server.html b/tests/phpunit/data/blocks/fixtures/core__image.server.html new file mode 100644 index 0000000000..39d6cec9b9 --- /dev/null +++ b/tests/phpunit/data/blocks/fixtures/core__image.server.html @@ -0,0 +1,3 @@ + +
    + diff --git a/tests/phpunit/data/blocks/fixtures/core__image__attachment-link.server.html b/tests/phpunit/data/blocks/fixtures/core__image__attachment-link.server.html new file mode 100644 index 0000000000..be53c43310 --- /dev/null +++ b/tests/phpunit/data/blocks/fixtures/core__image__attachment-link.server.html @@ -0,0 +1,3 @@ + +
    + diff --git a/tests/phpunit/data/blocks/fixtures/core__image__center-caption.server.html b/tests/phpunit/data/blocks/fixtures/core__image__center-caption.server.html new file mode 100644 index 0000000000..4f62db1967 --- /dev/null +++ b/tests/phpunit/data/blocks/fixtures/core__image__center-caption.server.html @@ -0,0 +1,3 @@ + +
    Give it a try. Press the "really wide" button on the image toolbar.
    + diff --git a/tests/phpunit/data/blocks/fixtures/core__image__custom-link.server.html b/tests/phpunit/data/blocks/fixtures/core__image__custom-link.server.html new file mode 100644 index 0000000000..a4a580543b --- /dev/null +++ b/tests/phpunit/data/blocks/fixtures/core__image__custom-link.server.html @@ -0,0 +1,3 @@ + +
    + diff --git a/tests/phpunit/data/blocks/fixtures/core__image__media-link.server.html b/tests/phpunit/data/blocks/fixtures/core__image__media-link.server.html new file mode 100644 index 0000000000..9ed77f1138 --- /dev/null +++ b/tests/phpunit/data/blocks/fixtures/core__image__media-link.server.html @@ -0,0 +1,3 @@ + +
    + diff --git a/tests/phpunit/data/blocks/fixtures/core__invalid-Capitals.server.html b/tests/phpunit/data/blocks/fixtures/core__invalid-Capitals.server.html new file mode 100644 index 0000000000..8b13789179 --- /dev/null +++ b/tests/phpunit/data/blocks/fixtures/core__invalid-Capitals.server.html @@ -0,0 +1 @@ + diff --git a/tests/phpunit/data/blocks/fixtures/core__invalid-special.server.html b/tests/phpunit/data/blocks/fixtures/core__invalid-special.server.html new file mode 100644 index 0000000000..8b13789179 --- /dev/null +++ b/tests/phpunit/data/blocks/fixtures/core__invalid-special.server.html @@ -0,0 +1 @@ + diff --git a/tests/phpunit/data/blocks/fixtures/core__latest-comments.server.html b/tests/phpunit/data/blocks/fixtures/core__latest-comments.server.html new file mode 100644 index 0000000000..17ac04fb9f --- /dev/null +++ b/tests/phpunit/data/blocks/fixtures/core__latest-comments.server.html @@ -0,0 +1 @@ +
    No comments to show.
    diff --git a/tests/phpunit/data/blocks/fixtures/core__latest-posts.server.html b/tests/phpunit/data/blocks/fixtures/core__latest-posts.server.html new file mode 100644 index 0000000000..b671f3d6ab --- /dev/null +++ b/tests/phpunit/data/blocks/fixtures/core__latest-posts.server.html @@ -0,0 +1 @@ + diff --git a/tests/phpunit/data/blocks/fixtures/core__latest-posts__displayPostDate.server.html b/tests/phpunit/data/blocks/fixtures/core__latest-posts__displayPostDate.server.html new file mode 100644 index 0000000000..b671f3d6ab --- /dev/null +++ b/tests/phpunit/data/blocks/fixtures/core__latest-posts__displayPostDate.server.html @@ -0,0 +1 @@ + diff --git a/tests/phpunit/data/blocks/fixtures/core__list__ul.server.html b/tests/phpunit/data/blocks/fixtures/core__list__ul.server.html new file mode 100644 index 0000000000..0c558ef413 --- /dev/null +++ b/tests/phpunit/data/blocks/fixtures/core__list__ul.server.html @@ -0,0 +1,3 @@ + + + diff --git a/tests/phpunit/data/blocks/fixtures/core__missing.server.html b/tests/phpunit/data/blocks/fixtures/core__missing.server.html new file mode 100644 index 0000000000..7862abe71f --- /dev/null +++ b/tests/phpunit/data/blocks/fixtures/core__missing.server.html @@ -0,0 +1,6 @@ + +

    Testing missing block with some

    +
    + HTML content +
    + diff --git a/tests/phpunit/data/blocks/fixtures/core__more.server.html b/tests/phpunit/data/blocks/fixtures/core__more.server.html new file mode 100644 index 0000000000..cbba8ef27b --- /dev/null +++ b/tests/phpunit/data/blocks/fixtures/core__more.server.html @@ -0,0 +1,3 @@ + + + diff --git a/tests/phpunit/data/blocks/fixtures/core__more__custom-text-teaser.server.html b/tests/phpunit/data/blocks/fixtures/core__more__custom-text-teaser.server.html new file mode 100644 index 0000000000..65cd03d8d6 --- /dev/null +++ b/tests/phpunit/data/blocks/fixtures/core__more__custom-text-teaser.server.html @@ -0,0 +1,4 @@ + + + + diff --git a/tests/phpunit/data/blocks/fixtures/core__nextpage.server.html b/tests/phpunit/data/blocks/fixtures/core__nextpage.server.html new file mode 100644 index 0000000000..69cf437029 --- /dev/null +++ b/tests/phpunit/data/blocks/fixtures/core__nextpage.server.html @@ -0,0 +1,3 @@ + + + diff --git a/tests/phpunit/data/blocks/fixtures/core__paragraph__align-right.server.html b/tests/phpunit/data/blocks/fixtures/core__paragraph__align-right.server.html new file mode 100644 index 0000000000..1db164ca1f --- /dev/null +++ b/tests/phpunit/data/blocks/fixtures/core__paragraph__align-right.server.html @@ -0,0 +1,3 @@ + +

    ... like this one, which is separate from the above and right aligned.

    + diff --git a/tests/phpunit/data/blocks/fixtures/core__paragraph__deprecated.server.html b/tests/phpunit/data/blocks/fixtures/core__paragraph__deprecated.server.html new file mode 100644 index 0000000000..d029bd55a5 --- /dev/null +++ b/tests/phpunit/data/blocks/fixtures/core__paragraph__deprecated.server.html @@ -0,0 +1,3 @@ + +Unwrapped is still valid. + diff --git a/tests/phpunit/data/blocks/fixtures/core__preformatted.server.html b/tests/phpunit/data/blocks/fixtures/core__preformatted.server.html new file mode 100644 index 0000000000..438c162aac --- /dev/null +++ b/tests/phpunit/data/blocks/fixtures/core__preformatted.server.html @@ -0,0 +1,3 @@ + +
    Some preformatted text...
    And more!
    + diff --git a/tests/phpunit/data/blocks/fixtures/core__pullquote.server.html b/tests/phpunit/data/blocks/fixtures/core__pullquote.server.html new file mode 100644 index 0000000000..8103cf6f39 --- /dev/null +++ b/tests/phpunit/data/blocks/fixtures/core__pullquote.server.html @@ -0,0 +1,7 @@ + +
    +
    +

    Testing pullquote block...

    ...with a caption +
    +
    + diff --git a/tests/phpunit/data/blocks/fixtures/core__pullquote__multi-paragraph.server.html b/tests/phpunit/data/blocks/fixtures/core__pullquote__multi-paragraph.server.html new file mode 100644 index 0000000000..b1d0053742 --- /dev/null +++ b/tests/phpunit/data/blocks/fixtures/core__pullquote__multi-paragraph.server.html @@ -0,0 +1,9 @@ + +
    +
    +

    Paragraph one

    +

    Paragraph two

    + by whomever +
    +
    + diff --git a/tests/phpunit/data/blocks/fixtures/core__quote__style-1.server.html b/tests/phpunit/data/blocks/fixtures/core__quote__style-1.server.html new file mode 100644 index 0000000000..369cebb77d --- /dev/null +++ b/tests/phpunit/data/blocks/fixtures/core__quote__style-1.server.html @@ -0,0 +1,3 @@ + +

    The editor will endeavour to create a new page and post building experience that makes writing rich posts effortless, and has “blocks” to make it easy what today might take shortcodes, custom HTML, or “mystery meat” embed discovery.

    Matt Mullenweg, 2017
    + diff --git a/tests/phpunit/data/blocks/fixtures/core__quote__style-2.server.html b/tests/phpunit/data/blocks/fixtures/core__quote__style-2.server.html new file mode 100644 index 0000000000..f75ac8088b --- /dev/null +++ b/tests/phpunit/data/blocks/fixtures/core__quote__style-2.server.html @@ -0,0 +1,3 @@ + +

    There is no greater agony than bearing an untold story inside you.

    Maya Angelou
    + diff --git a/tests/phpunit/data/blocks/fixtures/core__separator.server.html b/tests/phpunit/data/blocks/fixtures/core__separator.server.html new file mode 100644 index 0000000000..3e79e2620f --- /dev/null +++ b/tests/phpunit/data/blocks/fixtures/core__separator.server.html @@ -0,0 +1,3 @@ + +
    + diff --git a/tests/phpunit/data/blocks/fixtures/core__shortcode.server.html b/tests/phpunit/data/blocks/fixtures/core__shortcode.server.html new file mode 100644 index 0000000000..eb3661f811 --- /dev/null +++ b/tests/phpunit/data/blocks/fixtures/core__shortcode.server.html @@ -0,0 +1,2 @@ +

    [gallery ids="238,338"]

    + diff --git a/tests/phpunit/data/blocks/fixtures/core__spacer.server.html b/tests/phpunit/data/blocks/fixtures/core__spacer.server.html new file mode 100644 index 0000000000..e0302d2a89 --- /dev/null +++ b/tests/phpunit/data/blocks/fixtures/core__spacer.server.html @@ -0,0 +1,3 @@ + + + diff --git a/tests/phpunit/data/blocks/fixtures/core__subhead.server.html b/tests/phpunit/data/blocks/fixtures/core__subhead.server.html new file mode 100644 index 0000000000..bddf91f11e --- /dev/null +++ b/tests/phpunit/data/blocks/fixtures/core__subhead.server.html @@ -0,0 +1,3 @@ + +

    This is a subhead.

    + diff --git a/tests/phpunit/data/blocks/fixtures/core__table.server.html b/tests/phpunit/data/blocks/fixtures/core__table.server.html new file mode 100644 index 0000000000..561dde6adc --- /dev/null +++ b/tests/phpunit/data/blocks/fixtures/core__table.server.html @@ -0,0 +1,3 @@ + +
    VersionMusicianDate
    .70No musician chosen.May 27, 2003
    1.0Miles DavisJanuary 3, 2004
    Lots of versions skipped, see the full list
    4.4Clifford BrownDecember 8, 2015
    4.5Coleman HawkinsApril 12, 2016
    4.6Pepper AdamsAugust 16, 2016
    4.7Sarah VaughanDecember 6, 2016
    + diff --git a/tests/phpunit/data/blocks/fixtures/core__text-columns.server.html b/tests/phpunit/data/blocks/fixtures/core__text-columns.server.html new file mode 100644 index 0000000000..3fcbb7df04 --- /dev/null +++ b/tests/phpunit/data/blocks/fixtures/core__text-columns.server.html @@ -0,0 +1,10 @@ + +
    +
    +

    One

    +
    +
    +

    Two

    +
    +
    + diff --git a/tests/phpunit/data/blocks/fixtures/core__text__converts-to-paragraph.server.html b/tests/phpunit/data/blocks/fixtures/core__text__converts-to-paragraph.server.html new file mode 100644 index 0000000000..2907dab577 --- /dev/null +++ b/tests/phpunit/data/blocks/fixtures/core__text__converts-to-paragraph.server.html @@ -0,0 +1,3 @@ + +

    This is an old-style text block. Changed to paragraph in #2135.

    + diff --git a/tests/phpunit/data/blocks/fixtures/core__verse.server.html b/tests/phpunit/data/blocks/fixtures/core__verse.server.html new file mode 100644 index 0000000000..7903ff845d --- /dev/null +++ b/tests/phpunit/data/blocks/fixtures/core__verse.server.html @@ -0,0 +1,3 @@ + +
    A verse
    And more!
    + diff --git a/tests/phpunit/data/blocks/fixtures/core__video.server.html b/tests/phpunit/data/blocks/fixtures/core__video.server.html new file mode 100644 index 0000000000..e46e3a2621 --- /dev/null +++ b/tests/phpunit/data/blocks/fixtures/core__video.server.html @@ -0,0 +1,3 @@ + +
    + diff --git a/tests/phpunit/includes/functions.php b/tests/phpunit/includes/functions.php index 17bc879ec1..d600c71b03 100644 --- a/tests/phpunit/includes/functions.php +++ b/tests/phpunit/includes/functions.php @@ -212,3 +212,17 @@ function _wp_rest_server_class_filter() { // Skip `setcookie` calls in auth_cookie functions due to warning: // Cannot modify header information - headers already sent by ... tests_add_filter( 'send_auth_cookies', '__return_false' ); + +/** + * After the init action has been run once, trying to re-register block types can cause + * _doing_it_wrong warnings. To avoid this, unhook the block registration functions. + * + * @since 5.0.0 + */ +function _unhook_block_registration() { + remove_action( 'init', 'register_block_core_archives' ); + remove_action( 'init', 'register_block_core_categories' ); + remove_action( 'init', 'register_block_core_latest_posts' ); + remove_action( 'init', 'register_block_core_shortcode' ); +} +tests_add_filter( 'init', '_unhook_block_registration', 1000 ); diff --git a/tests/phpunit/tests/blocks/block-parser.php b/tests/phpunit/tests/blocks/block-parser.php index 3818cd9816..8ab5b6b536 100644 --- a/tests/phpunit/tests/blocks/block-parser.php +++ b/tests/phpunit/tests/blocks/block-parser.php @@ -59,7 +59,7 @@ class WP_Test_Block_Parser extends WP_UnitTestCase { foreach ( array( $html_path, $parsed_json_path ) as $filename ) { if ( ! file_exists( $filename ) ) { - //throw new Exception( "Missing fixture file: '$filename'" ); + throw new Exception( "Missing fixture file: '$filename'" ); } } @@ -116,5 +116,4 @@ class WP_Test_Block_Parser extends WP_UnitTestCase { protected function strip_r( $input ) { return str_replace( "\r", '', $input ); } - } diff --git a/tests/phpunit/tests/blocks/render.php b/tests/phpunit/tests/blocks/render.php new file mode 100644 index 0000000000..a03397bc10 --- /dev/null +++ b/tests/phpunit/tests/blocks/render.php @@ -0,0 +1,310 @@ +test_block_instance_number = 0; + + $registry = WP_Block_Type_Registry::get_instance(); + if ( $registry->is_registered( 'core/test' ) ) { + $registry->unregister( 'core/test' ); + } + } + + /** + * @ticket 45109 + */ + public function test_do_blocks_removes_comments() { + $original_html = file_get_contents( DIR_TESTDATA . '/blocks/do-blocks-original.html' ); + $expected_html = file_get_contents( DIR_TESTDATA . '/blocks/do-blocks-expected.html' ); + + $actual_html = do_blocks( $original_html ); + + $this->assertEquals( $expected_html, $actual_html ); + } + + /** + * @ticket 45109 + */ + public function test_the_content() { + add_shortcode( 'someshortcode', array( $this, 'handle_shortcode' ) ); + + $classic_content = "Foo\n\n[someshortcode]\n\nBar\n\n[/someshortcode]\n\nBaz"; + $block_content = "\n

    Foo

    \n\n\n[someshortcode]\n\nBar\n\n[/someshortcode]\n\n\n

    Baz

    \n"; + + $classic_filtered_content = apply_filters( 'the_content', $classic_content ); + $block_filtered_content = apply_filters( 'the_content', $block_content ); + + // Block rendering add some extra blank lines, but we're not worried about them. + $block_filtered_content = preg_replace( "/\n{2,}/", "\n", $block_filtered_content ); + + $this->assertEquals( $classic_filtered_content, $block_filtered_content ); + } + + function handle_shortcode( $atts, $content ) { + return $content; + } + + /** + * @ticket 45109 + */ + public function data_do_block_test_filenames() { + self::$fixtures_dir = DIR_TESTDATA . '/blocks/fixtures'; + + $fixture_filenames = array_merge( + glob( self::$fixtures_dir . '/*.json' ), + glob( self::$fixtures_dir . '/*.html' ) + ); + + $fixture_filenames = array_values( + array_unique( + array_map( + array( $this, 'clean_fixture_filename' ), + $fixture_filenames + ) + ) + ); + + return array_map( + array( $this, 'pass_parser_fixture_filenames' ), + $fixture_filenames + ); } + + /** + * @dataProvider data_do_block_test_filenames + * @ticket 45109 + */ + public function test_do_block_output( $html_filename, $server_html_filename ) { + $html_path = self::$fixtures_dir . '/' . $html_filename; + $server_html_path = self::$fixtures_dir . '/' . $server_html_filename; + + foreach ( array( $html_path, $server_html_path ) as $filename ) { + if ( ! file_exists( $filename ) ) { + throw new Exception( "Missing fixture file: '$filename'" ); + } + } + + $html = do_blocks( self::strip_r( file_get_contents( $html_path ) ) ); + $expected_html = self::strip_r( file_get_contents( $server_html_path ) ); + + $this->assertEquals( + $expected_html, + $html, + "File '$html_path' does not match expected value" + ); + } + + /** + * @ticket 45109 + */ + public function test_dynamic_block_rendering() { + $settings = array( + 'render_callback' => array( + $this, + 'render_test_block', + ), + ); + register_block_type( 'core/test', $settings ); + + // The duplicated dynamic blocks below are there to ensure that do_blocks() replaces each one-by-one. + $post_content = + 'before' . + '' . + '' . + 'between' . + '' . + '' . + 'after'; + + $updated_post_content = do_blocks( $post_content ); + $this->assertEquals( + $updated_post_content, + 'before' . + '1:b1' . + '2:b1' . + 'between' . + '3:b2' . + '4:b2' . + 'after' + ); + } + + /** + * @ticket 45109 + */ + public function test_global_post_persistence() { + global $post; + + register_block_type( + 'core/test', + array( + 'render_callback' => array( + $this, + 'render_test_block_wp_query', + ), + ) + ); + + $posts = self::factory()->post->create_many( 5 ); + $post = get_post( end( $posts ) ); + + $global_post = $post; + do_blocks( '' ); + + $this->assertEquals( $global_post, $post ); + } + + /** + * @ticket 45109 + */ + public function test_dynamic_block_renders_string() { + $settings = array( + 'render_callback' => array( + $this, + 'render_test_block_numeric', + ), + ); + + register_block_type( 'core/test', $settings ); + $block_type = new WP_Block_Type( 'core/test', $settings ); + + $rendered = $block_type->render(); + + $this->assertSame( '10', $rendered ); + $this->assertInternalType( 'string', $rendered ); + } + + /** + * Helper function to remove relative paths and extension from a filename, leaving just the fixture name. + * + * @since 5.0.0 + * + * @param string $filename The filename to clean. + * @return string The cleaned fixture name. + */ + protected function clean_fixture_filename( $filename ) { + $filename = basename( $filename ); + $filename = preg_replace( '/\..+$/', '', $filename ); + return $filename; + } + + /** + * Helper function to return the filenames needed to test the parser output. + * + * @since 5.0.0 + * + * @param string $filename The cleaned fixture name. + * @return array The input and expected output filenames for that fixture. + */ + protected function pass_parser_fixture_filenames( $filename ) { + return array( + "$filename.html", + "$filename.server.html", + ); + } + + /** + * Helper function to remove '\r' characters from a string. + * + * @since 5.0.0 + * + * @param string $input The string to remove '\r' from. + * @return string The input string, with '\r' characters removed. + */ + protected function strip_r( $input ) { + return str_replace( "\r", '', $input ); + } + + /** + * Test block rendering function. + * + * @since 5.0.0 + * + * @param array $attributes Block attributes. + * @return string Block output. + */ + public function render_test_block( $attributes ) { + $this->test_block_instance_number += 1; + return $this->test_block_instance_number . ':' . $attributes['value']; + } + + /** + * Test block rendering function, returning numeric value. + * + * @since 5.0.0 + * + * @return int Block output. + */ + public function render_test_block_numeric() { + return 10; + } + + /** + * Test block rendering function, creating a new WP_Query instance. + * + * @since 5.0.0 + * + * @return string Block output. + */ + public function render_test_block_wp_query() { + $content = ''; + $recent = new WP_Query( + array( + 'numberposts' => 10, + 'orderby' => 'ID', + 'order' => 'DESC', + 'post_type' => 'post', + 'post_status' => 'draft, publish, future, pending, private', + 'suppress_filters' => true, + ) + ); + + while ( $recent->have_posts() ) { + $recent->the_post(); + + $content .= get_the_title(); + } + + wp_reset_postdata(); + + return $content; + } + +} diff --git a/tools/webpack/packages.js b/tools/webpack/packages.js index 9376d37e1b..c9842cb55c 100644 --- a/tools/webpack/packages.js +++ b/tools/webpack/packages.js @@ -117,7 +117,14 @@ module.exports = function( env = { environment: 'production', watch: false } ) { }; const phpFiles = { - 'block-serialization-default-parser/parser.php': 'wp-includes/class-wp-block-parser.php', + // Parser shouldn't be copied until nested block issues are resolved. + // 'block-serialization-default-parser/parser.php': 'wp-includes/class-wp-block-parser.php', + 'block-library/src/archives/index.php': 'wp-includes/blocks/archives.php', + 'block-library/src/block/index.php': 'wp-includes/blocks/block.php', + 'block-library/src/categories/index.php': 'wp-includes/blocks/categories.php', + 'block-library/src/latest-comments/index.php': 'wp-includes/blocks/latest-comments.php', + 'block-library/src/latest-posts/index.php': 'wp-includes/blocks/latest-posts.php', + 'block-library/src/shortcode/index.php': 'wp-includes/blocks/shortcode.php', }; const externals = {