TL;DR: 10秒でできる解決策
ほとんどの場合、このエラーは関数内でグローバルなデータベース変数を参照するように指示するのを忘れているために発生します。通常、1行追加するだけで即座に解決します。
function get_my_data() {
global $wpdb; // これが不足している記述です
return $wpdb->get_results("SELECT * FROM {$wpdb->prefix}options WHERE option_name = 'siteurl'");
}
コードがクラッシュする理由
PHPは非常に率直です。「nullに対して関数を呼び出すことはできない」というエラーは、使用している変数(この場合は $wpdb)が現在空であることを意味します。これは、鍵を持っていないのに車を始動させようとするようなものです。WordPressにおいて、$wpdb は MySQL データベースへの主要な架け橋です。渡る前にその橋が構築されていなければ、スクリプトは失敗します。
このエラーが発生する主な原因は以下の3つです。
- **変数のスコープ:** 関数が独自のバブルの中にあり、`$wpdb` がグローバルに存在することを知りません。
- **タイミングの誤り:** WordPressがコアデータベースファイルの読み込みを完了する前に、クエリを実行しています。
- **孤立したスクリプト:** カスタムの `.php` ファイルを作成したが、WordPressの実行環境を読み込んでいません。
修正方法
1. $wpdb をスコープ内に入れる
PHPの関数は設計上、隔離されています。たとえWordPressが開始時に $wpdb を定義していても、明示的に取り込まない限り、特定の関数内から参照することはできません。これは、プラグインやテーマのエラーの約90%で見られる原因です。
間違った方法:
function fetch_user_count() {
$count = $wpdb->get_var("SELECT COUNT(*) FROM $wpdb->users"); // エラー: ここでは $wpdb は null です
}
正しい方法:
function fetch_user_count() {
global $wpdb;
$count = $wpdb->get_var("SELECT COUNT(*) FROM $wpdb->users");
return $count;
}
2. 読み込み順序を守る
WordPressには厳格な起動シーケンスがあります。functions.php の最上部などで、フック(hook)を使わずにデータベースクエリを直接記述すると、高確率で失敗します。その時点では $wpdb オブジェクトがまだ生成されていないからです。
常にWordPressの準備が整うのを待ってください。データベースを操作する前に、環境が安定していることを保証するために init や plugins_loaded フックを使用してください。
add_action('plugins_loaded', function() {
global $wpdb;
// ここでクエリを実行するのが安全です
$results = $wpdb->get_results("SELECT * FROM {$wpdb->prefix}posts LIMIT 5");
});
3. 外部スクリプトのセットアップ
WordPressのフォルダ構造の外で、スタンドアロンの移行スクリプトやカスタムAPIエンドポイントを実行している場合、デフォルトでは $wpdb は存在しません。手動でWordPressのコアを読み込む必要があります。スクリプトで wp-load.php を読み込むように指定してください。このファイルは、すべてのWordPress関数と変数へのゲートウェイとして機能します。
<?php
// スクリプトの場所に合わせてパスを調整してください
require_once( __DIR__ . '/wp-load.php' );
global $wpdb;
$user_count = $wpdb->get_var("SELECT COUNT(*) FROM $wpdb->users");
echo "ユーザー総数: " . $user_count;
?>
4. クラスでの利用
クラス内で global を使用することは一般的ですが、コードが乱雑になる可能性があります。より洗練されたアプローチは、クラスのコンストラクタに $wpdb を渡すことです。これにより、コードのテストが容易になり、可読性も向上します。
class MyPluginHandler {
private $db;
public function __construct($database_object) {
$this->db = $database_object;
}
public function get_data() {
return $this->db->get_results("SELECT * FROM my_table");
}
}
// 使い方
global $wpdb;
$my_handler = new MyPluginHandler($wpdb);
正常に動作しているか確認する方法
単にページを更新して解決を祈るだけでは不十分です。wp-content/debug.log ファイルを開いてください。スコープの問題が解決していれば、Fatal error のログは表示されなくなるはずです。また、オブジェクトを使用する前に存在を確認する簡単なチェックを追加することもできます。これにより、将来何か問題が発生しても、サイト全体のクラッシュを防ぐことができます。
global $wpdb;
if (!isset($wpdb)) {
error_log('データベースオブジェクトが見つかりません!');
return;
}
$data = $wpdb->get_results("...");

