WordPress公式のdeprecated(非推奨)チュートリアルページを日本語で訳してみた

投稿日:2024年10月30日(水)
WordPress公式のdeprecated(非推奨)チュートリアルページを日本語で訳してみた|UMENOKI|すぐに仕事で使えるIT技術情報メディア

みなさんこんにちは!エンジニアの高澤です!

今回はWordPress公式のdeprecated(非推奨)チュートリアルページを日本語で訳してみた!という内容でチュートリアルページをご紹介したいと思います。

WordPress公式のdeprecated(非推奨)チュートリアルとは

WordPress公式のdeprecated(非推奨)チュートリアルとは、下図の公式サイトにて公開されている開発者向けのページのことをいいます。

以下がページのURLになります。クリックしてご確認ください。

当記事では、こちらのチュートリアルページの内容を筆者が日本語訳してみた、という内容の記事となっております。ちなみに翻訳ツールとしてはChatGPTを利用しております。

少し読みやすいようにアレンジしている箇所がありますが、意味が違ってしまうことが極力注意しつつ編集しておりますので、ご安心いただければと思います。

もし何か翻訳や内容に間違いがありましたら、お気軽にお問い合わせにてご指摘内容をお送りいただければと思います。

deprecated(非推奨)チュートリアル

それでは早速、WordPressのブロック開発におけるdeprecated(非推奨)チュートリアルを始めます。

まず以下の状況を考えてみてください。

静的なブロックを実装するプラグインを作成し、WordPressのプラグインディレクトリに公開しました。そのブロックはすでに数百のウェブサイトで使われていますが、さらに良くするアイデアを思いつきました。しかし、今になって変更を加えるとなると問題が出てきます。

もう一つ状況を考えてみましょう。

クライアントから連絡があり、サイト用に開発したカスタムブロックにいくつかの変更を加えてほしいと依頼されました。しかしそのブロックは、サイト内の様々なページや投稿で数十、もしくは数百回も使われている静的なブロックです。これもまた、対応が難しい状況です。

なぜこれらの状況がブロック開発者にとって問題になるのでしょうか?

静的ブロックに変更を加えると、特にsave()関数に変更を加えた場合(この関数は、データベースに保存されフロントエンドで表示される内容を決定します)、後ほどブロックエディタを開いた時に「このブロックには予期しない、または無効なコンテンツが含まれています」というエラーメッセージが表示される可能性が高くなります。

画像引用元:developer.wordpress.org

この問題が発生する理由は、以前のバージョンでブロックが保存したコンテンツの構造が、新しいバージョンで保存する構造と一致しなくなるためで、その結果、ブロック検証エラーが発生するからです。

このエラーはブロック開発中によく見られるもので、ブロック開発者にとっては慣れた問題ですが、普通のユーザーがこれを目にすると、何かが壊れたのではと感じてしまうでしょう。

もしブロックに変更を加えると、ブロックエディタにてサイト運営者がこの検証エラーを目にすることになり、このエラーを解除するためには、追加してある各ブロックごとに「ブロックの回復を試みる」ボタンを押して壊れたブロックを修復する必要があります。

つまり、最初の状況では数百人のユーザーに迷惑をかけるリスクがあり、2つ目の状況ではクライアントや、そのサイトのコンテンツエディター(ブロックエディタ)に大きな負担をかけるリスクがあります。彼らはサイト全体を見直して、変更されたすべてのブロックを回復しなければならなくなります。

では、どうすればいいのでしょうか?クライアントに変更できないと伝えますか?それとも、静的ブロックを動的ブロックに変更しますか?あるいは、新しい別バージョンのブロックを作成し、ユーザーに新しいバージョンを使ってもらいますか?

いいえ、もちろんそんな必要はありません!

解決策 – ブロックの非推奨(deprecate)設定を実装する

その解決策としては、「ブロックの非推奨(deprecate)設定を実装する」という方法があります。

これは、古いバージョンのブロックを「非推奨(deprecated)」として扱うことをいいます。

非推奨設定を使うと、古いバージョンのブロックを使っている部分に対して、問題が起きないように適切な代わりの処理を用意できます。つまり、古いバージョンのブロックをそのまま使っている場合でも、新しいバージョンにうまく切り替えられるようにすることができるということです。

この方法により、コンテンツエディターは「このブロックには予期しない、または無効なコンテンツが含まれています」というエラーメッセージを目にすることはなく、ページや投稿を更新する際に新しいバージョンがデータベースに保存され、古いバージョンの内容が置き換えられます。

