デバッグモードをON(true)にしていると表示される「Warning: Undefined array key “〇〇” in…」という警告。何かの配列を取得した際に存在しないkeyがありますよ!という警告です。

実際にこの状況が発生しないと出ないので、長く同じコードで運営していて今まで大丈夫だったのに..となることが多いのも特徴です。

また、この警告はPHP8.0以降で厳格化されたルールに基づいているので、PHPバージョンの変更後に突然発生するので、自動的にPHPバージョンが更新されるようなレンタルサーバーで運営しているサイトでは、突然..と感じるかも知れません。

警告表示なので即座にプログラム(サイト)が停止してしまうものではないので、表示を停止してしまうというのも1つの方法ではあるものの、PHPバージョンが上がるにつれてより厳格になっていきますので、早めに対処したほうがよいかも知れません。

「Warning: Undefined array key “〇〇” in…」への一般的な対処

対処としては「未定義のものを除く」ことですから、issetを使って「存在するか」を判別することで、ほとんどの場合は対処が可能です(コードによっては別の方法を取る必要がある場合もあります)。

具体的には、

$ua = $_SERVER['HTTP_USER_AGENT'];

というような、ユーザーエージェントを取得して、$uaという変数に格納しようとしたとき、未定義のユーザーエージェントがあった場合に警告表示されるので、以下のようにすることで解消できます。

if(isset($_SERVER['HTTP_USER_AGENT'])){
	$ua = $_SERVER['HTTP_USER_AGENT'];
}

PHP8.0で空や未定義のものに対する処理が厳格化されたことによるものなので、使用しているプラグインで発生した場合には作者へ知らせてあげる、自作プラグインやどこかからコピーして実装したコードであれば、該当箇所のコードをよく見て修正すればよいでしょう。

メタボックスからカスタムフィールドの値を更新する処理の具体例

投稿や固定ページへカスタムフィールドの値を設定するメタボックス(入力窓)を設け、そこに入力した値を更新させる処理で「Warning: Undefined array key “〇〇” in…」の警告が出ることがあります。

以下が私が実際に対処したコードの例です。この処理は、多分同じようなコードで処理していると思いますので参考になれば幸いです。

PHP8.0よりも前のバージョンで大丈夫だったコード例

「is_nofollow」というメタキーに対して、

  • メタボックスに入力があり、カスタムフィールドの値がなかったら入力された値で更新
  • メタボックスに入力がなく、カスタムフィールドの値があったらカスタムフィールドを削除

という処理をするものです。PHP8.0までは以下の記述で大丈夫でした。

//Nofollowの更新
if(!empty($_POST['is_nofollow'])){
	update_post_meta($post_id, 'is_nofollow', $_POST['is_nofollow'] );
}else{
	delete_post_meta($post_id, 'is_nofollow', $_POST['is_nofollow']);
}

PHP8.0以降のバージョンでも大丈夫なコード例

配列の中でキーが定義されていないというのが「Warning: Undefined array key “〇〇” in…」の原因なので、issetを用いてキーの存在有無を判断させます。

キーの存在判断

「$_POST[‘is_nofollow’]」というキーが存在したらそのキーに対して、そうでなかったら何もなかったことにして..という判断をして、$is_nofollowという変数に格納します(存在有無を確定します)

if(isset($_POST['is_nofollow'])){
	$is_nofollow = $_POST['is_nofollow'];
}else{
	$is_nofollow = '';
}

更新処理の変更

$is_nofollow(メタキーがある場合はそのメタキー、ない場合は空)に対して、メタボックスに入力した値があれば更新、なければ削除という処理をします。

if(!empty($is_nofollow)){
	update_post_meta($post_id, 'is_nofollow', $is_nofollow );
}else{
	delete_post_meta($post_id, 'is_nofollow', $is_nofollow);
}

両方を組み合わせて、以下がセットになりますね。

if(isset($_POST['is_nofollow'])){
	$is_nofollow = $_POST['is_nofollow'];
}else{
	$is_nofollow = '';
}

if(!empty($is_nofollow)){
	update_post_meta($post_id, 'is_nofollow', $is_nofollow );
}else{
	delete_post_meta($post_id, 'is_nofollow', $is_nofollow);
}

処理全体をissetで判断させる方法もあるけど...

処理を分けずに、以下のように書くこともできます。

if(isset($_POST['is_nofollow'])){
	if(!empty($_POST['is_nofollow'])){
		update_post_meta($post_id, 'is_nofollow', $_POST['is_nofollow'] );
	}else{
		delete_post_meta($post_id, 'is_nofollow', $_POST['is_nofollow']);
	}
}

一応これでも、PHPの警告自体は出なくなります。

が、テキスト入力では上記コードで問題なく動作するものの、チェックボックスやセレクトボックス、ラジオボタンなどでは、削除側の処理がされず、チェックを外したのに更新したらチェックが入ったままという状態になってしまうことがあるので、実際にテストをして確実に処理されるかを確認しましょう。


PHP8.0以降に切り替えたら今回のような警告が出るケースは他にもいろいろとありますが、それらはすべてPHP8.0で「ない場合の処理を確実に書く」ことに対して厳格になったものですので、警告が出たら、ひとまずif(…)を使う場合にきちんとないもの処理がされているかを確認して対処すれば大丈夫です。

もちろんプログラムを書き換えたらチェックとテストをお忘れなく!


最後に補足として、WordPressを普通に使っていて、突然このようなメッセージが出た!なんとかしなきゃ!と思っている方、そもそもその表示が出てしまうことが問題かも知れませんから、以下のページを参考にしてみてください。