2026年5月20日
2026年5月20日
WordPressプラグインでメタボックスを追加する方法
はじめに
メタボックスはWordPress投稿編集画面に独自の入力欄を追加する機能です。ACFを使わずに、プラグインから直接メタボックスを追加してカスタムフィールドを管理する方法を解説します。
症状・原因
- 投稿編集画面に独自の入力フォームを追加したい
- ACFを使わずにカスタムフィールドを実装したい
- 特定の投稿タイプの編集画面だけにメタボックスを表示したい
- メタボックスで入力したデータを安全に保存したい
解決手順
ステップ1:メタボックスを登録する
// functions.php またはプラグインファイル
add_action('add_meta_boxes', function(): void {
add_meta_box(
'myplugin_product_info', // ID(ユニークな名前)
'商品情報', // タイトル
'myplugin_product_info_callback', // コールバック関数
'post', // 投稿タイプ(post/page/カスタム投稿)
'normal', // 表示位置(normal/side/advanced)
'high' // 優先度(high/default/low)
);
});
// 複数の投稿タイプに追加する場合
add_action('add_meta_boxes', function(): void {
foreach (['post', 'product', 'news'] as $post_type) {
add_meta_box(
'myplugin_seo_box',
'SEO設定',
'myplugin_seo_box_callback',
$post_type,
'normal',
'high'
);
}
});
ステップ2:メタボックスのHTMLを出力する
function myplugin_product_info_callback(\WP_Post $post): void {
// nonceフィールドを出力(CSRF対策)
wp_nonce_field('myplugin_save_product_info', 'myplugin_product_nonce');
// 既存の値を取得
$price = get_post_meta($post->ID, '_product_price', true);
$sku = get_post_meta($post->ID, '_product_sku', true);
$in_stock = get_post_meta($post->ID, '_product_in_stock', true);
?>
<table class="form-table">
<tr>
<th><label for="product_price">価格(円)</label></th>
<td>
<input type="number" id="product_price" name="product_price"
value="<?php echo esc_attr($price); ?>" min="0" step="1"
class="regular-text">
</td>
</tr>
<tr>
<th><label for="product_sku">SKU</label></th>
<td>
<input type="text" id="product_sku" name="product_sku"
value="<?php echo esc_attr($sku); ?>"
class="regular-text">
</td>
</tr>
<tr>
<th>在庫状況</th>
<td>
<label>
<input type="checkbox" name="product_in_stock" value="1"
<?php checked($in_stock, '1'); ?>>
在庫あり
</label>
</td>
</tr>
</table>
<?php
}
ステップ3:データを安全に保存する
add_action('save_post', function(int $post_id): void {
// 自動保存・nonce検証・権限チェック
if (wp_is_post_autosave($post_id) || wp_is_post_revision($post_id)) {
return;
}
$nonce = $_POST['myplugin_product_nonce'] ?? '';
if (!wp_verify_nonce($nonce, 'myplugin_save_product_info')) {
return;
}
if (!current_user_can('edit_post', $post_id)) {
return;
}
// 価格を保存(数値としてサニタイズ)
if (isset($_POST['product_price'])) {
update_post_meta($post_id, '_product_price', absint($_POST['product_price']));
}
// SKUを保存(テキストとしてサニタイズ)
if (isset($_POST['product_sku'])) {
update_post_meta($post_id, '_product_sku',
sanitize_text_field($_POST['product_sku']));
}
// チェックボックス(未チェック時はPOSTに含まれない)
$in_stock = isset($_POST['product_in_stock']) ? '1' : '0';
update_post_meta($post_id, '_product_in_stock', $in_stock);
});
ステップ4:メタボックスをスクリーンオプションで非表示対応にする
// メタボックスを特定条件で非表示(サイドバーのみ表示など)
add_action('add_meta_boxes', function(): void {
// 現在のユーザーが管理者の場合のみ表示
if (!current_user_can('manage_options')) {
return;
}
add_meta_box('myplugin_admin_box', '管理者設定', 'myplugin_admin_callback', 'post', 'side');
});
// 不要なデフォルトメタボックスを削除
add_action('add_meta_boxes', function(): void {
remove_meta_box('postcustom', 'post', 'normal'); // カスタムフィールド
remove_meta_box('commentstatusdiv', 'post', 'normal'); // コメント状態
}, 20); // 優先度20(add_meta_boxesより後に実行)
ステップ5:WP-CLIでメタデータを確認する
# 保存されたメタデータを確認
wp post meta list 123 --format=table
# 特定フィールドの値を取得
wp post meta get 123 _product_price
wp post meta get 123 _product_sku
# メタデータを直接更新(テスト用)
wp post meta update 123 _product_price 9800
# 特定メタキーを持つ投稿を検索
wp post list --meta_key=_product_price --meta_value=9800 --format=table
注意事項
save_postフックでは必ずwp_verify_nonce()で検証し、current_user_can()で権限を確認してください- 自動保存(autosave)時は処理をスキップする条件チェックが必須です
- チェックボックスはPOSTに含まれない場合があるため、
isset()で確認してから処理してください
まとめ
add_meta_box() でメタボックスを登録し、コールバックでHTMLフォームを出力します。save_post フックでnonce検証・権限確認後に update_post_meta() でデータを保存します。WP-CLIの wp post meta list で保存結果を確認できます。