Changeset 57026
- Timestamp:
- 10/28/2023 01:00:14 AM (15 months ago)
- Location:
- trunk
- Files:
-
- 2 edited
Legend:
- Unmodified
- Added
- Removed
-
trunk/src/wp-includes/blocks.php
r56970 r57026 353 353 354 354 $is_core_block = str_starts_with( $file_or_folder, ABSPATH . WPINC ); 355 356 if ( ! $is_core_block && ! file_exists( $metadata_file ) ) { 355 // If the block is not a core block, the metadata file must exist. 356 $metadata_file_exists = $is_core_block || file_exists( $metadata_file ); 357 if ( ! $metadata_file_exists && empty( $args['name'] ) ) { 357 358 return false; 358 359 } 359 360 360 361 // Try to get metadata from the static cache for core blocks. 361 $metadata = false;362 $metadata = array(); 362 363 if ( $is_core_block ) { 363 364 $core_block_name = str_replace( ABSPATH . WPINC . '/blocks/', '', $file_or_folder ); … … 368 369 369 370 // If metadata is not found in the static cache, read it from the file. 370 if ( ! $metadata) {371 if ( $metadata_file_exists && empty( $metadata ) ) { 371 372 $metadata = wp_json_file_decode( $metadata_file, array( 'associative' => true ) ); 372 373 } 373 374 374 if ( ! is_array( $metadata ) || empty( $metadata['name']) ) {375 if ( ! is_array( $metadata ) || ( empty( $metadata['name'] ) && empty( $args['name'] ) ) ) { 375 376 return false; 376 377 } 377 $metadata['file'] = wp_normalize_path( realpath( $metadata_file ) ); 378 379 $metadata['file'] = $metadata_file_exists ? wp_normalize_path( realpath( $metadata_file ) ) : null; 378 380 379 381 /** … … 405 407 $property_mappings = array( 406 408 'apiVersion' => 'api_version', 409 'name' => 'name', 407 410 'title' => 'title', 408 411 'category' => 'category', … … 427 430 if ( isset( $metadata[ $key ] ) ) { 428 431 $settings[ $mapped_key ] = $metadata[ $key ]; 429 if ( $ textdomain && isset( $i18n_schema->$key ) ) {432 if ( $metadata_file_exists && $textdomain && isset( $i18n_schema->$key ) ) { 430 433 $settings[ $mapped_key ] = translate_settings_using_i18n_schema( $i18n_schema->$key, $settings[ $key ], $textdomain ); 431 434 } 432 }433 }434 435 $script_fields = array(436 'editorScript' => 'editor_script_handles',437 'script' => 'script_handles',438 'viewScript' => 'view_script_handles',439 );440 foreach ( $script_fields as $metadata_field_name => $settings_field_name ) {441 if ( ! empty( $metadata[ $metadata_field_name ] ) ) {442 $scripts = $metadata[ $metadata_field_name ];443 $processed_scripts = array();444 if ( is_array( $scripts ) ) {445 for ( $index = 0; $index < count( $scripts ); $index++ ) {446 $result = register_block_script_handle(447 $metadata,448 $metadata_field_name,449 $index450 );451 if ( $result ) {452 $processed_scripts[] = $result;453 }454 }455 } else {456 $result = register_block_script_handle(457 $metadata,458 $metadata_field_name459 );460 if ( $result ) {461 $processed_scripts[] = $result;462 }463 }464 $settings[ $settings_field_name ] = $processed_scripts;465 }466 }467 468 $style_fields = array(469 'editorStyle' => 'editor_style_handles',470 'style' => 'style_handles',471 );472 foreach ( $style_fields as $metadata_field_name => $settings_field_name ) {473 if ( ! empty( $metadata[ $metadata_field_name ] ) ) {474 $styles = $metadata[ $metadata_field_name ];475 $processed_styles = array();476 if ( is_array( $styles ) ) {477 for ( $index = 0; $index < count( $styles ); $index++ ) {478 $result = register_block_style_handle(479 $metadata,480 $metadata_field_name,481 $index482 );483 if ( $result ) {484 $processed_styles[] = $result;485 }486 }487 } else {488 $result = register_block_style_handle(489 $metadata,490 $metadata_field_name491 );492 if ( $result ) {493 $processed_styles[] = $result;494 }495 }496 $settings[ $settings_field_name ] = $processed_styles;497 }498 }499 500 if ( ! empty( $metadata['blockHooks'] ) ) {501 /**502 * Map camelCased position string (from block.json) to snake_cased block type position.503 *504 * @var array505 */506 $position_mappings = array(507 'before' => 'before',508 'after' => 'after',509 'firstChild' => 'first_child',510 'lastChild' => 'last_child',511 );512 513 $settings['block_hooks'] = array();514 foreach ( $metadata['blockHooks'] as $anchor_block_name => $position ) {515 // Avoid infinite recursion (hooking to itself).516 if ( $metadata['name'] === $anchor_block_name ) {517 _doing_it_wrong(518 __METHOD__,519 __( 'Cannot hook block to itself.' ),520 '6.4.0'521 );522 continue;523 }524 525 if ( ! isset( $position_mappings[ $position ] ) ) {526 continue;527 }528 529 $settings['block_hooks'][ $anchor_block_name ] = $position_mappings[ $position ];530 435 } 531 436 } … … 558 463 } 559 464 465 $settings = array_merge( $settings, $args ); 466 467 $script_fields = array( 468 'editorScript' => 'editor_script_handles', 469 'script' => 'script_handles', 470 'viewScript' => 'view_script_handles', 471 ); 472 foreach ( $script_fields as $metadata_field_name => $settings_field_name ) { 473 if ( ! empty( $settings[ $metadata_field_name ] ) ) { 474 $metadata[ $metadata_field_name ] = $settings[ $metadata_field_name ]; 475 } 476 if ( ! empty( $metadata[ $metadata_field_name ] ) ) { 477 $scripts = $metadata[ $metadata_field_name ]; 478 $processed_scripts = array(); 479 if ( is_array( $scripts ) ) { 480 for ( $index = 0; $index < count( $scripts ); $index++ ) { 481 $result = register_block_script_handle( 482 $metadata, 483 $metadata_field_name, 484 $index 485 ); 486 if ( $result ) { 487 $processed_scripts[] = $result; 488 } 489 } 490 } else { 491 $result = register_block_script_handle( 492 $metadata, 493 $metadata_field_name 494 ); 495 if ( $result ) { 496 $processed_scripts[] = $result; 497 } 498 } 499 $settings[ $settings_field_name ] = $processed_scripts; 500 } 501 } 502 503 $style_fields = array( 504 'editorStyle' => 'editor_style_handles', 505 'style' => 'style_handles', 506 ); 507 foreach ( $style_fields as $metadata_field_name => $settings_field_name ) { 508 if ( ! empty( $settings[ $metadata_field_name ] ) ) { 509 $metadata[ $metadata_field_name ] = $settings[ $metadata_field_name ]; 510 } 511 if ( ! empty( $metadata[ $metadata_field_name ] ) ) { 512 $styles = $metadata[ $metadata_field_name ]; 513 $processed_styles = array(); 514 if ( is_array( $styles ) ) { 515 for ( $index = 0; $index < count( $styles ); $index++ ) { 516 $result = register_block_style_handle( 517 $metadata, 518 $metadata_field_name, 519 $index 520 ); 521 if ( $result ) { 522 $processed_styles[] = $result; 523 } 524 } 525 } else { 526 $result = register_block_style_handle( 527 $metadata, 528 $metadata_field_name 529 ); 530 if ( $result ) { 531 $processed_styles[] = $result; 532 } 533 } 534 $settings[ $settings_field_name ] = $processed_styles; 535 } 536 } 537 538 if ( ! empty( $metadata['blockHooks'] ) ) { 539 /** 540 * Map camelCased position string (from block.json) to snake_cased block type position. 541 * 542 * @var array 543 */ 544 $position_mappings = array( 545 'before' => 'before', 546 'after' => 'after', 547 'firstChild' => 'first_child', 548 'lastChild' => 'last_child', 549 ); 550 551 $settings['block_hooks'] = array(); 552 foreach ( $metadata['blockHooks'] as $anchor_block_name => $position ) { 553 // Avoid infinite recursion (hooking to itself). 554 if ( $metadata['name'] === $anchor_block_name ) { 555 _doing_it_wrong( 556 __METHOD__, 557 __( 'Cannot hook block to itself.' ), 558 '6.4.0' 559 ); 560 continue; 561 } 562 563 if ( ! isset( $position_mappings[ $position ] ) ) { 564 continue; 565 } 566 567 $settings['block_hooks'][ $anchor_block_name ] = $position_mappings[ $position ]; 568 } 569 } 570 560 571 /** 561 572 * Filters the settings determined from the block type metadata. … … 566 577 * @param array $metadata Metadata provided for registering a block type. 567 578 */ 568 $settings = apply_filters( 569 'block_type_metadata_settings', 570 array_merge( 571 $settings, 572 $args 573 ), 574 $metadata 575 ); 579 $settings = apply_filters( 'block_type_metadata_settings', $settings, $metadata ); 580 581 $metadata['name'] = ! empty( $settings['name'] ) ? $settings['name'] : $metadata['name']; 576 582 577 583 return WP_Block_Type_Registry::get_instance()->register( -
trunk/tests/phpunit/tests/blocks/register.php
r56607 r57026 601 601 602 602 /** 603 * Tests registering a block using arguments instead of a block.json file. 604 * 605 * @ticket 56865 606 * 607 * @covers ::register_block_type_from_metadata 608 */ 609 public function test_register_block_type_from_metadata_with_arguments() { 610 $result = register_block_type_from_metadata( 611 '', 612 array( 613 'api_version' => 2, 614 'name' => 'tests/notice-from-array', 615 'title' => 'Notice from array', 616 'category' => 'common', 617 'icon' => 'star', 618 'description' => 'Shows warning, error or success notices… (registered from an array)', 619 'keywords' => array( 620 'alert', 621 'message', 622 ), 623 'textdomain' => 'notice-from-array', 624 ) 625 ); 626 627 $this->assertInstanceOf( 'WP_Block_Type', $result, 'The block was not registered' ); 628 $this->assertSame( 2, $result->api_version, 'The API version is incorrect' ); 629 $this->assertSame( 'tests/notice-from-array', $result->name, 'The block name is incorrect' ); 630 $this->assertSame( 'Notice from array', $result->title, 'The block title is incorrect' ); 631 $this->assertSame( 'common', $result->category, 'The block category is incorrect' ); 632 $this->assertSame( 'star', $result->icon, 'The block icon is incorrect' ); 633 $this->assertSame( 634 'Shows warning, error or success notices… (registered from an array)', 635 $result->description, 636 'The block description is incorrect' 637 ); 638 $this->assertSameSets( array( 'alert', 'message' ), $result->keywords, 'The block keywords are incorrect' ); 639 } 640 641 /** 642 * Tests that defined $args can properly override the block.json file. 643 * 644 * @ticket 56865 645 * 646 * @covers ::register_block_type_from_metadata 647 */ 648 public function test_block_registers_with_args_override() { 649 $result = register_block_type_from_metadata( 650 DIR_TESTDATA . '/blocks/notice', 651 array( 652 'name' => 'tests/notice-with-overrides', 653 'title' => 'Overriden title', 654 'style' => array( 'tests-notice-style-overridden' ), 655 ) 656 ); 657 658 $this->assertInstanceOf( 'WP_Block_Type', $result, 'The block was not registered' ); 659 $this->assertSame( 2, $result->api_version, 'The API version is incorrect' ); 660 $this->assertSame( 'tests/notice-with-overrides', $result->name, 'The block name was not overridden' ); 661 $this->assertSame( 'Overriden title', $result->title, 'The block title was not overridden' ); 662 $this->assertSameSets( 663 array( 'tests-notice-editor-script' ), 664 $result->editor_script_handles, 665 'The block editor script is incorrect' 666 ); 667 $this->assertSameSets( 668 array( 'tests-notice-style-overridden' ), 669 $result->style_handles, 670 'The block style was not overridden' 671 ); 672 $this->assertIsCallable( $result->render_callback ); 673 } 674 675 /** 676 * Tests that when the `name` is missing, `register_block_type_from_metadata()` 677 * will return `false`. 678 * 679 * @ticket 56865 680 * 681 * @covers ::register_block_type_from_metadata 682 * 683 * @dataProvider data_register_block_registers_with_args_override_returns_false_when_name_is_missing 684 * 685 * @param string $file The metadata file. 686 * @param array $args Array of block type arguments. 687 */ 688 public function test_block_registers_with_args_override_returns_false_when_name_is_missing( $file, $args ) { 689 $this->assertFalse( register_block_type_from_metadata( $file, $args ) ); 690 } 691 692 /** 693 * Data provider. 694 * 695 * @return array[] 696 */ 697 public function data_register_block_registers_with_args_override_returns_false_when_name_is_missing() { 698 return array( 699 'no block.json file and no name argument' => array( 700 'file' => '', // No block.json file. 701 'args' => array( 702 'title' => 'Overriden title', 703 'style' => array( 'tests-notice-style-overridden' ), 704 ), 705 ), 706 'existing file and args not an array' => array( 707 // A file that exists but is empty. This will bypass the file_exists() check. 708 'file' => DIR_TESTDATA . '/blocks/notice/block.js', 709 'args' => false, 710 ), 711 'existing file and args[name] missing' => array( 712 // A file that exists but is empty. This will bypass the file_exists() check. 713 'file' => DIR_TESTDATA . '/blocks/notice/block.js', 714 'args' => array( 715 'title' => 'Overriden title', 716 'style' => array( 'tests-notice-style-overridden' ), 717 ), 718 ), 719 ); 720 } 721 722 /** 603 723 * Tests that the function returns the registered block when the `block.json` 604 724 * is found in the fixtures directory.
Note: See TracChangeset
for help on using the changeset viewer.