同じように、新しいブロックを作成するときも、最新の内容がきちんと保存されるようになります。つまり、古いバージョンのブロックではなく、新しいバージョンの設定が反映されるということです。

ブロックの非推奨設定の方法を詳しく説明する前に、この問題の範囲について少し考えてみましょう。

ちなみにこのエラーメッセージが表示されてしまう問題は、静的ブロックにのみ発生し、またエディターでのみ発生します。

静的ブロックには save() 関数があり、コンテンツが投稿に保存されます。この保存されたコンテンツは検証の対象となります。一方、動的ブロックには save() 関数がなく、コンテンツがリアルタイムでレンダリングされるため、データベースには保存されず、検証の対象にはなりません。

したがって、動的ブロックでは「このブロックには予期しない、または無効なコンテンツが含まれています」というエラーメッセージが表示されることはありません。動的ブロックの詳細や、静的ブロックとの違い、使い分けについては、Joni Halabiの関連記事をご覧ください。

また、この問題はエディター内だけ発生するものであり、フロントエンドには影響がありません。ウェブサイトのフロントエンドを閲覧する人は、データベースの wp_posts テーブルに保存されている内容をそのまま閲覧することができ、古いバージョンで保存されていたとしても、新しいバージョンで更新されていない限り影響を受けません。

それでは、ブロックの非推奨(deprecated)設定の例をいくつか見ていきましょう。

ブロックの非推奨設定 – シンプルな例

新しいブロックプラグインを @wordpress/create-block を使って作成します。

npx @wordpress/create-block deprecation-example

次に、WordPressの管理画面で新しいプラグインを有効化し、このブロックを使った投稿を作成します。

エディター上では次のような内容が表示されます:

画像引用元:developer.wordpress.org

フロントエンドでは次のように表示されます:

画像引用元:developer.wordpress.org

では、ブロックに変更を加えてみましょう。まず、wp-content/plugins/deprecation-example ディレクトリ内で npm start を実行することを忘れないでください。このチュートリアルでの変更はすべて src ディレクトリ内のファイルに行います。

save.js ファイルの save() 関数で返されるコンテンツを変更します。例えば、21行目を次のように変更します:

変更前:

◾️save.js

{ 'Deprecation Example – hello from the saved content!' }

変更後:

◾️save.js

{ 'Deprecation Example – hi from the saved content!' }

ファイルを保存し、エディターとフロントエンドでページを再読み込みしてください。

ご確認いただくとお分かりかと思いますが、フロントエンドでは変化が無いかと思います。フロントエンドはあくまでデータベースに保存されている内容をレンダリングするだけなので、データベースの内容が変更されない限り表示も変わらないからです。

しかし、エディターでは「このブロックには予期しない、または無効なコンテンツが含まれています」というエラーが表示されます。

また、ブラウザのコンソールを確認すると、次のようなエラーメッセージが表示されているかと思います。

画像引用元:developer.wordpress.org

このエラーが表示されるのは、save() 関数の変更によって、データベースに保存されたブロックの構造と新しい構造が一致しなくなったためです。

ただここで「ブロックの復旧を試みる」ボタンをクリックして復旧しようとするのはちょっと待ってください!代わりに、ブロックを非推奨(deprecated)の実装をおこない問題を解決しましょう。

まず、src ディレクトリに deprecated.js というファイルを作成します。このファイル内に v1 という定数を定義し、以前のバージョンの save() 関数を含むオブジェクトを代入します。

◾️deprecated.js

const v1 = {
  save() {
    return (
      <p { ...useBlockProps.save() }>
        { 'Deprecation Example – hello from the saved content!' }
      </p>
    );
  }
}

このようにして、v1 定数に以前の save() 関数を保持することで、古いバージョンのブロックがある場合に適切に処理されるようにします。

deprecated.js ファイルで useBlockProps フックを使用しているため、それも deprecated.js にインポートする必要があります。

◾️deprecated.js

// src/deprecated.js
import { useBlockProps } from '@wordpress/block-editor';

const v1 = {
  save() {
    return (
      <p { ...useBlockProps.save() }>
        { 'Deprecation Example – hello from the saved content!' }
      </p>
    );
  }
}

export default [v1];

次に、index.js にこの配列をインポートし、registerBlockType 関数に渡す設定オブジェクトに deprecated プロパティとして指定します。

◾️index.js

// src/index.js
import deprecated from './deprecated';

registerBlockType(metadata.name, {
  edit: Edit,
  save,
  deprecated,
});

変更したファイルを保存し、ブロックエディタでページを再読み込みすると、ブロックの検証エラーが消えるはずです。

