カスタムブロックの更新時に何かするときのメモ

繰り返し使うカスタムブロックにおいて、以前の属性(設定)を読み出すような仕組みを実装できないか考えた。当初は編集中に属性が変わったことをuseEffectで捉え、その度に独自のREST APIで更新していたが、この方法では更新頻度が多くなり、更新頻度を少なくする方法を検討してみた。

更新頻度を下げるには

useEffectよりも更新頻度を下げるために思いついたのが、投稿を更新するタイミング。このタイミングで確実に処理できるのがベストと思い、ChatGPTに『WordPressのカスタムブロックで投稿の「更新」時に何らかの処理を行う場合はどうすれば良いでしょうか。』と質問してみた。

少しやりとりしながら教えてもらったJavaScript部分は以下のような内容だった(要所に空白を入れたもの)。

const { subscribe } = wp.data;

let lastIsSavingPost = wp.data.select( 'core/editor' ).isSavingPost();

subscribe( () => {
	const isSavingPost = wp.data.select( 'core/editor' ).isSavingPost();
	const isAutosavingPost = wp.data.select( 'core/editor' ).isAutosavingPost();
	if ( lastIsSavingPost && ! isSavingPost && ! isAutosavingPost ) {
		const blocks = select( 'core/block-editor' ).getBlocks();
		blocks.forEach( block => {
			if ( 'ブロック名' === block.name ) {

				// 処理

			}
		} );
	}
	lastIsSavingPost = isSavingPost;
} );

1行目の記述が見慣れなかったので、ちょっと質問したところ『古いバージョンのWordPress Gutenbergで使用されていた方法です。』とのこと。今は次のような記述で問題ないらしい。

import { subscribe, select } from '@wordpress/data';

上記のコードのポイントが、subscribe。さまざまな状態が変化するたびに呼び出されるリスナー関数を登録している。そしてリスナー関数内では次のメソッドを使って状態を判別している。

  • isSavingPost()
    投稿が保存中の場合はtrue
  • isAutosavingPost()
    投稿が自動保存中の場合はtrue

ここでわからなかったのが、直接isSavingPost()の返り値を比較せずに一旦lastIsSavingPostに保存。リスナー関数が次回以降呼び出されたタイミングで目的の処理を行うようになっていること。気になったので、isAutosavingPost()の後に次の1文を追加する。

console.log( lastIsSavingPost, isSavingPost, isAutosavingPost );

プラグインをビルドし、投稿編集画面で「更新」ボタンを押す。コンソールには次のようなログが流れた。

false false false
false false false
false true false
true true false
true true false
true true false
true false false
false false false
false false false
false false false

真ん中のisSavingPostの値は4回連続でtrueになっており、このことを考慮してlastIsSavingPostに保存し、次回以降で投稿の保存完了を判定してるようだ。

またログを見ながらisAutosavingPost()の判定は不要だと思ったので、最終形は次のようにした。

import { subscribe, select } from '@wordpress/data';

let lastIsSavingPost = false;

subscribe( () => {
	const isSavingPost = select( 'core/editor' )?.isSavingPost();
	if ( lastIsSavingPost && ! isSavingPost ) {
		const blocks = select( 'core/block-editor' ).getBlocks();
		blocks.forEach( block => {
			if ( 'ブロック名' === block.name ) {

				// 処理

			}
		} );
	}
	lastIsSavingPost = isSavingPost;
} );

これにより、投稿の更新時にカスタムブロックの設定内容を保存できた。ChatGPTと対話と動作確認を繰り返し、意図したように動作できるようになるのはいい。

【更新】2024.07.13 select( 'core/editor' )の後に「?」を追加し、限定的な状況でのエラーに対応。


最終更新 : 2024年07月13日 16:06

お勧め

add_shortcode(2018年5月27日 更新)

void add_shortcode( string $tag, mixed $func )
ショートコード(独自タグ)を追加する。ショートコードは、投稿記事内でテキスト内容がない[tag]や、テキストを内包する[tag]テキスト[/tag]の書式で使用できる独自タグのこと。標準の状態では、 the_content関数によって表示する直前のフィルター処理内でパラメータ$funcで指定した関数・メソッドが実行される。

get_user_setting(2022年1月31日 更新)

mixed get_user_setting( string $name [ , string $default = false ] )
ユーザーインターフェイス設定を取得する。

have_posts(2018年5月27日 更新)

bool have_posts( )
次の投稿データが存在するかを調べる。

in_category(2018年5月27日 更新)

bool in_category( mixed $category [ , mixed $post = null ] )
投稿情報が指定したカテゴリーに属しているか調べる。

add_feed(2024年6月24日 更新)

string add_feed( string $feedname, callable $callback )
フィードを追加する。