2026年9月29日

2026年9月29日

WordPressのGutenbergブロックエラーを解決する方法

はじめに

WordPressのブロックエディタで「このブロックにはエラーが含まれており、回復できません」というBlock recovery errorが出る・register_block_type()でカスタムブロックを登録したのに挿入メニューに表示されない・block.jsonのattributesが保存されない・InnerBlocksを使ったブロックが正しくレンダリングされない・フロントエンドでブロックのスタイルが適用されないといった問題は、ブロック登録の方法とJavaScript・PHPの連携を正しく設定することで解決できます。

症状・原因

  • block.jsonのファイルパスがregister_block_type()の引数と一致していない
  • JavaScriptビルドが完了していないか@wordpress/scriptsでのビルドが失敗している
  • ブロックのedit関数とsave関数の出力が一致しないためBlock recovery errorが発生する
  • view_scriptに指定したスクリプトがフロントエンドで正しくエンキューされていない

解決手順

ステップ1:ブロックエラーを診断する

# 登録済みブロックを確認
wp eval "
\$blocks = WP_Block_Type_Registry::get_instance()->get_all_registered();
foreach (array_keys(\$blocks) as \$name) {
    echo \$name . PHP_EOL;
}
" | grep my-plugin

# ブロックの詳細情報を確認
wp eval "
\$block = WP_Block_Type_Registry::get_instance()->get_registered('my-plugin/my-block');
if (\$block) {
    echo 'editor_script: ' . implode(', ', (array)\$block->editor_script_handles) . PHP_EOL;
    echo 'style: '         . implode(', ', (array)\$block->style_handles) . PHP_EOL;
}
"

# JSビルドエラーを確認
cd /path/to/plugin && npm run build 2>&1 | tail -20

ステップ2:block.jsonとPHP登録を正しく設定する

// block.json
{
    "$schema": "https://schemas.wp.org/trunk/block.json",
    "apiVersion": 3,
    "name": "my-plugin/my-block",
    "version": "1.0.0",
    "title": "マイブロック",
    "category": "text",
    "icon": "smiley",
    "description": "カスタムブロックの説明",
    "supports": {
        "html": false,
        "color": { "background": true, "text": true },
        "spacing": { "padding": true }
    },
    "attributes": {
        "content": { "type": "string", "default": "" },
        "alignment": { "type": "string", "default": "left" }
    },
    "editorScript": "file:./index.js",
    "editorStyle":  "file:./index.css",
    "style":        "file:./style-index.css",
    "viewScript":   "file:./view.js"
}
// plugin.php: block.json があるディレクトリを指定するだけ
add_action('init', function(): void {
    // block.json のディレクトリを渡す(ファイル名は不要)
    register_block_type(__DIR__ . '/build');
});

ステップ3:edit関数とsave関数を正しく実装する

// src/index.js
import { registerBlockType } from '@wordpress/blocks';
import { useBlockProps, RichText } from '@wordpress/block-editor';
import metadata from './block.json';

registerBlockType(metadata.name, {
    edit({ attributes, setAttributes }) {
        const blockProps = useBlockProps();
        return (
            <div {...blockProps}>
                <RichText
                    tagName="p"
                    value={attributes.content}
                    onChange={content => setAttributes({ content })}
                    placeholder="テキストを入力..."
                />
            </div>
        );
    },

    // save 関数は静的HTMLを返す(変更するとBlock recovery errorの原因に)
    save({ attributes }) {
        const blockProps = useBlockProps.save();
        return (
            <div {...blockProps}>
                <RichText.Content tagName="p" value={attributes.content} />
            </div>
        );
    },
});

ステップ4:Block recovery errorを修正する

// save関数の出力を変更した場合はdeprecatedを追加する
registerBlockType(metadata.name, {
    // ... edit関数

    save({ attributes }) {
        // 新しいsave関数(v2)
        const blockProps = useBlockProps.save({ className: 'my-block-v2' });
        return <div {...blockProps}><p>{attributes.content}</p></div>;
    },

    deprecated: [
        {
            // 旧バージョンのsave関数(v1)
            save({ attributes }) {
                return <div className="my-block"><p>{attributes.content}</p></div>;
            },
            // 必要に応じてマイグレーション処理
            migrate(attributes) {
                return attributes;
            },
        },
    ],
});
# Block recovery errorを一括修正(コンテンツに影響がない場合)
wp post list --post_type=post --format=ids | xargs -I{} \
    wp post update {} --post_content="$(wp post get {} --field=post_content | \
    sed 's/<!-- wp:my-plugin\/old-block/<!-- wp:my-plugin\/my-block/g')"

ステップ5:動的ブロック(PHP render)を実装する

// server-side rendering: save関数不要でPHPでレンダリング
add_action('init', function(): void {
    register_block_type(__DIR__ . '/build', [
        'render_callback' => 'render_my_block',
    ]);
});

function render_my_block(array $attributes, string $content): string {
    $content_text = esc_html($attributes['content'] ?? '');
    $alignment    = esc_attr($attributes['alignment'] ?? 'left');

    $wrapper_attrs = get_block_wrapper_attributes([
        'class' => "align-{$alignment}",
    ]);

    return "<div {$wrapper_attrs}><p>{$content_text}</p></div>";
}
// 動的ブロックの edit 関数(save は null を返す)
registerBlockType(metadata.name, {
    edit({ attributes, setAttributes }) {
        // 編集UIのみ
        return <div>...</div>;
    },
    save() {
        // 動的ブロックは null を返す
        return null;
    },
});

注意事項

  • save関数の出力を変更した場合、既存の投稿にあるブロックはBlock recovery errorになります。deprecated配列に旧バージョンのsave関数を必ず追加してください
  • @wordpress/scriptsでビルドする場合、npm run start(開発)とnpm run build(本番)を正しく使い分けてください。startはsource mapあり・未圧縮、buildは最適化済みです

まとめ

Gutenbergブロックエラーの解決は①WP_Block_Type_Registryで登録済みブロック確認・npm run buildのエラーを確認・ブロックのhandle名を確認、②block.jsonに$schema/name/attributes/editorScript/styleを設定・register_block_type(__DIR__ . '/build')でディレクトリを指定、③editでRichTextを使って編集UI・saveで静的HTML出力・useBlockPropsでWP標準属性を付与、④save関数変更時はdeprecated配列に旧save関数を追加・migrate()でデータ変換・CLIで既存コンテンツを一括修正、⑤動的ブロックはrender_callbackでPHPレンダリング・saveはnullを返す・get_block_wrapper_attributes()でWP標準属性を出力の手順で解決します。

お気軽にご相談ください

お見積りへ お問い合わせへ
▲