また、投稿を更新すると(新しいブロックを追加するかページに何らかの変更を加える必要がある場合があります)、フロントエンドには新しいバージョンのコンテンツが表示されます。

これが、ブロックの非推奨設定(デプリケーション)の効果です。サイト運営者はコンテンツエディターのブロックに変更が加えられたことにまったく気づかずに使用できるのです。

では、ここで行われた処理の内容を説明いたします。ブロックエディターが保存されたコンテンツが save() 関数によって生成されるバージョンと一致しないことを判断したとき、registerBlockType() 関数に渡されたブロック設定オブジェクトの deprecated プロパティを探します。

その後、deprecated 配列(現在は1つだけですが)内のオブジェクトを順番に確認し、保存されたコンテンツと一致する save() 関数を持つものを探します。

それが見つかると、エディター内でブロックをパースするために使用され、投稿やページが更新される際に新しいバージョンがデータベースに保存されるようになります。

attributesオブジェクトを使った実装

次に、もう少し複雑な例を試してみましょう。まず、block.jsonattributes オブジェクトを追加し、その中に text プロパティを追加します。

◾️block.json

"attributes": {
  "text": {
    "type": "string",
    "source": "html",
    "selector": "p",
    "default": "Deprecation Test"
  }
}

これによって、テキストが固定されたものではなく、ユーザーが自由に設定できるようになります。ユーザーが設定できるようにするためには、edit.jsを変更する必要があります。

まず、edit.jsRichText コンポーネントをインポートします。

◾️edit.js

import { useBlockProps, RichText } from '@wordpress/block-editor';

次に、Edit() 関数を更新して、RichText コンポーネントを使用できるようにします。

◾️edit.js

export default function Edit( { attributes, setAttributes } ) {

  const onChangeContent = ( val ) => {
    setAttributes( { text: val } )
  }

  return (
    <RichText { ...useBlockProps() }
      tagName="p"
      onChange={ onChangeContent }
      value={ attributes.text }
      placeholder="Enter text here..."
    />
  );
}

関数のパラメーターリストに attributessetAttributes を分解して設定することを忘れないでください。setAttributes は、onChange 関数内でテキスト属性を更新するために使用されます。

これでテキストは編集可能になりました。エディタからブロックを選択して確認してみてください。

次は重要なステップです。 前のバージョンを非推奨にして、save.js を更新します。

deprecated.js に新しい定数 v2 を追加し、その値を現在の save() 関数を含むオブジェクトに設定します。

◾️deprecated.js

const v2 = {
  save() {
    return (
      <p { ...useBlockProps.save() }>
        { 'Deprecation Example – hi from the saved content!' }
      </p>
    );
  }
}

次に、save.jsRichText コンポーネントをインポートします。

◾️save.js

import { useBlockProps, RichText } from '@wordpress/block-editor';

そして、save() 関数を更新します。

◾️save.js

export default function save( { attributes } ) {
  return (
    <RichText.Content { ...useBlockProps.save() }
      tagName="p"
      value={ attributes.text }
    />
  );
}

最後に、deprecated.js でエクスポートされる配列に v2 定数を追加します。

◾️deprecated.js

export default [ v2, v1 ];

配列の最初に最新の修正を置くことはベストプラクティスであり、決まりごとといっても過言ではありません。

配列は最初の要素から順に解析され、一致するバージョンが見つかるまで続けられるため、最新の非推奨版を最初に試すことができます。

一般的に言えば、最新の非推奨版が一致する可能性が最も高いため、配列の最初に配置することで、一致する可能性が低い非推奨版を無駄に処理することを避けることができます。

attributesオブジェクトの属性の移行(マイグレーション)

次に、ブロックの変更時によく必要となる作業である属性の移行(マイグレーション)について見てみましょう。

現在、ブロックには「text」という属性がありますが、テキストは別の目的に使用する予定なので、新しいバージョンでは「content」という属性名を使いたいと考えています。また、「content」という名前は、ブロックの内容を表すにはより適した名前であるといえます。

ここで最初にするべきことは、現在のsave()関数のバージョンのコピーをdeprecated.jsに流用して作成することです。新しい定数v3を追加し、その値を最新のsave()関数を含むオブジェクトに設定します。

◾️deprecated.js

const v3 = {
  save( { attributes } ) {
    return (
      <RichText.Content { ...useBlockProps.save() }
        tagName="p"
        value={ attributes.text }
      />
    );
  }
}

このバージョンでは RichText コンポーネントを使用するため、deprecated.js にも RichText をインポートする必要があります。

◾️deprecated.js

import { useBlockProps, RichText } from '@wordpress/block-editor';

次に、block.json で属性の名前を text から content に変更します。

◾️block.json

"attributes": {
  "content": {
    "type": "string",
    "source": "html",
    "selector": "p"
  }
}

次に、Edit() 関数と save() 関数の両方で text へのすべての参照を content に変更する必要があります。

以下は新しい Edit() 関数です。変更する参照が2つありますので、onChange ハンドラー内のものを忘れないようにしてください。

◾️edit.js

export default function Edit( { attributes, setAttributes } ) {

  const onChangeContent = ( val ) => {
    setAttributes( { content: val } )
  }

  return (
    <RichText { ...useBlockProps() }
      tagName="p"
      onChange={ onChangeContent }
      value={ attributes.content }
      placeholder="Enter text here..."
    />
  );
}

そしてこちらが新しい save() 関数で、変更する参照は1つだけです。

◾️save.js

export default function save( { attributes } ) {
  return (
    <RichText.Content { ...useBlockProps.save() }
      tagName="p"
      value={ attributes.content }
    />
  );
}

次に、deprecation が属性を認識し、新しい名前に移行できるようにする必要があります。v3 オブジェクトに、廃止される text 属性を持つ attributes プロパティを追加します。

◾️deprecated.js

attributes: {
  text: {
    type: 'string',
    source: 'html',
    selector: 'p',
  },
},

次に、渡されたオブジェクトから text 属性を分割代入して、migrate 関数を追加します。この関数は、以前の text の値を持つ新しい属性 content を返すようにします。

◾️deprecated.js

migrate( { text } ) {
  return {
    content: text,
  };
},

最終的に、ここまでで v3 オブジェクトは以下のようになります。

◾️deprecated.js

const v3 = {

  attributes: {
    text: {
      type: 'string',
      source: 'html',
      selector: 'p',
    },
  },

  migrate( { text } ) {
    return {
      content: text,
    };
  },

  save( { attributes } ) {
    return (
      <RichText.Content { ...useBlockProps.save() }
        tagName="p"
        value={ attributes.text }
      />
    );
  }

}

最後に、v3 オブジェクトを配列の先頭に追加します。

◾️deprecated.js

export default [ v3, v2, v1 ];

これで、エディタのページをリフレッシュすると、以前は text 属性にあったテキストが content 属性に移動していることが確認できます。ブロックをエディタで選択し、ブラウザのコンソールで次のコマンドを実行して確認できます。

wp.data.select( 'core/block-editor' ).getSelectedBlock().attributes
画像引用元:developer.wordpress.org

まとめ

要点を簡単にまとめると、registerBlockType() 関数に渡されるブロック構成オブジェクトには、deprecated プロパティを持たせることができます。

このプロパティには配列を値として指定します。この配列の各要素は、ブロックの旧バージョンを表すオブジェクトであり、各オブジェクトには以下のプロパティを含めることができます。

  • attributes
  • supports
  • save
  • migrate
  • isEligible

ブロックの非推奨に関する詳細情報や、この記事ではカバーしていない supports および isEligible プロパティについては、ブロックエディタのハンドブックにある非推奨ページを参照してください。

また、Gutenberg リポジトリにある非推奨ブロックの例を確認するのも良いアイデアです。カバーブロックdeprecated.js ファイルは、自分の非推奨をモデル化するのに良い例です。ボタン ブロックものも見てみてください。

こちらは読みづらいですが、各バージョンを定数に保存し、その定数をエクスポートされた配列に追加することがなぜ良いアイデアであるかを示しています。

そうすることで、コードがよりクリーンで読みやすくなり、将来的にさらに多くの非推奨を追加する際も簡単になります。

執筆者

UMENOKI編集部 高澤 翔汰

歴5年目(2024年8月以降から5年目です)のエンジニアです!
CMSでのサイト構築とWebデザイン制作を兼任して5年目になります。
自作のiOSアプリ(iPhoneアプリ)やWordPressプラグインを開発することもあり、まだまだ現在進行形で勉強中です!

お気軽に皆さんのご要望をお聞かせください!

どんなに些細なことでも構いません!よろしければ記事や当サイトへの「こんな記事があったら仕事とかで役に立つな〜」や「こうだったらもっと役に立つのに!」といったようなご要望等をお気軽にお聞かせください!今後のサービス改善にお役立てさせていただきます!

例1)Reactの技術記事を書いてほしい!
例2)WordPressの使い方とかを初心者向けに解説してほしい!...など

送信と同時にプライバシーポリシーに同意したものとします。
サンタさん